How to re-center polymer paper dialog after dynamic content loads..? - polymer

Polymer how to re-center paper dialog after dynamic image loads..??
Please check image attached.

Is the best way I found yet..
If the content changes the dialog needs to be notified:
this.$.dialog.notifyResize();
this.$.dialog.toggle();
if(this.$.dialog.opened) {
this.async(function () {
this.$.dialog.notifyResize();
});
}
Ref: https://github.com/PolymerElements/paper-dialog/issues/68

Related

Testing <dialog>'s backdrop clicks in React testing library

I created a popup component in React using the element. The element comes with a useful pseudo element "::backdrop". I created functionality that when a user clicks on the backdrop, the popup closes. I'm trying to test this behaviour in React testing library, but without success. I can't seem to interact with this ::backdrop element. Is there a way to do it which I'm overlooking, or maybe another way to test this behaviour?
Unfortunately it is impossible to directly interact with/target pseudo elements and that includes ::backdrop.
When you click on the "backdrop" you actually click on the <dialog> element, so in order to test that, you need to target that element.
Give your dialog element a role="dialog" and in your test use getByRole('dialog', { hidden: true }) to grab it. the hidden: true option is necessary as RTL doesn't fully support the dialog element yet so at the moment it always considers it "hidden", even when it is open.
After grabbing the dialog element, just simulate a click using the userEvent api and check that your function was called.
P.S - You might want include this workaround mentioned in this thread to mock the showModal and close methods for the same reason that jsdom doesn't fully support it yet
In the end your test might look like something along these lines:
// workaround until dialog elements are supported in jest/jsdom
beforeAll(() => {
HTMLDialogElement.prototype.showModal = jest.fn();
HTMLDialogElement.prototype.close = jest.fn();
});
it('closes the dialog when the backdrop is clicked', async () => {
const { user } = render(<Modal {...props} />);
const backdrop = screen.getByRole('dialog', { hidden: true });
await user.click(backdrop);
expect(onBackdropClick).toHaveBeenCalledTimes(1);
});
I was creating a modal component based on the <dialog> element very recently and these 2 resources helped me a lot:
React modal using dialog element - article
introduction to dialog element - video

Angular Material autocomplete panel does not become hidden when autocomplete becomes hidden in scrolling area

