Is there a way to prevent updates (painting) to a `WebView` and then re-enable them? - javafx

Is there a way to prevent updates (painting) to a WebView and then re-enable them?
e.g.
disable painting
set new html content
re-enable painting
Why I'd like to do this
because my html is jumpy the elements will all be in the same positions on the HTML page after as before but during the update of the HTML they will move around a bit. Since I'm refreshing the HTML on a periodic basis, it is quite annoying to have it jump around often.

There is no real painting on/off switch either in WebView or in general for JavaFX (as far as I know), but perhaps the workaround below might help.
You could always:
snapshot the WebView, to create an image.
Replace the WebView with the snapshot image.
Set new html content.
Replace the snapshot image with the WebView.
To do this, you could put the snapshot image and the WebView in a StackPane, with the WebView on top and trigger setVisible(false) on the WebView when you want to hide it and set new html content and trigger setVisible(true) once you want the new content to be seen.
You might want to use some synchronization to know when the newly set html content has finished rendering either by a message from the JavaScript to Java or by monitoring the html events in Java (doing such is beyond the scope of this post). There might also be some issues with the WebView detecting it is not actually visible and then deciding to be lazy because of an optimization and not repaint itself for updated html content until it is made visible again (not sure I haven't tried it).
Anyway, perhaps give this technique a try and see if it works for you.

Related

Gluon Mobile 5.0.0 - New FAB behaviour causes trouble

In our app we use multiple floating action buttons. With Gluon 4.4.4 we added them as layers, which had the following behaviour:
Each view had it's own FAB.
When changing the view, the FAB was hiding.
When changing back to the view, the FAB was showing.
Now, with Gluon 5.0.0 (FAB's as objects) the following happens:
The buttons get stacked over each other, when they are not hidden.
When they are hidden and we change back to a view, the FAB is no longer showing.
This led to a lot of trouble and unnecessary code lines. How can we improve this or how is it intended to be used?
We could imagine to use one FAB for the whole app and exchange it's content for each view - however, this ends up in a bigger mess as well, since it would have to be declared public etc.
Any help is appreciated :-)
You are looking for the new FloatingActionButton#showOn(View) method.
This method makes sure to automatically show and hide the FAB depending on the View's showing property, removing most of the boiler code required in earlier versions to achieve the same functionality.
From the Javadocs:
Makes sure that the FAB is automatically shown when the supplied view is shown. The FAB also automatically hides when the view is hidden. This allows the developer to not worry about calling show() and hide() methods explicitly.

Google VR Reticle Click on UI Button

So I am having this issue with using Google VR reticle where I cannot click a button. I have an image attached showing the heirarchy and the PlayButton is what I am trying to click. The Canvas has a Graphic Raycaster, the button has an Event Trigger that calls the method to navigate to the next scene. The UpScrollPanel, and DownScrollPanel work just fine. The EventSystem has the Gaze Input Module, as well as Event System, and Touch Input Module.
Any ideas on how to get this working? I have watched a few videos from NurFACEGAMES and while they helped a little, I haven't gotten the click to work yet.
Oh, and I am using Unity 5.3.4f
Sometimes things can get in the way of the button, make sure that no other UI elements overlap it, for example text borders (which are actually larger than they appear). You can also fix this by moving the button up the hierarchy among its siblings, I believe the first child is top.
Also try moving the button up the hierarchy if possible, sometimes UI having certain parents makes them not work
The canvas object should have a graphic raycaster
I found the issue to be unrelated to anything I thought it was. The menu I was using is a prefab I also use in another view that isn't VR. The scrollrect was loading that prefab, instead of the modified one I was using in the VR menu, and therefore the triggers I had added to the button were no being used when the app loaded.

Immediately clearing the contents of an IFrame in Flex

I have a Flex HTML component that is displaying content from a remote URL and a button in the Flex application that reloads the content. However, it takes a few seconds for the IFrame's content to refresh. During this time, there is no obvious feedback to the user that any action is underway.
I would like to clear the contents of the IFrame, so there is immediate feedback after clicking refresh, and then load the remote URL again. Is there a way to do this?
I've tried setting the HTMLText property to "" and setting the IFrame location to "about:blank", and neither of these have the desired immediate effect. (on it's own, setting the location to about:blank immediately clears the IFrame, but if it is followed by resetting the location to the original URL, the immediate clearing doesn't occur. Is this something to do with the IFrame caching the original page?)
One approach is to remove the component from the display list and add a new instantiated component back in its place.
This will assure fully initialized state.
One other way you could get around would be having a blank iframe or loading screen ready with the same size and same position, while the contents are being loaded, hide the content iframe, and show the blank iframe or loading screen. This could be much easier to achieve a more flexible result.

How to update a QLayout and get the new dimensions before returning?

This is driving me nuts. I have a custom menu class that, when set visible, shows a list of items located in a particular folder. When a hardware button is pressed, my application gets the latest list of items, populates the menu with them, and returns.
The menu displaying these items uses a QListWidget filled with custom widgets. Each of the widgets contains one or more QLabels in a horizontal layout, and is created at the time the menu is shown. In order to adjust the text displayed based on the menu width available, I need to get the size of the QLabel AFTER it has been resized according to the layout, but before the menu becomes visible to the user. The problem is, my layout does not get updated until all of the functions constructing my list return.
I have tried QApplication::ProcessEvents() and the layout update functions, but none of them have updated the values of my QLabels before returning. I can set a QTimer when the button is initially pressed, and have it show the menu, update the items, and stop itself, but that seems like a terrible solution.
Any help would really be appreciated! I've spent most of a day on this.
Marlon
I had this exact problem and could not find an answer anywhere on the Internet. Calling Layout.update(), Layout.activate(), or widget.adjustSize() (all suggested in various places) all did not work.
I had a widget with a vertical layout that I wanted to add a QLabel to and then immediately use the size of the QLabel.
The only thing that worked reliably was
layout->addWidget(myLabel);
myLabel->show();
size = myLabel->size();
It would seem that layouts will just not recalculate until you either return from a function and allow the Qt event loop to progress or manually call show() yourself.
How to update a QLayout and get the new dimensions before returning?
Don't. You're not meant to do that. It'll drive you "nuts" because you're doing it backwards. Layout updates are handled asynchronously from the event loop. Instead of getting layout dimensions right away, set yourself up to be part of the system. Some options are:
Implement a custom widget that will interact properly with the layout, growing to fill the available width of the layout. Perhaps all you need is a size policy and a way to elide text?
Make a custom layout that takes the special properties of your use case into account.
You want to call QWidget::adjustSize() on your parent widget. This will force the layout recalculations.
Have you tried using layout()->update(); ?
I've tried many but nothing works for me on Qt 5.15.
Only invented little patch - create timer and get size after 20 msec:
QTimer::singleShot(20, this, [this]
{
const auto height = myLayout->contentsRect().height();
// ...
});

Reducing flicker with QBoxLayout

Whenever a displayed QBoxLayout is populated, there's some flicker on the screen as widgets get added to the layout. How do I stop this flicker?
setUpdatesEnabled did not do the trick.
show() the widget only after you've finished populating it/laying it out.
Or don't attach your layout to it's widget before you're done adding things to it. (i.e. only call setLayout(your_layout) when you've finished adding things to your_layout).
Alternatively, look into the updatesEnabled QWidget property. You can use that to temporarily disable the widget's updates to prevent flicker. (This is most useful on the more complex widgets like QTableWidget and similar when you are making "massive" changes to the underlying data.)
Quote from the doc above:
setUpdatesEnabled() is normally used to disable updates for a short period of time, for instance to avoid screen flicker during large changes. In Qt, widgets normally do not generate screen flicker, but on X11 the server might erase regions on the screen when widgets get hidden before they can be replaced by other widgets. Disabling updates solves this.

Resources