swing在运行时更改java应用程序的外观(IDE:Netbeans) 3 月,2 周 Questions & Answers 11548 我正在构建一个java应用程序,我想用这些单选按钮在运行时更改应用程序的主题(外观)。我不知道该怎么做 提前谢谢
# 1 楼答案 那么,考虑到目前选择了Nimbus,我假设您想将LAF更改为Nimbus?如果是这样,您需要执行以下操作: UIManager.setLookAndFeel("javax.swing.plaf.nimbus.NimbusLookAndFeel"); 如果要查看当前安装的所有LAF,可以使用UIManager.getInstalledLookAndFeels();。有关更多信息,请考虑阅读this
# 2 楼答案 这是我的: 当用户单击JMenuItem或您选择的其他对象时发生操作事件时,应该调用此方法 private void changeLookAndFeel() { final LookAndFeelInfo[] list = UIManager.getInstalledLookAndFeels(); final List<String> lookAndFeelsDisplay = new ArrayList<>(); final List<String> lookAndFeelsRealNames = new ArrayList<>(); for (LookAndFeelInfo each : list) { lookAndFeelsDisplay.add(each.getName()); lookAndFeelsRealNames.add(each.getClassName()); } if (lookAndFeelsDisplay.size() != lookAndFeelsRealNames.size()) { throw new InternalError(); } String changeSpeed = (String) JOptionPane.showInputDialog(this, "Choose Look and Feel Here\n(these are all available on your system):", "Choose Look And Feel", JOptionPane.QUESTION_MESSAGE, null, lookAndFeelsDisplay.toArray(), null); boolean update = false; if (changeSpeed != null && changeSpeed.length() > 0) { for (int a = 0; a < lookAndFeelsDisplay.size(); a++) { if (changeSpeed.equals(lookAndFeelsDisplay.get(a))) { try { UIManager.setLookAndFeel(lookAndFeelsRealNames.get(a)); //re update with correct class name String this.whichLookAndFeel = changeSpeed; update = true; } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { err.println(ex); ex.printStackTrace(); Logger.getLogger(Starfighter.class.getName()).log(Level.SEVERE, null, ex); } } } } if (update) { int width = 800; int height = 625; if (UIManager.getLookAndFeel().getName().equals("CDE/Motif")) { height += 12; } this.setSize(width, height); this.menuBar.updateUI(); this.menuBar = new JMenuBar(); menuBar.updateUI(); this.setJMenuBar(menuBar); } }
# 3 楼答案 您可以通过调用SwingUtilities.updateTreeComponentUI(frame)并传递容器组件来实现这一点。请注意,它并非总是有效的。比如说: public static void changeLaf(JFrame frame) { try { UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException e) { e.printStackTrace(); } SwingUtilities.updateComponentTreeUI(frame); } 此方法将当前LaF更改为系统 编辑: 通过JRadioMenuItem演示更改LaF: import java.awt.BorderLayout; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.swing.ButtonGroup; import javax.swing.JButton; import javax.swing.JComboBox; import javax.swing.JFrame; import javax.swing.JMenu; import javax.swing.JMenuBar; import javax.swing.JPanel; import javax.swing.JRadioButtonMenuItem; import javax.swing.JScrollPane; import javax.swing.JSpinner; import javax.swing.JTable; import javax.swing.SwingUtilities; import javax.swing.UIManager; import javax.swing.UnsupportedLookAndFeelException; import javax.swing.table.DefaultTableModel; public class LafDemo { public static void changeLaf(JFrame frame, String laf) { if (laf.equals("metal")) { try { UIManager.setLookAndFeel(UIManager .getCrossPlatformLookAndFeelClassName()); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException e) { e.printStackTrace(); } } if (laf.equals("nimbus")) { try { UIManager .setLookAndFeel("javax.swing.plaf.nimbus.NimbusLookAndFeel"); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException e) { e.printStackTrace(); } } if (laf.equals("system")) { try { UIManager.setLookAndFeel(UIManager .getSystemLookAndFeelClassName()); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException e) { e.printStackTrace(); } } SwingUtilities.updateComponentTreeUI(frame); } public static void main(String[] args) { SwingUtilities.invokeLater(new Runnable() { @Override public void run() { final JFrame frame = new JFrame(); JPanel panel = new JPanel(); JButton btnDemo = new JButton("JButton"); JSpinner spnDemo = new JSpinner(); JComboBox<String> cmbDemo = new JComboBox<String>(); cmbDemo.addItem("One"); cmbDemo.addItem("Two"); cmbDemo.addItem("Three"); JMenuBar mBar = new JMenuBar(); frame.setJMenuBar(mBar); JMenu mnuLaf = new JMenu("Look and feel"); JRadioButtonMenuItem mniNimbus = new JRadioButtonMenuItem( "Nimbus"); JRadioButtonMenuItem mniMetal = new JRadioButtonMenuItem( "Metal"); JRadioButtonMenuItem mniSystem = new JRadioButtonMenuItem( "Systems"); ButtonGroup btnGroup = new ButtonGroup(); btnGroup.add(mniNimbus); btnGroup.add(mniMetal); btnGroup.add(mniSystem); mBar.add(mnuLaf); mnuLaf.add(mniNimbus); mnuLaf.add(mniMetal); mnuLaf.add(mniSystem); mniNimbus.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { changeLaf(frame, "nimbus"); } }); mniMetal.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { changeLaf(frame, "metal"); } }); mniSystem.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { changeLaf(frame, "system"); } }); DefaultTableModel model = new DefaultTableModel( new Object[][] {}, new String[] { "First", "Second" }); model.addRow(new Object[] { "Some text", "Another text" }); JTable table = new JTable(model); panel.add(btnDemo); panel.add(spnDemo); panel.add(cmbDemo); frame.add(panel, BorderLayout.NORTH); frame.add(new JScrollPane(table), BorderLayout.CENTER); frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); frame.pack(); frame.setVisible(true); } }); } }
# 4 楼答案 您只需使用UIManager.LookAndFeelInfo[]来存储可用的LookAndFeel,然后使用UIManager.setLookAndFeel(LookAndFeelClassName)来设置并在此之后执行SwingUtilities.updateComponentTreeUI(frameReference) 编辑: 务必在末尾对JFrame/JWindow/JDialog(父容器)调用pack,正如Swing Lord@andrewhompson所指定的那样 请看一看这个小例子: import java.awt.*; import java.awt.event.*; import javax.swing.*; public class LookAndFeelDemo { private JFrame frame; private JButton button; private int counter; private Timer timer; private JLabel lafNameLabel; private UIManager.LookAndFeelInfo[] lafs; public LookAndFeelDemo() { lafs = UIManager.getInstalledLookAndFeels(); counter = 0; } private ActionListener eventActions = new ActionListener() { @Override public void actionPerformed(ActionEvent ae) { if (ae.getSource() == timer) { counter %= lafs.length; try { UIManager.setLookAndFeel(lafs[counter].getClassName()); } catch(Exception e) {e.printStackTrace();} SwingUtilities.updateComponentTreeUI(frame); lafNameLabel.setText(lafs[counter++].getName()); frame.pack(); } else if (ae.getSource() == button) { if (timer.isRunning()) { timer.stop(); button.setText("Start"); } else { timer.start(); button.setText("Stop"); } } } }; private void displayGUI() { frame = new JFrame("Swing Worker Example"); frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); JPanel contentPane = new JPanel(); lafNameLabel = new JLabel("Nothing to display yet...", JLabel.CENTER); button = new JButton("Stop"); button.addActionListener(eventActions); contentPane.add(lafNameLabel); contentPane.add(button); frame.addWindowListener(new WindowAdapter() { @Override public void windowClosed(WindowEvent e) { timer.stop(); } }); frame.setContentPane(contentPane); frame.pack(); frame.setLocationByPlatform(true); frame.setVisible(true); timer = new Timer(1000, eventActions); timer.start(); } public static void main(String[] args) { Runnable runnable = new Runnable() { @Override public void run() { new LookAndFeelDemo().displayGUI(); } }; EventQueue.invokeLater(runnable); } } 编辑2: 更新代码示例以包括动态地从JRadioButtonMenuItem添加LookAndFeels。尽管请注意,如果使用Action而不是ActionListener会更好,但我使用它只是为了合并前面代码中的更改:-) import java.awt.*; import java.awt.event.*; import javax.swing.*; public class LookAndFeelDemo { private JFrame frame; private JButton button; private int counter; private Timer timer; private JLabel lafNameLabel; private ButtonGroup bg; private JRadioButtonMenuItem[] radioItems; private UIManager.LookAndFeelInfo[] lafs; public LookAndFeelDemo() { lafs = UIManager.getInstalledLookAndFeels(); counter = 0; } private ActionListener eventActions = new ActionListener() { @Override public void actionPerformed(ActionEvent ae) { if (ae.getSource() == timer) { counter %= lafs.length; try { UIManager.setLookAndFeel(lafs[counter].getClassName()); } catch(Exception e) {e.printStackTrace();} SwingUtilities.updateComponentTreeUI(frame); lafNameLabel.setText(lafs[counter++].getName()); frame.pack(); } else if (ae.getSource() == button) { if (timer.isRunning()) { timer.stop(); button.setText("Start"); } else { timer.start(); button.setText("Stop"); } } else if (ae.getSource() instanceof JRadioButtonMenuItem) { JRadioButtonMenuItem radioItem = (JRadioButtonMenuItem) ae.getSource(); String lafName = radioItem.getActionCommand(); System.out.println("LAF Name : " + lafName); for (int i = 0; i < radioItems.length; i++) { if (lafName.equals(radioItems[i].getActionCommand())) { setApplicationLookAndFeel(lafs[i].getClassName()); } } } } private void setApplicationLookAndFeel(String className) { try { UIManager.setLookAndFeel(className); } catch (Exception e) {e.printStackTrace();} SwingUtilities.updateComponentTreeUI(frame); frame.pack(); } }; private void displayGUI() { frame = new JFrame("Swing Worker Example"); frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); JPanel contentPane = new JPanel(); lafNameLabel = new JLabel("Nothing to display yet...", JLabel.CENTER); button = new JButton("Start"); button.addActionListener(eventActions); contentPane.add(lafNameLabel); contentPane.add(button); frame.addWindowListener(new WindowAdapter() { @Override public void windowClosed(WindowEvent e) { timer.stop(); } }); frame.setJMenuBar(getMenuBar()); frame.setContentPane(contentPane); frame.pack(); frame.setLocationByPlatform(true); frame.setVisible(true); timer = new Timer(1000, eventActions); } private JMenuBar getMenuBar() { JMenuBar menuBar = new JMenuBar(); JMenu lookAndFeelMenu = new JMenu("Look And Feels"); bg = new ButtonGroup(); radioItems = new JRadioButtonMenuItem[lafs.length]; for (int i = 0; i < radioItems.length; i++) { radioItems[i] = new JRadioButtonMenuItem(lafs[i].getName()); radioItems[i].addActionListener(eventActions); bg.add(radioItems[i]); lookAndFeelMenu.add(radioItems[i]); } menuBar.add(lookAndFeelMenu); return menuBar; } public static void main(String[] args) { Runnable runnable = new Runnable() { @Override public void run() { new LookAndFeelDemo().displayGUI(); } }; EventQueue.invokeLater(runnable); } }
# 1 楼答案
那么,考虑到目前选择了Nimbus,我假设您想将LAF更改为Nimbus?如果是这样,您需要执行以下操作:
UIManager.setLookAndFeel("javax.swing.plaf.nimbus.NimbusLookAndFeel");
如果要查看当前安装的所有LAF,可以使用
UIManager.getInstalledLookAndFeels();
。有关更多信息,请考虑阅读this# 2 楼答案
这是我的:
当用户单击JMenuItem或您选择的其他对象时发生操作事件时,应该调用此方法
# 3 楼答案
您可以通过调用
SwingUtilities.updateTreeComponentUI(frame)
并传递容器组件来实现这一点。请注意,它并非总是有效的。比如说:此方法将当前LaF更改为系统
编辑:
通过
JRadioMenuItem
演示更改LaF:# 4 楼答案
您只需使用
UIManager.LookAndFeelInfo[]
来存储可用的LookAndFeel
,然后使用UIManager.setLookAndFeel(LookAndFeelClassName)
来设置并在此之后执行SwingUtilities.updateComponentTreeUI(frameReference)
编辑:
务必在末尾对
JFrame/JWindow/JDialog
(父容器)调用pack
,正如Swing Lord
@andrewhompson所指定的那样请看一看这个小例子:
编辑2:
更新代码示例以包括动态地从
JRadioButtonMenuItem
添加LookAndFeels
。尽管请注意,如果使用Action而不是ActionListener
会更好,但我使用它只是为了合并前面代码中的更改:-)