Fix problems with window resizing in Linux

This commit is contained in:
Haowei Wen 2025-01-04 00:34:48 +08:00
parent b5cea83a8a
commit 56d20a5d08

View File

@ -48,8 +48,7 @@ public class DecoratorSkin extends SkinBase<Decorator> {
private final Stage primaryStage; private final Stage primaryStage;
private final TransitionPane navBarPane; private final TransitionPane navBarPane;
private double xOffset, yOffset, newX, newY, initX, initY; private double mouseInitX, mouseInitY, stageInitX, stageInitY, stageInitWidth, stageInitHeight;
private boolean titleBarTransparent = true;
/** /**
* Constructor for all SkinBase instances. * Constructor for all SkinBase instances.
@ -299,13 +298,6 @@ public class DecoratorSkin extends SkinBase<Decorator> {
return navBar; return navBar;
} }
private void updateInitMouseValues(MouseEvent mouseEvent) {
initX = mouseEvent.getScreenX();
initY = mouseEvent.getScreenY();
xOffset = mouseEvent.getSceneX();
yOffset = mouseEvent.getSceneY();
}
private boolean isRightEdge(double x, double y, Bounds boundsInParent) { private boolean isRightEdge(double x, double y, Bounds boundsInParent) {
return x < root.getWidth() && x >= root.getWidth() - root.snappedLeftInset(); return x < root.getWidth() && x >= root.getWidth() - root.snappedLeftInset();
} }
@ -322,154 +314,139 @@ public class DecoratorSkin extends SkinBase<Decorator> {
return x >= 0 && x <= root.snappedLeftInset(); return x >= 0 && x <= root.snappedLeftInset();
} }
private boolean setStageWidth(double width) { private void resizeStage(double newWidth, double newHeight) {
if (width >= primaryStage.getMinWidth() && width >= titleContainer.getMinWidth()) { if (newWidth < 0)
// Workaround for JDK-8344372 (https://github.com/openjdk/jfx/pull/1654) newWidth = primaryStage.getWidth();
// Width and height must be set simultaneously to avoid the bug if (newWidth < primaryStage.getMinWidth())
primaryStage.setWidth(width); newWidth = primaryStage.getMinWidth();
primaryStage.setHeight(primaryStage.getHeight()); if (newWidth < titleContainer.getMinWidth())
initX = newX; newWidth = titleContainer.getMinWidth();
return true;
} else {
if (width >= primaryStage.getMinWidth() && width <= titleContainer.getMinWidth()) {
primaryStage.setWidth(titleContainer.getMinWidth());
primaryStage.setHeight(primaryStage.getHeight());
}
return false; if (newHeight < 0)
} newHeight = primaryStage.getHeight();
if (newHeight < primaryStage.getMinHeight())
newHeight = primaryStage.getMinHeight();
if (newHeight < titleContainer.getMinHeight())
newHeight = titleContainer.getMinHeight();
// Width and height must be set simultaneously to avoid JDK-8344372 (https://github.com/openjdk/jfx/pull/1654)
primaryStage.setWidth(newWidth);
primaryStage.setHeight(newHeight);
} }
private boolean setStageHeight(double height) { private void onMouseMoved(MouseEvent mouseEvent) {
if (height >= primaryStage.getMinHeight() && height >= titleContainer.getHeight()) { if (!primaryStage.isFullScreen() && primaryStage.isResizable()) {
primaryStage.setHeight(height); double x = mouseEvent.getX(), y = mouseEvent.getY();
primaryStage.setWidth(primaryStage.getWidth()); Bounds boundsInParent = root.getBoundsInParent();
initY = newY; double diagonalSize = root.snappedLeftInset() + 10;
return true; if (this.isRightEdge(x, y, boundsInParent)) {
} else { if (y < diagonalSize) {
if (height >= primaryStage.getMinHeight() && height <= titleContainer.getHeight()) { root.setCursor(Cursor.NE_RESIZE);
primaryStage.setHeight(titleContainer.getHeight()); } else if (y > root.getHeight() - diagonalSize) {
primaryStage.setWidth(primaryStage.getWidth()); root.setCursor(Cursor.SE_RESIZE);
}
return false;
}
}
// ====
protected void onMouseMoved(MouseEvent mouseEvent) {
if (!primaryStage.isFullScreen()) {
updateInitMouseValues(mouseEvent);
if (primaryStage.isResizable()) {
double x = mouseEvent.getX(), y = mouseEvent.getY();
Bounds boundsInParent = root.getBoundsInParent();
double diagonalSize = root.snappedLeftInset() + 10;
if (this.isRightEdge(x, y, boundsInParent)) {
if (y < diagonalSize) {
root.setCursor(Cursor.NE_RESIZE);
} else if (y > root.getHeight() - diagonalSize) {
root.setCursor(Cursor.SE_RESIZE);
} else {
root.setCursor(Cursor.E_RESIZE);
}
} else if (this.isLeftEdge(x, y, boundsInParent)) {
if (y < diagonalSize) {
root.setCursor(Cursor.NW_RESIZE);
} else if (y > root.getHeight() - diagonalSize) {
root.setCursor(Cursor.SW_RESIZE);
} else {
root.setCursor(Cursor.W_RESIZE);
}
} else if (this.isTopEdge(x, y, boundsInParent)) {
if (x < diagonalSize) {
root.setCursor(Cursor.NW_RESIZE);
} else if (x > root.getWidth() - diagonalSize) {
root.setCursor(Cursor.NE_RESIZE);
} else {
root.setCursor(Cursor.N_RESIZE);
}
} else if (this.isBottomEdge(x, y, boundsInParent)) {
if (x < diagonalSize) {
root.setCursor(Cursor.SW_RESIZE);
} else if (x > root.getWidth() - diagonalSize) {
root.setCursor(Cursor.SE_RESIZE);
} else {
root.setCursor(Cursor.S_RESIZE);
}
} else { } else {
root.setCursor(Cursor.DEFAULT); root.setCursor(Cursor.E_RESIZE);
} }
} else if (this.isLeftEdge(x, y, boundsInParent)) {
if (y < diagonalSize) {
root.setCursor(Cursor.NW_RESIZE);
} else if (y > root.getHeight() - diagonalSize) {
root.setCursor(Cursor.SW_RESIZE);
} else {
root.setCursor(Cursor.W_RESIZE);
}
} else if (this.isTopEdge(x, y, boundsInParent)) {
if (x < diagonalSize) {
root.setCursor(Cursor.NW_RESIZE);
} else if (x > root.getWidth() - diagonalSize) {
root.setCursor(Cursor.NE_RESIZE);
} else {
root.setCursor(Cursor.N_RESIZE);
}
} else if (this.isBottomEdge(x, y, boundsInParent)) {
if (x < diagonalSize) {
root.setCursor(Cursor.SW_RESIZE);
} else if (x > root.getWidth() - diagonalSize) {
root.setCursor(Cursor.SE_RESIZE);
} else {
root.setCursor(Cursor.S_RESIZE);
}
} else {
root.setCursor(Cursor.DEFAULT);
} }
} else { } else {
root.setCursor(Cursor.DEFAULT); root.setCursor(Cursor.DEFAULT);
} }
} }
protected void onMouseReleased(MouseEvent mouseEvent) { private void onMouseReleased(MouseEvent mouseEvent) {
getSkinnable().setDragging(false); getSkinnable().setDragging(false);
} }
protected void onMouseDragged(MouseEvent mouseEvent) { private void onMouseDragged(MouseEvent mouseEvent) {
getSkinnable().setDragging(true); if (!getSkinnable().isDragging()) {
if (mouseEvent.isPrimaryButtonDown() && (this.xOffset != -1.0 || this.yOffset != -1.0)) { getSkinnable().setDragging(true);
if (!this.primaryStage.isFullScreen() && !mouseEvent.isStillSincePress()) { mouseInitX = mouseEvent.getScreenX();
this.newX = mouseEvent.getScreenX(); mouseInitY = mouseEvent.getScreenY();
this.newY = mouseEvent.getScreenY(); stageInitX = primaryStage.getX();
double deltaX = this.newX - this.initX; stageInitY = primaryStage.getY();
double deltaY = this.newY - this.initY; stageInitWidth = primaryStage.getWidth();
Cursor cursor = root.getCursor(); stageInitHeight = primaryStage.getHeight();
if (Cursor.E_RESIZE == cursor) { }
this.setStageWidth(this.primaryStage.getWidth() + deltaX);
mouseEvent.consume();
} else if (Cursor.NE_RESIZE == cursor) {
if (this.setStageHeight(this.primaryStage.getHeight() - deltaY)) {
this.primaryStage.setY(this.primaryStage.getY() + deltaY);
}
this.setStageWidth(this.primaryStage.getWidth() + deltaX); if (primaryStage.isFullScreen() || !mouseEvent.isPrimaryButtonDown() || mouseEvent.isStillSincePress())
mouseEvent.consume(); return;
} else if (Cursor.SE_RESIZE == cursor) {
this.setStageWidth(this.primaryStage.getWidth() + deltaX);
this.setStageHeight(this.primaryStage.getHeight() + deltaY);
mouseEvent.consume();
} else if (Cursor.S_RESIZE == cursor) {
this.setStageHeight(this.primaryStage.getHeight() + deltaY);
mouseEvent.consume();
} else if (Cursor.W_RESIZE == cursor) {
if (this.setStageWidth(this.primaryStage.getWidth() - deltaX)) {
this.primaryStage.setX(this.primaryStage.getX() + deltaX);
}
mouseEvent.consume(); double dx = mouseEvent.getScreenX() - mouseInitX;
} else if (Cursor.SW_RESIZE == cursor) { double dy = mouseEvent.getScreenY() - mouseInitY;
if (this.setStageWidth(this.primaryStage.getWidth() - deltaX)) {
this.primaryStage.setX(this.primaryStage.getX() + deltaX);
}
this.setStageHeight(this.primaryStage.getHeight() + deltaY); Cursor cursor = root.getCursor();
mouseEvent.consume(); if (getSkinnable().isAllowMove()) {
} else if (Cursor.NW_RESIZE == cursor) { if (cursor == Cursor.DEFAULT) {
if (this.setStageWidth(this.primaryStage.getWidth() - deltaX)) { primaryStage.setX(stageInitX + dx);
this.primaryStage.setX(this.primaryStage.getX() + deltaX); primaryStage.setY(stageInitY + dy);
} mouseEvent.consume();
}
}
if (this.setStageHeight(this.primaryStage.getHeight() - deltaY)) { if (getSkinnable().isResizable()) {
this.primaryStage.setY(this.primaryStage.getY() + deltaY); if (cursor == Cursor.E_RESIZE) {
} resizeStage(stageInitWidth + dx, -1);
mouseEvent.consume();
mouseEvent.consume(); } else if (cursor == Cursor.S_RESIZE) {
} else if (Cursor.N_RESIZE == cursor) { resizeStage(-1, stageInitHeight + dy);
if (this.setStageHeight(this.primaryStage.getHeight() - deltaY)) { mouseEvent.consume();
this.primaryStage.setY(this.primaryStage.getY() + deltaY);
}
mouseEvent.consume(); } else if (cursor == Cursor.W_RESIZE) {
} else if (getSkinnable().isAllowMove()) { resizeStage(stageInitWidth - dx, -1);
this.primaryStage.setX(mouseEvent.getScreenX() - this.xOffset); primaryStage.setX(stageInitX + stageInitWidth - primaryStage.getWidth());
this.primaryStage.setY(mouseEvent.getScreenY() - this.yOffset); mouseEvent.consume();
mouseEvent.consume();
} } else if (cursor == Cursor.N_RESIZE) {
resizeStage(-1, stageInitHeight - dy);
primaryStage.setY(stageInitY + stageInitHeight - primaryStage.getHeight());
mouseEvent.consume();
} else if (cursor == Cursor.SE_RESIZE) {
resizeStage(stageInitWidth + dx, stageInitHeight + dy);
mouseEvent.consume();
} else if (cursor == Cursor.SW_RESIZE) {
resizeStage(stageInitWidth - dx, stageInitHeight + dy);
primaryStage.setX(stageInitX + stageInitWidth - primaryStage.getWidth());
mouseEvent.consume();
} else if (cursor == Cursor.NW_RESIZE) {
resizeStage(stageInitWidth - dx, stageInitHeight - dy);
primaryStage.setX(stageInitX + stageInitWidth - primaryStage.getWidth());
primaryStage.setY(stageInitY + stageInitHeight - primaryStage.getHeight());
mouseEvent.consume();
} else if (cursor == Cursor.NE_RESIZE) {
resizeStage(stageInitWidth + dx, stageInitHeight - dy);
primaryStage.setY(stageInitY + stageInitHeight - primaryStage.getHeight());
mouseEvent.consume();
} }
} }
} }