如何将JavaFX WebView内容适合窗口大小?
我想显示缩放到父窗口大小的浏览器内容。 SetScale
部分地解决了这个问题,因为组件行为疯狂,并且缩放浏览器位于父窗口的中心。显示的网站大小始终为1280x800,窗口大小可以手动设置。
答案 0 :(得分:1)
答案基于:https://gist.github.com/RupprechJo/7455537
解决方案是将WebView置于缩放窗格中,然后执行内容调整大小。
它可能看起来有点邋but但显示出主要想法并且......有效!
package webscale;
import java.awt.BorderLayout;
import java.awt.Dimension;
import javafx.application.Platform;
import javafx.beans.property.DoubleProperty;
import javafx.beans.property.SimpleDoubleProperty;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.embed.swing.JFXPanel;
import javafx.geometry.Pos;
import javafx.scene.Node;
import javafx.scene.Scene;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.Pane;
import javafx.scene.transform.Scale;
import javafx.scene.web.WebView;
import javax.swing.JApplet;
import javax.swing.JFrame;
import javax.swing.SwingUtilities;
public class WebScale extends JApplet {
static ZoomingPane zoomingPane;
private static JFXPanel fxContainer;
/**
* @param args the command line arguments
*/
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
final JFrame frame = new JFrame("JavaFX 2 in Swing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JApplet applet = new WebScale();
applet.init();
frame.setContentPane(applet.getContentPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
applet.start();
frame.addComponentListener(new java.awt.event.ComponentAdapter() {
@Override
public void componentResized(java.awt.event.ComponentEvent evt) {
if (zoomingPane != null) {
zoomingPane.setZoomFactors((double)(frame.getWidth()/ 1280.0), (double)(frame.getHeight() / 800.0));
}
}
});
}
});
}
@Override
public void init() {
fxContainer = new JFXPanel();
fxContainer.setPreferredSize(new Dimension(300, 200));
add(fxContainer, BorderLayout.CENTER);
// create JavaFX scene
Platform.runLater(new Runnable() {
@Override
public void run() {
createScene();
}
});
}
private void createScene() {
WebView webView = new WebView();
zoomingPane = new ZoomingPane(webView);
BorderPane bp = new BorderPane();
bp.setCenter(zoomingPane);
fxContainer.setScene(new Scene(bp));
webView.getEngine().load("http://google.pl");
}
private class ZoomingPane extends Pane {
Node content;
private final DoubleProperty zoomFactor = new SimpleDoubleProperty(1);
private double zoomFactory = 1.0;
private ZoomingPane(Node content) {
this.content = content;
getChildren().add(content);
final Scale scale = new Scale(1, 1);
content.getTransforms().add(scale);
zoomFactor.addListener(new ChangeListener<Number>() {
@Override
public void changed(ObservableValue<? extends Number> observable, Number oldValue, Number newValue) {
scale.setX(newValue.doubleValue());
scale.setY(zoomFactory);
requestLayout();
}
});
}
@Override
protected void layoutChildren() {
Pos pos = Pos.TOP_LEFT;
double width = getWidth();
double height = getHeight();
double top = getInsets().getTop();
double right = getInsets().getRight();
double left = getInsets().getLeft();
double bottom = getInsets().getBottom();
double contentWidth = (width - left - right)/zoomFactor.get();
double contentHeight = (height - top - bottom)/zoomFactory;
layoutInArea(content, left, top,
contentWidth, contentHeight,
0, null,
pos.getHpos(),
pos.getVpos());
}
public final Double getZoomFactor() {
return zoomFactor.get();
}
public final void setZoomFactor(Double zoomFactor) {
this.zoomFactor.set(zoomFactor);
}
public final void setZoomFactors(Double zoomFactorx, Double Zoomfactory) {
this.zoomFactory = Zoomfactory;
this.zoomFactor.set(zoomFactorx);
}
public final DoubleProperty zoomFactorProperty() {
return zoomFactor;
}
}
}
答案 1 :(得分:1)
使用“堆栈窗格”来整理布局。然后使用'Rectangle2D primaryScreenBounds = Screen.getPrimary()。getVisualBounds(); '获取用户窗口尺寸。
package com.ruemerc;
import javafx.application.Application;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.concurrent.Worker;
import javafx.geometry.Rectangle2D;
import javafx.scene.Scene;
import javafx.scene.image.Image;
import javafx.scene.layout.StackPane;
import javafx.scene.web.WebEngine;
import javafx.scene.web.WebView;
import javafx.stage.Screen;
import javafx.stage.Stage;
public class MainWindow extends Application{
public static void main(String[] args) {
launch(args);
}
@Override
public void start(Stage primaryStage) throws Exception {
WebView webview = new WebView();
StackPane stackPane=new StackPane();
stackPane.getChildren().add(webview);
WebEngine webEngine= webview.getEngine();
webEngine.setJavaScriptEnabled(true);
webEngine.load("http://www.ruemerc.co.ke/apps/smsgateway");
webEngine.getLoadWorker().stateProperty().addListener(
new ChangeListener<Worker.State>() {
public void changed(@SuppressWarnings("rawtypes") ObservableValue ov, Worker.State oldState, Worker.State newState) {
if(newState.toString().equals("FAILED")){
webEngine.loadContent("<!DOCTYPE html><html><head><title>Page Title</title></head><body>"
+ "<h1>Error:</h1>"
+ "<p>Internet connection Problem.</p>" +"<button onclick=\"window.location.href='http://www.ruemerc.co.ke/apps/smsgateway/'\">Retry</button>"
+ "</body></html>");
}
}
});
Scene scene=new Scene(stackPane);
primaryStage.setTitle("Ruemerc SMS");
primaryStage.getIcons().add(new Image("images/logoedtrack.png"));
primaryStage.setScene(scene);
Rectangle2D primaryScreenBounds = Screen.getPrimary().getVisualBounds();
//set Stage boundaries to visible bounds of the main screen
primaryStage.setX(primaryScreenBounds.getMinX());
primaryStage.setY(primaryScreenBounds.getMinY());
primaryStage.setWidth(primaryScreenBounds.getWidth());
primaryStage.setHeight(primaryScreenBounds.getHeight());
primaryStage.show();
}
}