桌面程序当中,托盘显示是一个常用的功能。
C#的WinForm程序要实现托盘是挺轻松的,而Java Swing要实现这个功能虽然也不难,
但是由于Java Swing开发者或许没有C#多,所以看到很多新手求助这个实例。
我写了一个很简单的Demo,希望能帮到所需要的人。
因为很简单,不赘述讲解,直接上代码。
(工程目录截图,以及Demo用到的png托盘图标都放在文末了)
(另有不清楚的可以联系QQ:119945778)
package ui; import java.awt.AWTException; import java.awt.EventQueue; import java.awt.MenuItem; import java.awt.PopupMenu; import java.awt.SystemTray; import java.awt.TrayIcon; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.swing.ImageIcon; import javax.swing.JFrame; public class TuoPanDemo extends JFrame { private static final long serialVersionUID = 1L; // 当前操作系统的托盘对象 private SystemTray sysTray; // 托盘图标 private TrayIcon trayIcon; // 图片 private ImageIcon icon = null; // 消息是否需要闪烁。默认false不需要闪烁。这个状态需要跨线程修改的。 // 所以为了健壮代码、线程安全,注意使用关键字volatile private volatile boolean msgNeedFlash = false; public static void main(String[] args) { EventQueue.invokeLater(new Runnable() { public void run() { try { TuoPanDemo frame = new TuoPanDemo(); frame.setVisible(true); } catch (Exception e) { e.printStackTrace(); } } }); } public TuoPanDemo() { setBounds(100, 100, 450, 300); setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);// 这句可以注释掉的,用托盘右键退出程序即可。 getContentPane().setLayout(null); setLocationRelativeTo(null); createTrayIcon(); // 这里可以开启检测是否有消息的线程,如果有,就闪烁图标 new Thread(runnableFlash).start(); } private void createTrayIcon() { // 实例化当前操作系统的托盘对象 sysTray = SystemTray.getSystemTray(); // 实例化一个图标 icon = new ImageIcon(TuoPanDemo.class.getResource("/img/rabbit_24px.png")); // Java托盘程序必须有一个右键菜单 PopupMenu popupMenu = new PopupMenu(); MenuItem menuOpen = new MenuItem("Open Msg"); MenuItem menuExit = new MenuItem("Exit"); popupMenu.add(menuOpen); popupMenu.add(menuExit); // 为右键弹出菜单项添加事件 menuOpen.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { EventQueue.invokeLater(new Runnable() { @Override public void run() { Msg msg = new Msg(); msg.setVisible(true); // 显示窗口 msg.toFront(); // 显示窗口到最前端 } }); msgNeedFlash = false; // 消息打开了,就不要闪烁了 } }); menuExit.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { System.exit(0); } }); // 实例化托盘图标 trayIcon = new TrayIcon(icon.getImage(), "消息盒子", popupMenu); // 图标大小自适应 trayIcon.setImageAutoSize(true); // 将托盘图标添入托盘 try { sysTray.add(trayIcon); } catch (AWTException e1) { e1.printStackTrace(); } } private Runnable runnableFlash = new Runnable() { @Override public void run() { while (true) { if (msgNeedFlash == true)// 如果新消息需要闪烁 { try { // 闪动消息的空白时间 trayIcon.setImage(new ImageIcon("").getImage()); Thread.sleep(500); // 闪动消息的提示图片 trayIcon.setImage(icon.getImage()); Thread.sleep(500); } catch (Exception e) { e.printStackTrace(); } } else //如果不需要闪烁,就重置托盘图标 { trayIcon.setImage(icon.getImage()); try { Thread.sleep(1000 * 10);//10秒闪烁一次。可以在这里读数据库是否有新的审批 msgNeedFlash = true; } catch (InterruptedException e) { e.printStackTrace(); } } } } }; }
package ui; import java.awt.EventQueue; import javax.swing.JFrame; import javax.swing.JLabel; public class Msg extends JFrame { private static final long serialVersionUID = 1L; public static void main(String[] args) { EventQueue.invokeLater(new Runnable() { public void run() { try { Msg frame = new Msg(); frame.setVisible(true); } catch (Exception e) { e.printStackTrace(); } } }); } public Msg() { setBounds(100, 100, 260, 120); setResizable(false); setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); getContentPane().setLayout(null); JLabel label = new JLabel("您有新的消息"); label.setBounds(77, 30, 100, 15); getContentPane().add(label); } }