diff --git a/Ports/JavaSE/src/com/codename1/impl/javase/JavaSEPort.java b/Ports/JavaSE/src/com/codename1/impl/javase/JavaSEPort.java index 3884c37a5d..f9a47df2f4 100644 --- a/Ports/JavaSE/src/com/codename1/impl/javase/JavaSEPort.java +++ b/Ports/JavaSE/src/com/codename1/impl/javase/JavaSEPort.java @@ -4031,7 +4031,7 @@ public Class getColumnClass(int column) { skinsTable.setRowHeight(112); skinsTable.getTableHeader().setReorderingAllowed(false); final JTextField filter = new JTextField(); - final TableRowSorter sorter = new TableRowSorter<>(((DefaultTableModel) skinsTable.getModel())); + final TableRowSorter sorter = new TableRowSorter(((DefaultTableModel) skinsTable.getModel())); filter.getDocument().addDocumentListener(new javax.swing.event.DocumentListener() { @@ -6220,6 +6220,13 @@ public void run() { } + static BufferedImage deepCopy(BufferedImage bi) { + java.awt.image.ColorModel cm = bi.getColorModel(); + boolean isAlphaPremultiplied = cm.isAlphaPremultiplied(); + java.awt.image.WritableRaster raster = bi.copyData(null); + return new BufferedImage(cm, raster, isAlphaPremultiplied, null); + } + private void drawNativePeerImpl(Object graphics, PeerComponent cmp, JComponent jcmp) { if (cmp instanceof Peer) { Peer peer = (Peer)cmp; @@ -7502,6 +7509,7 @@ public Object makeTransformScale(float scaleX, float scaleY, float scaleZ) { + @Override public void setTransformScale(Object nativeTransform, float scaleX, float scaleY, float scaleZ) { AffineTransform at = (AffineTransform)nativeTransform; @@ -11851,7 +11859,8 @@ public static class Peer extends PeerComponent { private boolean matchCN1Style; - + private Image peerImage; + private boolean lightweightMode; private PeerComponentBuffer peerBuffer; // Buffered image that will be drawn to by AWT and read from @@ -12143,7 +12152,12 @@ protected void initComponent() { lastH=0; lastW=0; lastZoom=1; + peerImage = null; super.initComponent(); + if (!init) { + addNativeCnt(); + } + } @Override @@ -12153,33 +12167,127 @@ protected void deinitialize() { instance.testRecorder.dispose(); instance.testRecorder = null; } - SwingUtilities.invokeLater(new Runnable() { + if (init) { + removeNativeCnt(); + } + + // We set visibility to false, and then schedule removal + // for 1000ms from now. This will deal with the situation where + // a modal dialog is shown to avoid having to fully remove the native + // container. + //cnt.setVisible(false); + //removeNativeCnt(3000); + } + + /** + * Adds the native container to the swing component hierarchy. + * + * This can be called off the Swing event thread, in which case it will just schedule a call + * to itself later. + * + * + */ + protected void addNativeCnt() { + + if (!EventQueue.isDispatchThread()) { + EventQueue.invokeLater(new Runnable() { + public void run() { + addNativeCnt(); + } + }); + return; + } + + if (!init && isInitialized()) { - @Override - public void run() { - frm.remove(cnt); - frm.repaint(); - } - }); + init = true; + cnt.setVisible(true); + frm.add(cnt, 0); + frm.repaint(); + } + + } + + /** + * Removes the native container from the Swing component hierarchy. + * This can be called on or off the swing event thread. If called off the swing event + * thread, it will just schedule itself on the event thread later - async. + */ + protected void removeNativeCnt() { + if (!EventQueue.isDispatchThread()) { + EventQueue.invokeLater(new Runnable() { + public void run() { + removeNativeCnt(); + } + }); + return; + } + if (peerImage == null) { + peerImage = generatePeerImage(); + } + init = false; + frm.remove(cnt); + frm.repaint(); + + } + + @Override + protected com.codename1.ui.Image generatePeerImage() { + if (peerImage != null) { + return peerImage; + } + if (peerBuffer != null) { + peerBuffer.modifyBuffer(new Runnable() { + public void run() { + BufferedImage bimg = peerBuffer.getBufferedImage(); + peerImage = instance.new NativeImage(bimg); + } + + }); + } + return super.generatePeerImage(); + } + + @Override + protected boolean shouldRenderPeerImage() { + return lightweightMode && peerImage != null; } + + + + protected void setLightweightMode(final boolean l) { + if (lightweightMode == l) { + if (l || init) { + return; + } + } + lightweightMode = l; + if (l) { + if (peerImage == null) { + peerImage = generatePeerImage(); + } + } else { + peerImage = null; + } SwingUtilities.invokeLater(new Runnable() { @Override public void run() { - if (!l) { if (!init) { init = true; cnt.setVisible(true); frm.add(cnt, 0); frm.repaint(); + peerImage = null; } else { - cnt.setVisible(false); + cnt.setVisible(true); } } else { if (init) { + cnt.setVisible(false); } } @@ -12194,8 +12302,13 @@ protected com.codename1.ui.geom.Dimension calcPreferredSize() { (int)(cmp.getPreferredSize().getHeight() * retinaScale / instance.zoomLevel)); } + @Override public void paint(final Graphics g) { + if (lightweightMode) { + super.paint(g); + return; + } if (init) { onPositionSizeChange(); instance.drawNativePeer(Accessor.getNativeGraphics(g), this, cnt); @@ -12310,7 +12423,7 @@ public void run() { public static boolean checkForPermission(String permission, String description){ return checkForPermission(permission, description, false); } - + public static boolean checkForPermission(String permission, String description, boolean forceAsk){ if(!android6PermissionsFlag){ diff --git a/Ports/JavaSE/src/com/codename1/impl/javase/fx/SEBrowserComponent.java b/Ports/JavaSE/src/com/codename1/impl/javase/fx/SEBrowserComponent.java index 71eedada6e..a1a232f0be 100644 --- a/Ports/JavaSE/src/com/codename1/impl/javase/fx/SEBrowserComponent.java +++ b/Ports/JavaSE/src/com/codename1/impl/javase/fx/SEBrowserComponent.java @@ -288,8 +288,8 @@ private void setZoom(double zoom) { } private static void init(SEBrowserComponent self, BrowserComponent p) { - final WeakReference weakSelf = new WeakReference<>(self); - final WeakReference weakP = new WeakReference<>(p); + final WeakReference weakSelf = new WeakReference(self); + final WeakReference weakP = new WeakReference(p); SwingUtilities.invokeLater(new Runnable() { public void run() { SEBrowserComponent self = weakSelf.get(); @@ -381,6 +381,11 @@ public void changed(ObservableValue ov, State oldState, State newState) { if (self == null || p == null) { return; } + /* + // DISABLING TRANSPARENCY BECAUSE IT CAUSES A MESS WHEN SCROLLING + // ORIGINALLY TRIED TO ADD THIS FOR CSS GENERATION, BUT LATER OPTED + // TO ONLY USE CEF FOR THAT ANYWAYS + // SINCE THIS FX COMPONENT IS DEPRECATED, WE'LL JUST LET IT DIE self.transparent = p.getStyle().getBgTransparency() == 0; if (self.transparent) { try { @@ -392,7 +397,7 @@ public void changed(ObservableValue ov, State oldState, State newState) { setBackgroundColor.invoke(webPage, 0); } catch (Exception ex){} } - + */ String url = self.web.getEngine().getLocation(); if (newState == State.SCHEDULED) { p.fireWebEvent("onStart", new ActionEvent(url)); diff --git a/Samples/samples/BrowserComponentBlocked3300/BrowserComponentBlocked3300.java b/Samples/samples/BrowserComponentBlocked3300/BrowserComponentBlocked3300.java new file mode 100644 index 0000000000..64a458fdb1 --- /dev/null +++ b/Samples/samples/BrowserComponentBlocked3300/BrowserComponentBlocked3300.java @@ -0,0 +1,128 @@ +package com.codename1.samples; +import static com.codename1.ui.CN.*; + +import com.codename1.components.SpanLabel; +import com.codename1.ui.*; +import com.codename1.ui.events.ActionEvent; +import com.codename1.ui.events.ActionListener; +import com.codename1.ui.layouts.BorderLayout; +import com.codename1.ui.plaf.UIManager; +import com.codename1.ui.util.Resources; +import com.codename1.io.Log; + + +import java.io.IOException; +import java.util.ArrayList; + +import com.codename1.ui.layouts.BoxLayout; +import com.codename1.io.NetworkEvent; + +/** + * This file was generated by Codename One for the purpose + * of building native mobile applications using Java. + */ +public class BrowserComponentBlocked3300 { +private Form current; +private Resources theme; +boolean onloadCalled=false; +BrowserComponent bc; +public void init(Object context) { + // use two network threads instead of one + updateNetworkThreadCount(2); + + theme = UIManager.initFirstTheme("/theme"); + + // Enable Toolbar on all Forms by default + Toolbar.setGlobalToolbar(true); + + // Pro only feature + Log.bindCrashProtection(true); + + addNetworkErrorListener(err -> { + // prevent the event from propagating + err.consume(); + if(err.getError() != null) { + Log.e(err.getError()); + } + Log.sendLogAsync(); + Dialog.show("Connection Error", "There was a networking error in the connection to " + err.getConnectionRequest().getUrl(), "OK", null); + }); +} + +public void start() { + if(current != null){ + current.show(); + return; + } + Form hi = new Form("Hi World", new BorderLayout()); + bc=new BrowserComponent(); + bc.addWebEventListener("onLoad", new ActionListener() { + @Override + public void actionPerformed(ActionEvent evt) { + +if (onloadCalled) {return;} else +{onloadCalled=true; + +//openAlertDialog("Test Dialog after onload","Blocking"); + +} + + }}); + + bc.setPage(""+ + createLines()+ + "",""); + + Button button=new Button("Press this button after HTML is loaded to test"); + button.addActionListener(new ActionListener() { + @Override + public void actionPerformed(ActionEvent evt) { + openAlertDialog("User activated test Dialog","Blocking"); + } + }); + hi.add(BorderLayout.NORTH,button); + hi.add(BorderLayout.CENTER,bc); + hi.show(); + +} + + +private String createLines() +{ + String result=""; + for (int i=0;i<100;i++) + result=result+"

TRY TO SELECT THIS TEXT / TRY TO SCROLL - LINE "+i+"

"; + return result; +} +public void stop() { + current = getCurrentForm(); + if(current instanceof Dialog) { + ((Dialog)current).dispose(); + current = getCurrentForm(); + } +} + +public void destroy() { +} + + +Command okCommand=new Command("ok"); + +private void openAlertDialog( String s1, String s2) +{ + Dialog alertDialog=new Dialog(s1); + Button okButton=new Button(okCommand); + alertDialog.setLayout(BoxLayout.y()); + Container c1=new Container(); + c1.setLayout(BoxLayout.x()); + alertDialog.add(new SpanLabel(s2, "DialogBody")); + c1.add(okButton); + alertDialog.add(c1); + Command result=alertDialog.showDialog(); + +} +} + +