There is a bug I've opened up for this (https://github.com/angular/components/issues/20209), I'm asking this question to see if there is a workaround or fix anyone knows.
The issue is visible on this demo page https://stackblitz.com/edit/angular-rczreu
The issue is due to the CDK panel (autocomplete's panel) being rendered as a separate layer in the demo, distinct from the autocomplete element. So when the autocomplete element moves out of the visible area of the scrollable element, the autocomplete does become hidden, but the panel does not due to this separate layer rendering.
In pseudo code, the angular html is as follows,
<html>
<body>
<my-app>
<my-component cdkScrollable> // this is a scrollable element, it's children should become hidden when we scroll
<autocomplete></autocomplete>
<some-other-child></some-other-child>
</my-component>
</my-app>
<div class="cdk-overlay-container">
// ... other stuff
<div>
// autocomplete's panel
</div>
</div>
Okay, I've made a fork of your StackBlitz with the solution here:
https://stackblitz.com/edit/angular-rczreu-yqyphm
Basically here are the highlights:
On your component html, I added a component ID to the formField:
<mat-form-field #formField class="example-full-width">
Then on your component ts, I added the references to the ViewChild for the Autocomplete elements (the form field and the Autocomplete panel itself):
#ViewChild(MatAutocompleteTrigger) autocomplete: MatAutocompleteTrigger;
#ViewChild("formField") autoCompleteFormField: MatFormField;
Then I added an implementation of AfterViewInit to your component to make sure the view elements are already loaded so that it is not undefined.
ngAfterViewInit() {
var observer = new IntersectionObserver((entries) => {
if(!entries[0].isIntersecting)
console.log('Element is is not in screen');
this.autocomplete.closePanel();
}, { threshold: [1] });
observer.observe(this.autoCompleteFormField._elementRef.nativeElement);
}
So what this code snippet do is using the efficient Intersection Observer API which detects if an element is on screen or not. Then just simply close the autocomplete panel if the element is off-screen.
https://usefulangle.com/post/113/javascript-detecting-element-visible-during-scroll#:~:text=To%20know%20whether%20the%20element%20is%20fully%20visible%20in%20viewport,height%20and%20bottom%20%3E%3D%200.

Bootstrap panel collapse incorrect icons with collabsible panel in another collapsible panel

I'm trying to use collapsible panels to show and hide data and am using glyph icons also to show the state. Initially on start up the glyph icons were not showing correctly (wrong states) but I found a fix for this using JS.
$('.collapse').on('shown.bs.collapse', function(){
$(this).parent().find(".glyphicon-plus").removeClass("glyphicon-plus").addClass("glyphicon-minus");
}).on('hidden.bs.collapse', function(){
$(this).parent().find(".glyphicon-minus").removeClass("glyphicon-minus").addClass("glyphicon-plus");
});
See this JSFiddle working correctly (i.e. icons show the correct state on start up and when minimizing and maximizing the individual collpasible panels)
However, I then put these 2 collapsible panels into a simple collabsible button (readmoreless) so these are only shown when the Read more button is presssed and hidden when Read less is pressed.
I added some JS for this to toggle the text on the button (from Read more to Read less) when the button is pressed.
$(document).ready(function(){
$("#readmoreless").on("hide.bs.collapse", function(){
$(".btn2").html('Read more');
});
$("#readmoreless").on("show.bs.collapse", function(){
$(".btn2").html('Read less');
});
});
However the addition of this collapsible button area now breaks the panel icon states. They both seem to be affected by clicking on the Read more/Read less button and also both are affected when collapsing/opening one of the panels. The states of both panel area icons are always the same as each other even though one might be open and one closed.
See updated broken JSFiddle here.
Has anyone got any ideas how I can make this work?
Thanks!
I've replaced the .collapse with .panel-collapse to fix the icon states and changed the way you replace your text (read more / read less) by overriding the text() function return inside the click() function of your button.
Here is what you should insert to your JS
//Change icon states
$('.panel-collapse').on('shown.bs.collapse', function () {
$(this).parent().find(".glyphicon-plus").removeClass("glyphicon-plus").addClass("glyphicon-minus");
}).on('hidden.bs.collapse', function () {
$(this).parent().find(".glyphicon-minus").removeClass("glyphicon-minus").addClass("glyphicon-plus");
});
//Read more or less
$(document).ready(function () {
$(".btn2").click(function () {
$(this).text(function (i, text) {
return text === "Read more" ? "Read less" : "Read more";
})
});
});
JSFiddle
text() - function

One page website - Buttons .show and .hide text but how to link to a specific "page"?

I made a one-page website which only has text on it and buttons which only purpose is to change the text in the container. And now when I made everything I forgot what if someone wants to link to a specific "page"/text to my site. What would be the best way to do this? So when someone clicks the button, address changes for each paragraph and if someone points to that address specific paragraph would appear/specific button function would do its job.
This is a jquery code for buttons so you can understand better :
$(document).ready(function () {
$('[id*=txt]').hide();
$('[id*=home]').show();
$('#btnhome').css({'background-color':'#555', 'opacity':"0.5"});
$('.button').click(function (){
$('[id*=txt]').hide();
$('.button').css({'background':'transparent', 'opacity':'1'});
$(this).css({'background-color':'#555', 'opacity':'0.5'});
});
$('#btnhome').click(function () {
$('[id*=home]').show();
});
$('#btnabout').click(function () {
$('[id*=about]').show();
});
$('#btncontact').click(function () {
$('[id*=contact]').show();
});
You would have to add a parameter to the URL. Like http://mysite.com?page=1
Then you would have to parse out the parameter. Here's a site that will help you with that.
Finally, you would provide for the page parameter in the document.ready function. You could use a switch statement for that.

How to make tabs on the web page?

How to make tabs on the web page so that when click is performed on the tab, the tab gets css changed, but on the click page is also reloaded and the css is back to original.
dont use the jquery :D
all of what you needs a container, a contained data in a varable and the tabs
the container is the victim of the css changes.
the tabs will trigger the changing process.
if you have a static content, you can write this into a string, and simply load it from thiss.
if you have a dinamically generated content, you need to create ajax request to get the fresh content, and then store it in the same string waiting for load.
with the tabs you sould create a general functionusable for content loading.
function load(data) {
document.getElementById("victim").innerHTML = data;
}
function changeCss(element) {
//redoing all changes
document.getElementById("tab1").style.background="#fff";
document.getElementById("tab2").style.background="#fff";
element.style.background = "#f0f";
}
with static content the triggers:
document.getElementById("tab1").onclick = function() {load("static data 1");changeCss(document.getElementById("tab1"))};
document.getElementById("tab2").onclick = function() {load("static data 2");changeCss(document.getElementById("tab2"))};
if you want to change the css, you need another function which do the changes.
i tell you dont use the jquery because you will not know what are you doing.
but thiss whole code can be replaced by jquery like this:
$("tab1").click(function(e) {
$("#tab1 | #tab2").each(function() {
$(this).css("background","#fff"); });
$(this).css("background","#00f");
$("#victim").append("static content 1");
});
$("tab12click(function(e) {
$("#tab1 | #tab2").each(function() {
$(this).css("background","#fff"); });
$(this).css("background","#00f");
$("#victim").append("static content 2");
});
if you know how javascript works then there is noting wrong with the jquery, but i see there is more and more people who just want to do their website very fast and simple, but not knowing what are they doing and running into the same problem again and again.
Jquery UI Tabs:
http://jqueryui.com/demos/tabs/
Have a <A href tag around the "tab" and use onClick to fire some Javascript that changes the CSS.
If you do not want use Jquery for creating of UI tabs, please see my cross-browser JavaScript code: GitHub.
You can use different ways to create tabs and tab content.
Tab content can added only when tab gets focus.
You can remember selected tab. Selected tab opens immediatelly after opening of the page.
You can create tabs inside tab.
Custom background of the tab is available.
Example: Tabs