UI: fixed windows layer problems when old window overlapped new window (see #4318, #4320 and other)

This commit is contained in:
Oleg Agafonov 2018-01-01 18:00:42 +04:00
parent 89f8b1420e
commit 78d036b6bb
9 changed files with 74 additions and 20 deletions

View file

@ -239,10 +239,10 @@ public class MageFrame extends javax.swing.JFrame implements MageClient {
SessionHandler.startSession(this);
callbackClient = new CallbackClientImpl(this);
connectDialog = new ConnectDialog();
desktopPane.add(connectDialog, JLayeredPane.POPUP_LAYER);
desktopPane.add(connectDialog, JLayeredPane.MODAL_LAYER);
errorDialog = new ErrorDialog();
errorDialog.setLocation(100, 100);
desktopPane.add(errorDialog, JLayeredPane.POPUP_LAYER);
desktopPane.add(errorDialog, JLayeredPane.MODAL_LAYER);
UI.addComponent(MageComponents.DESKTOP_PANE, desktopPane);
PING_TASK_EXECUTOR.scheduleAtFixedRate(() -> SessionHandler.ping(), 60, 60, TimeUnit.SECONDS);
@ -945,7 +945,7 @@ public class MageFrame extends javax.swing.JFrame implements MageClient {
}//GEN-LAST:event_btnConnectActionPerformed
public void btnAboutActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_btnAboutActionPerformed
JInternalFrame[] windows = desktopPane.getAllFramesInLayer(JLayeredPane.POPUP_LAYER);
JInternalFrame[] windows = desktopPane.getAllFramesInLayer(JLayeredPane.MODAL_LAYER);
for (JInternalFrame window : windows) {
if (window instanceof AboutDialog) {
// don't open the window twice.
@ -953,7 +953,7 @@ public class MageFrame extends javax.swing.JFrame implements MageClient {
}
}
AboutDialog aboutDialog = new AboutDialog();
desktopPane.add(aboutDialog, JLayeredPane.POPUP_LAYER);
desktopPane.add(aboutDialog, JLayeredPane.MODAL_LAYER);
aboutDialog.showDialog(VERSION);
}//GEN-LAST:event_btnAboutActionPerformed
@ -1096,7 +1096,7 @@ public class MageFrame extends javax.swing.JFrame implements MageClient {
public void showUserRequestDialog(final UserRequestMessage userRequestMessage) {
final UserRequestDialog userRequestDialog = new UserRequestDialog();
userRequestDialog.setLocation(100, 100);
desktopPane.add(userRequestDialog, JLayeredPane.POPUP_LAYER);
desktopPane.add(userRequestDialog, JLayeredPane.MODAL_LAYER);
if (SwingUtilities.isEventDispatchThread()) {
userRequestDialog.showDialog(userRequestMessage);
} else {

View file

@ -114,7 +114,14 @@ public class AddLandDialog extends MageDialog {
}
cbLandSet.setModel(new DefaultComboBoxModel(landSetNames.toArray()));
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
// windows settings
if (this.isModal()){
MageFrame.getDesktop().add(this, JLayeredPane.MODAL_LAYER);
}else{
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
}
this.setVisible(true);
}

View file

@ -102,10 +102,10 @@ public class ConnectDialog extends MageDialog {
this.txtPassword.addActionListener(connectAction);
registerUserDialog = new RegisterUserDialog(this);
MageFrame.getDesktop().add(registerUserDialog, JLayeredPane.POPUP_LAYER);
MageFrame.getDesktop().add(registerUserDialog, JLayeredPane.MODAL_LAYER);
resetPasswordDialog = new ResetPasswordDialog(this);
MageFrame.getDesktop().add(resetPasswordDialog, JLayeredPane.POPUP_LAYER);
MageFrame.getDesktop().add(resetPasswordDialog, JLayeredPane.MODAL_LAYER);
}
public void showDialog() {

View file

@ -45,8 +45,8 @@ import java.awt.event.MouseEvent;
import java.beans.PropertyVetoException;
import java.lang.reflect.InvocationTargetException;
import java.util.logging.Level;
import javax.swing.JComponent;
import javax.swing.SwingUtilities;
import javax.swing.*;
import mage.client.MageFrame;
import org.apache.log4j.Logger;
@ -74,11 +74,34 @@ public class MageDialog extends javax.swing.JInternalFrame {
@Override
public void show() {
super.show();
this.toFront();
// frames desktop ordering
// more info https://docs.oracle.com/javase/7/docs/api/javax/swing/JLayeredPane.html
// WARNING, use
// - JLayeredPane.DEFAULT_LAYER: tables and games (tabs)
// - JLayeredPane.PALETTE_LAYER: toolbars and info windows like cards list, not modal dialogs (not required user actions)
// - JLayeredPane.MODAL_LAYER: all modal dialogs (user required actions - select cards in game, new game window, error windows)
// - JLayeredPane.POPUP_LAYER: hints and other top level graphics
// - JLayeredPane.DRAG_LAYER: top most layer for critical actions and user controls
/*
JInternalFrame[] frames = MageFrame.getDesktop().getAllFrames();
System.out.println("---");
for(JInternalFrame frame: frames){
int zorder = -1;
if (frame.getParent() != null){
frame.getParent().getComponentZOrder(frame);
}
System.out.println(frame.getClass() + " (" + frame.getTitle() + ") : layer = " + frame.getLayer() + ", zorder = " + zorder);
}
*/
if (modal) {
this.setClosable(false);
}
if (this.modal) {
this.toFront();
if (modal){
startModal();
}
}
@ -108,7 +131,6 @@ public class MageDialog extends javax.swing.JInternalFrame {
}
private synchronized void startModal() {
try {
if (SwingUtilities.isEventDispatchThread()) {
EventQueue theQueue = getToolkit().getSystemEventQueue();

View file

@ -165,7 +165,11 @@ public class PickChoiceDialog extends MageDialog {
}
// window settings
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
if (this.isModal()){
MageFrame.getDesktop().add(this, JLayeredPane.MODAL_LAYER);
}else{
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
}
if (mageDialogState != null) {
mageDialogState.setStateToDialog(this);
@ -174,7 +178,7 @@ public class PickChoiceDialog extends MageDialog {
this.setLocation(centered.x, centered.y);
GuiDisplayUtil.keepComponentInsideScreen(centered.x, centered.y, this);
}
// final load
loadData();

View file

@ -35,7 +35,9 @@
package mage.client.dialog;
import java.awt.Point;
import javax.swing.SpinnerNumberModel;
import javax.swing.*;
import mage.client.MageFrame;
import mage.client.util.SettingsManager;
import mage.client.util.gui.GuiDisplayUtil;
@ -60,6 +62,13 @@ public class PickNumberDialog extends MageDialog {
this.btnCancel.setVisible(false);
this.pack();
// window settings
if (this.isModal()){
MageFrame.getDesktop().add(this, JLayeredPane.MODAL_LAYER);
}else{
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
}
Point centered = SettingsManager.instance.getComponentPosition(getWidth(), getHeight());
this.setLocation(centered.x, centered.y);
GuiDisplayUtil.keepComponentInsideScreen(centered.x, centered.y, this);

View file

@ -114,6 +114,14 @@ public class PickPileDialog extends MageDialog {
this.revalidate();
this.repaint();
this.setModal(true);
// window settings
if (this.isModal()){
MageFrame.getDesktop().add(this, JLayeredPane.MODAL_LAYER);
}else{
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
}
this.setVisible(true);
}

View file

@ -120,15 +120,19 @@ public class ShowCardsDialog extends MageDialog {
this.cardArea.addCardEventListener(eventListener);
}
if (getParent() != MageFrame.getDesktop() /*|| this.isClosed*/) {
MageFrame.getDesktop().add(this, JLayeredPane.DEFAULT_LAYER);
}
pack();
this.revalidate();
this.repaint();
this.setModal(modal);
// window settings
if (this.isModal()){
MageFrame.getDesktop().add(this, JLayeredPane.MODAL_LAYER);
}else{
MageFrame.getDesktop().add(this, JLayeredPane.PALETTE_LAYER);
}
SwingUtilities.invokeLater(() -> {
if (!positioned) {
int width = ShowCardsDialog.this.getWidth();

View file

@ -1115,7 +1115,7 @@ public final class GamePanel extends javax.swing.JPanel {
}
this.feedbackPanel.getFeedback(required ? FeedbackMode.INFORM : FeedbackMode.CANCEL, message, gameView.getSpecial(), options0, messageId);
if (dialog != null) {
this.pickTarget.add(dialog);
this.pickTarget.add(dialog); // TODO: 01.01.2018, JayDi85: why feedbackPanel saved to pickTarget list? Need to research
}
}