GUI, preferences: reworked size settings:

- added size settings for player's panel size (closes #12455, closes #12451, closes #5605);
- size settings can be edit by slider or by text edit;
- size settings for fonts has preview button with real text sample;
- improved some tabs and hints for better UX;
- improved GUI rendering performance;
This commit is contained in:
Oleg Agafonov 2024-07-21 23:35:44 +04:00
parent 921e656e3c
commit 1f3fad6594
15 changed files with 3224 additions and 5913 deletions

View file

@ -248,12 +248,14 @@ public final class GamePanel extends javax.swing.JPanel {
resizeTimer = new Timer(1000, evt -> SwingUtilities.invokeLater(() -> {
resizeTimer.stop();
setGUISize();
setGUISize(false);
feedbackPanel.changeGUISize();
}));
pnlHelperHandButtonsStackArea.addComponentListener(componentAdapterPlayField);
initComponents = false;
setGUISize(true);
}
private Map<String, JComponent> getUIComponents(JLayeredPane jLayeredPane) {
@ -377,7 +379,7 @@ public final class GamePanel extends javax.swing.JPanel {
public void changeGUISize() {
initComponents = true;
setGUISize();
setGUISize(true);
stackObjects.changeGUISize();
feedbackPanel.changeGUISize();
handContainer.changeGUISize();
@ -418,7 +420,7 @@ public final class GamePanel extends javax.swing.JPanel {
initComponents = false;
}
private void setGUISize() {
private void setGUISize(boolean themeReload) {
jSplitPane0.setDividerSize(GUISizeHelper.dividerBarSize);
jSplitPane1.setDividerSize(GUISizeHelper.dividerBarSize);
jSplitPane2.setDividerSize(GUISizeHelper.dividerBarSize);
@ -453,7 +455,9 @@ public final class GamePanel extends javax.swing.JPanel {
pnlShortCuts.setMinimumSize(newDimension);
pnlShortCuts.setMaximumSize(newDimension);
reloadThemeRelatedGraphic();
if (themeReload) {
reloadThemeRelatedGraphic();
}
}
private void reloadThemeRelatedGraphic() {
@ -485,6 +489,20 @@ public final class GamePanel extends javax.swing.JPanel {
phaseButtons.forEach((phaseName, phaseButton) -> {
phaseButton.update(phaseButton.getText(), ImageManagerImpl.instance.getPhaseImage(phaseName));
});
// player panels
if (lastGameData.game != null) {
lastGameData.game.getPlayers().forEach(player -> {
PlayAreaPanel playPanel = this.players.getOrDefault(player.getPlayerId(), null);
if (playPanel != null) {
// see test render dialog for refresh commands order
playPanel.getPlayerPanel().fullRefresh(GUISizeHelper.playerPanelGuiScale);
playPanel.init(player, bigCard, gameId, player.getPriorityTimeLeftSecs());
playPanel.update(lastGameData.game, player, lastGameData.targets);
playPanel.getPlayerPanel().sizePlayerPanel(isSmallMode());
}
});
}
}
private void saveDividerLocations() {
@ -521,7 +539,13 @@ public final class GamePanel extends javax.swing.JPanel {
}
}
private boolean isSmallMode() {
// TODO: no needs on gui scale?
return this.getBounds().height < 770;
}
private void sizeToScreen() {
// on resize frame
Rectangle rect = this.getBounds();
if (rect.height < 770) {
@ -534,7 +558,7 @@ public final class GamePanel extends javax.swing.JPanel {
pnlShortCuts.revalidate();
pnlShortCuts.repaint();
for (PlayAreaPanel p : players.values()) {
p.setSizeMode(smallMode);
p.getPlayerPanel().sizePlayerPanel(smallMode);
}
}
} else if (smallMode) {
@ -546,7 +570,7 @@ public final class GamePanel extends javax.swing.JPanel {
pnlShortCuts.revalidate();
pnlShortCuts.repaint();
for (PlayAreaPanel p : players.values()) {
p.setSizeMode(smallMode);
p.getPlayerPanel().sizePlayerPanel(smallMode);
}
}
@ -667,6 +691,7 @@ public final class GamePanel extends javax.swing.JPanel {
public synchronized void init(int messageId, GameView game, boolean callGameUpdateAfterInit) {
addPlayers(game);
// default menu states
setMenuStates(
PreferencesDialog.getCachedValue(KEY_GAME_MANA_AUTOPAYMENT, "true").equals("true"),
@ -772,8 +797,10 @@ public final class GamePanel extends javax.swing.JPanel {
break;
}
}
// set init sizes
for (PlayAreaPanel p : players.values()) {
p.setSizeMode(smallMode);
p.getPlayerPanel().sizePlayerPanel(isSmallMode());
}
GridBagConstraints panelC = new GridBagConstraints();
@ -785,21 +812,6 @@ public final class GamePanel extends javax.swing.JPanel {
this.pnlBattlefield.add(topPanel, panelC);
panelC.gridy = 1;
this.pnlBattlefield.add(bottomPanel, panelC);
// TODO: combat arrows aren't visible on re-connect, must click on avatar to update correctrly
// reason: panels aren't visible/located here, so battlefieldpanel see wrong sizes
// recalc all component sizes and update permanents/arrows positions
// if you don't do it here then will catch wrong arrows drawing on re-connect (no sortLayout calls)
/*
this.validate();
for (Map.Entry<UUID, PlayAreaPanel> p : players.entrySet()) {
PlayerView playerView = game.getPlayers().stream().filter(view -> view.getPlayerId().equals(p.getKey())).findFirst().orElse(null);
if (playerView != null) {
p.getValue().getBattlefieldPanel().updateSize();
p.getValue().update(null, playerView, null);
}
}
*/
}
public synchronized void updateGame(int messageId, GameView game) {
@ -2423,8 +2435,6 @@ public final class GamePanel extends javax.swing.JPanel {
initPopupMenuTriggerOrder();
setGUISize();
// Replay panel to control replay of games
javax.swing.GroupLayout gl_pnlReplay = new javax.swing.GroupLayout(pnlReplay);
pnlReplay.setLayout(gl_pnlReplay);

View file

@ -25,7 +25,7 @@ import static mage.client.dialog.PreferencesDialog.*;
/**
* GUI: play area panel (player with avatar/mana panel + battlefield panel)
*
* @author BetaSteward_at_googlemail.com
* @author BetaSteward_at_googlemail.com, JayDi85
*/
public class PlayAreaPanel extends javax.swing.JPanel {
@ -49,16 +49,6 @@ public class PlayAreaPanel extends javax.swing.JPanel {
public static final int PANEL_HEIGHT_SMALL = 220;
private static final int PANEL_HEIGHT_EXTRA_FOR_ME = 25;
/**
* Creates new form PlayAreaPanel
*
* @param player
* @param bigCard
* @param gameId
* @param priorityTime
* @param gamePanel
* @param options
*/
public PlayAreaPanel(PlayerView player, BigCard bigCard, UUID gameId, int priorityTime, GamePanel gamePanel,
PlayAreaPanelOptions options) {
this.gamePanel = gamePanel;
@ -70,6 +60,7 @@ public class PlayAreaPanel extends javax.swing.JPanel {
// data init
init(player, bigCard, gameId, priorityTime);
update(null, player, null);
playerPanel.sizePlayerPanel(isSmallMode());
// init popup menu (must run after data init)
popupMenu = new JPopupMenu();
@ -78,7 +69,6 @@ public class PlayAreaPanel extends javax.swing.JPanel {
} else {
addPopupMenuWatcher();
}
this.add(popupMenu);
setGUISize();
}
@ -545,52 +535,18 @@ public class PlayAreaPanel extends javax.swing.JPanel {
private void initComponents() {
setBorder(BorderFactory.createLineBorder(new Color(0, 0, 0, 0)));
playerPanel = new PlayerPanelExt();
btnCheat = new javax.swing.JButton();
playerPanel = new PlayerPanelExt(GUISizeHelper.playerPanelGuiScale);
btnCheat = new javax.swing.JButton(); // TODO: not used? Delete
battlefieldPanel = new mage.client.game.BattlefieldPanel();
battlefieldPanel.setTopPanelBattlefield(options.topRow);
battlefieldPanel.setPreferredSize(new Dimension(Short.MAX_VALUE, Short.MAX_VALUE));
btnCheat.setText("Cheat");
btnCheat.addActionListener(evt -> btnCheatActionPerformed(evt));
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
layout.setHorizontalGroup(
layout.createSequentialGroup()
.addComponent(playerPanel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
.addPreferredGap(ComponentPlacement.RELATED)
.addComponent(battlefieldPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
);
layout.setVerticalGroup(
layout.createParallelGroup(Alignment.LEADING)
.addComponent(playerPanel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
.addComponent(battlefieldPanel, GroupLayout.DEFAULT_SIZE, 160, Short.MAX_VALUE)
);
this.setLayout(layout);
}
public void setSizeMode(boolean smallMode) {
this.smallMode = smallMode;
sizePlayerPanel(this.playerPanel, this.isMe, this.smallMode);
sizeBattlefieldPanel(this.battlefieldPanel, this.isMe, this.smallMode);
}
public static void sizePlayerPanel(PlayerPanelExt playerPanel, boolean isMe, boolean smallMode) {
playerPanel.sizePlayerPanel(smallMode);
int extraForMe = isMe ? PANEL_HEIGHT_EXTRA_FOR_ME : 0;
if (smallMode) {
playerPanel.setPreferredSize(new Dimension(92, PANEL_HEIGHT_SMALL + extraForMe));
} else {
playerPanel.setPreferredSize(new Dimension(92, PANEL_HEIGHT + extraForMe));
}
}
public static void sizeBattlefieldPanel(BattlefieldPanel battlefieldPanel, boolean isMe, boolean smallMode) {
int extraForMe = isMe ? PANEL_HEIGHT_EXTRA_FOR_ME : 0;
if (smallMode) {
battlefieldPanel.setPreferredSize(new Dimension(160, PANEL_HEIGHT_SMALL + extraForMe));
} else {
battlefieldPanel.setPreferredSize(new Dimension(160, PANEL_HEIGHT + extraForMe));
}
this.setLayout(new BorderLayout());
this.add(playerPanel, BorderLayout.WEST);
this.add(battlefieldPanel, BorderLayout.CENTER);
}
private void btnCheatActionPerformed(java.awt.event.ActionEvent evt) {

View file

@ -64,35 +64,49 @@ public class PlayerPanelExt extends javax.swing.JPanel {
private static final int PANEL_HEIGHT_SMALL = 218; // small mode (with avatar button) // TODO: no need in small mode after GUI scale added
private static final int PANEL_HEIGHT_EXTRA_FOR_ME = 25; // hints button
private final Border GREEN_BORDER;
private final Border RED_BORDER;
private final Border YELLOW_BORDER;
private final Border EMPTY_BORDER;
private Border GREEN_BORDER;
private Border RED_BORDER;
private Border YELLOW_BORDER;
private Border EMPTY_BORDER;
float guiScaleMod = 1.0f;
private final Color activeValueColor = new Color(244, 9, 47);
private final Font fontValuesZero;
private final Font fontValuesNonZero;
private Color activeValueColor = new Color(244, 9, 47);
private Font fontValuesZero;
private Font fontValuesNonZero;
private int avatarId = -1;
private String flagName;
private String basicTooltipText;
private static final Map<UUID, Integer> playerLives = new HashMap<>();
private Font defaultFont = null;
private PriorityTimer timer;
/**
* Creates new form PlayerPanel
*/
public PlayerPanelExt() {
this(1.0f);
}
public PlayerPanelExt(float guiScaleMod) {
// gui scale
// save default font cause panel can be recreated manually
this.defaultFont = this.getFont();
createAllComponents(guiScaleMod);
}
/**
* Refresh full panel's components due actual GUI settings
*/
public void fullRefresh(float guiScaleMod) {
this.cleanUp();
this.removeAll();
this.createAllComponents(guiScaleMod);
}
public void createAllComponents(float guiScaleMod) {
this.guiScaleMod = guiScaleMod;
this.setFont(this.getFont().deriveFont(sizeMod(this.getFont().getSize2D())));
this.setFont(this.defaultFont.deriveFont(sizeMod(this.defaultFont.getSize2D())));
this.fontValuesZero = this.getFont().deriveFont(Font.PLAIN);
this.fontValuesNonZero = this.getFont().deriveFont(Font.BOLD);
this.GREEN_BORDER = new LineBorder(Color.green, sizeMod(3));
@ -123,7 +137,8 @@ public class PlayerPanelExt extends javax.swing.JPanel {
toolHintsHelper.setVisible(this.isMe);
toolHintsHelper.setFocusable(false);
flagName = null;
if (priorityTime > 0) {
avatarId = -1;
if (priorityTime > 0 && priorityTime != Integer.MAX_VALUE) {
long delay = 1000L;
timer = new PriorityTimer(priorityTime, delay, () -> {
@ -360,9 +375,9 @@ public class PlayerPanelExt extends javax.swing.JPanel {
}
}
if (this.timer != null) {
if (player.getPriorityTimeLeft() != Integer.MAX_VALUE) {
if (player.getPriorityTimeLeftSecs() != Integer.MAX_VALUE) {
String priorityTimeValue = getPriorityTimeLeftString(player);
this.timer.setCount(player.getPriorityTimeLeft());
this.timer.setCount(player.getPriorityTimeLeftSecs());
this.timer.setBufferCount(player.getBufferTimeLeft());
this.avatar.setTopText(priorityTimeValue);
this.timerLabel.setText(priorityTimeValue);
@ -372,7 +387,7 @@ public class PlayerPanelExt extends javax.swing.JPanel {
if (player.getBufferTimeLeft() > 0) {
textColor = Color.GREEN;
foregroundColor = Color.GREEN.darker().darker();
} else if (player.getPriorityTimeLeft() < 300) { // visual indication for under 5 minutes
} else if (player.getPriorityTimeLeftSecs() < 300) { // visual indication for under 5 minutes
textColor = Color.RED;
foregroundColor = Color.RED.darker().darker();
} else {
@ -476,7 +491,7 @@ public class PlayerPanelExt extends javax.swing.JPanel {
}
private String getPriorityTimeLeftString(PlayerView player) {
int priorityTimeLeft = player.getPriorityTimeLeft() + player.getBufferTimeLeft();
int priorityTimeLeft = player.getPriorityTimeLeftSecs() + player.getBufferTimeLeft();
return getPriorityTimeLeftString(priorityTimeLeft);
}
@ -975,7 +990,7 @@ public class PlayerPanelExt extends javax.swing.JPanel {
}// </editor-fold>//GEN-END:initComponents
protected void sizePlayerPanel(boolean smallMode) {
public void sizePlayerPanel(boolean smallMode) {
int extraForMe = this.isMe ? PANEL_HEIGHT_EXTRA_FOR_ME : 0;
if (smallMode) {
avatar.setVisible(false);