I have a jquery mobile app that has a page. This page has three DIVs, I programmatically choose one of these DIVs based on a variety of variables. Regardless, the one DIV contains a select element. This element has 20 items in it. Because of the shear quantity, the select box opens in its own dialog. I'm fine with that, however, after a user makes a choice, the pagebeforeshow event of my hosting page is fired again. My problem is, I can't seem to figure out how to detect that this event was fired as a result of the user choosing an option or closing the select dialog.
Is there a way to detect in the pagebeforeshow event how we got here?
jQuery mobile passes meta-data to the callback functions of most events. From the docs on pagebeforehow:
Triggered on the "toPage" we are transitioning to, before the actual transition animation is kicked off. Callbacks for this event will recieve a data object as their 2nd arg. This data object has the following properties on it:
prevPage (object) - A jQuery collection object that contains the page DOM element that we are transitioning away from. Note that this collection is empty when the first page is transitioned in during application startup.
You should be able to use this in your callback function to branch to your advantage, i.e. detect if prevPage is the current page. This might look like:
$('#yourPage').live('pagebeforeshow', function(event, data) {
var from = data.prevPage;
// do some inspection of `from` and branch accordingly
// might require some experimental console.logging first
});
I also didn't verify the question raised in above comment, but data.prevPage has a copy of the entire previous page's HTML, accessed via data.prevPage[0].innerHTML. I'm sure you could do something like binding to the click event on the select dialog and tell it to add a class or whatever to the DOM where the user selected whatever entry, and scrape that back out of the HTML? Just throwing an idea out there.
Related
I am using Material-ui and React-final-form. Some form elements get prefilled from the browser cache, such as a login form. The problem is that this does not trigger an onChange event in React-final-form, which leaves the form field state in the "empty" state, which is visually problematic. As soon as a render cycle is triggered, React-final-form picks up the change and the ui is good. I'm wondering how to trigger this programmatically.
Wow. Good question! If you had a ref to the input itself, perhaps you could check it’s DOM value onMount and call the onChange function manually if props.input.value was !==. Just hypothesizing here....?
I'm writing a Selenium test for my Rails application, and sometimes run into the "Stale Element" exception. It's easy enough to perform another lookup on the element before operating on it, but to keep my code DRY, I'm wondering - is there any sort of method available on Selenium::WebDriver::Element objects to "refresh" stale references?
EDIT: To clarify, I'm asking if there's some shorthand method for doing another find_by_xpath (or id, etc.) call with the same parameter being passed. It's perfectly functional, just not as terse as some sort of "refresh" method would probably be.
If I understand correctly, you are asking about some sort of "refresh" or "update" method on a WebElement instance.
Unfortunately, there is no such thing in selenium by definition. According to the relevant issue WebElement refresh() or getBy() needed:
WebElement object is a proxy, a representative of a DOM element. When
DOM element is destroyed by the browser, WebElement is marked "stale"
and can't be used anymore.
If you have a similar DOM element on another page, you can obtain it
with findElement, and Selenium will create a new WebElement object
(a proxy) for this new DOM element. Your old WebElement object will
remain stale because underlaying DOM object is destroyed and never can
be restored. Similarity is not equality.
I would recommend store element-specific locators, but once the page refreshes, you would still need to "refind" the element by the locator.
The only thing available is keeping track of your application state when writing your Selenium code.
Did you perform an action that refreshed the DOM? Then you need to perform another findElement call to get a new instance of the element you want to interact with next.
Otherwise, write your own method findElementByXpath in a Utility class that tries to find an element, catches a StaleElement exception and retries.
I am going to describe my case which is similar:
I tried to find a table cell with some value by doing this:
Get all table rows
For each row - get a collection of the columns
For each column - seek the value
One day, I had a case with too many results in the table. So, I programmed the loop to click the "Get next page" link/icon.
Simple? no! when the program clicked the "next page of the table" link, the WebElement which pointed to the table was not usable, I received the same error as the author of this question: StaleElementReferenceException
What I did is:
Get the XPATH of the table first, and then I changed the loop so if all the rows were scanned, and he value was not found and if the next icon is enabled:
Click the next page of the table.
Update the WebElement to re-point the table.
I hope I am clear.
I have an NgComponent in Angular Dart which instantiates a search box and according to the query strings it populates another div in my html template with the ng-repeat directive.
More precisely,
Query string update: there is a binding to the input text value with a field in my components' controller.
Results population: In the attach() method I added a watcher for the local field which acts as a model to the input box, and whenever it changes I add to a local list some items which then acts as a model to the ng-repeat directive in another div.
So far everything works fine. But now I want to add some event listeners inside my component, like keystroke listeners or if possible to add listeners on specific elements in my html template. I have used CSS for hover and focus events and also ng-focus and ng-blur for easy functions. But I do not think that this can be used for keystroke listeners.
The reason I want the keystroke listener is to enable results traversing using the arrow keys. While the cursor is inside the input text box I would like to move to the first result, which is in another div, with the press of Down arrow, and then continue to the other results.
Thank you
OK, It seems that I have finally found the solution.
The solution is to implement the NgShadowRootAware interface with my component and then inside the void onShadowRoot(ShadowRoot shadowRoot) method I have full access to the DOM created inside the shadow dom template.
I have a requirement to ask a question when a certain scenario happens on my MVC 4 view.
When that scenario is true, I simply want to have a jQuery UI dialog pop up modally. That dialog will simply have two radio buttons for "WidgetType" (Purple or Blue).
The viewModel has a property for SelectedWidgetType (that has a default value).
I simple am looking for the best way to handle updating the underlying model with the selection a user picks in the dialog.
Thanks in advance for any replies.
NOTE: I am using this overly simple example as the basis for other dialogs that will have more fields on them that also update the underlying model.
Creating the dialog isn't the hard part, but I am struggling with getting the values.
User jQuery's AJAX post method.
Create a view model JavaScript object on the front end that maps to the parameters of your data model. This view model object can be triggered to get updated each time the user changes his selected options by calling an update method via the change event handles of each form element.
Pass it back to the server controller by packing it into a JSON object using json2.js
If you want a full framework/elegant solution look at using knockout.js which simulates most of this for you... !
let's assume i have the following structure:
pageA.xhtml - Here we can select an item which will be needed within pageB and pageC but not in pageE.
pageB.xhtml - Here we use the Item which was selected from pageA. We
also have a selectBox and some Buttons on this page.
When selecting something from the selectBox some Buttons will be deactivated and some Text can be displayed.
(when refreshing this page we want the same state again). pageB includes
pageD which lists some stuff. Now we can navigate to pageC.
We also create some objects which are only relevant for pageC but not for other pages.
pageC.xhtml - here we get the object from pageB and depending on some User input we modify it and when we press apply we come back
to pageB which displays
our changes. From pageB we can press save which will save the changes and pageD (which is included in pageB) will be
updated.
pageD.xhtml - just lists some stuff. (will only included within pageB)
pageE.xhtml - This page will start something completely differend and does not need the input from pageA but you can navigate directly
to pageC. In this case pageC has to
hide some things.
I hope the example is somehow clear. Actually i just made it up to make my question a bit clearer: I want to know what the best practises are to pass data between different pages and save the actual state (also have the same state when coming back).
Also how to reset/clear data which are needed in some pages but not in different ones.
For example some data will be needed for several pages but some only within nested pages (in an optimal world the data within the nested pages should be cleared when leaving them)
Of course i could save stuff i need into the session, but then i have to be careful to remove those stuff again when i don't need it anymore. JSF and CDI support Conversations. But the problem here is that it is not possible to have nested conversations. Of course i also could pass everything with request parameters .. but in this case i have to be careful if i have ajax requests within my page (i guess i would have to send always all parameters).
I'm using JSF 2.0 with CDI. Any answer will be appreciated. Sadly i cannot provide any code example .. so i hope i was able to express my self clear enough.
greetings kukudas
You could create a new CDI scope or recreate the ViewScope in CDI. Take a look at CODI conversations as well.