/** * $Revision: $ * $Date: $ * * Copyright (C) 2006 Jive Software. All rights reserved. * * This software is published under the terms of the GNU Lesser Public License (LGPL), * a copy of which is included in this distribution. */ package org.jivesoftware.spark.plugins; import org.jivesoftware.MainWindowListener; import org.jivesoftware.Spark; import org.jivesoftware.resource.Default; import org.jivesoftware.resource.Res; import org.jivesoftware.resource.SparkRes; import org.jivesoftware.smack.packet.Presence; import org.jivesoftware.spark.SparkManager; import org.jivesoftware.spark.Workspace; import org.jivesoftware.spark.component.ImageTitlePanel; import org.jivesoftware.spark.component.WrappedLabel; import org.jivesoftware.spark.ui.PresenceListener; import org.jivesoftware.spark.ui.status.StatusBar; import org.jivesoftware.spark.ui.status.StatusItem; import org.jdesktop.jdic.tray.SystemTray; import org.jdesktop.jdic.tray.TrayIcon; import java.awt.BorderLayout; import java.awt.Color; import java.awt.Dimension; import java.awt.Font; import java.awt.Frame; import java.awt.GridBagConstraints; import java.awt.GridBagLayout; import java.awt.Insets; import java.awt.MenuItem; import java.awt.Point; import java.awt.Toolkit; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import javax.swing.*; /** * Handles tray icon operations inside of Spark. Use to display incoming chat requests, incoming messages * and general notifications. */ public final class SparkSystemTray implements ActionListener, MainWindowListener { private SystemTray systemTray; private TrayIcon trayIcon; private JPopupMenu notificationDialog; private WrappedLabel messageLabel = new WrappedLabel(); private final JMenuItem openMenu = new JMenuItem(Res.getString("menuitem.open")); private final JMenuItem hideMenu = new JMenuItem(Res.getString("menuitem.hide")); private final JMenuItem exitMenu = new JMenuItem(Res.getString("menuitem.exit")); private final JMenuItem logoutMenu = new JMenuItem(Res.getString("menuitem.logout.no.status")); // Define DND MenuItems private final JMenu statusMenu = new JMenu(Res.getString("menuitem.status")); private ImageTitlePanel headerLabel = new ImageTitlePanel(); private JFrame hideWindow = null; private ImageIcon availableIcon; private ImageIcon awayIcon; private ImageIcon dndIcon; /** * Creates a new instance of notifications. */ public SparkSystemTray() { if(Spark.isMac()){ return; } setupNotificationDialog(); // Handle tray image. availableIcon = Default.getImageIcon(Default.TRAY_IMAGE); if (availableIcon == null) { availableIcon = SparkRes.getImageIcon(SparkRes.TRAY_IMAGE); } awayIcon = SparkRes.getImageIcon(SparkRes.MESSAGE_AWAY); dndIcon = SparkRes.getImageIcon(SparkRes.MESSAGE_DND); trayIcon = new TrayIcon(new ImageIcon(availableIcon.getImage())); trayIcon.setIconAutoSize(true); systemTray = SystemTray.getDefaultSystemTray(); setTrayIcon(availableIcon); trayIcon.setToolTip(Default.getString(Default.APPLICATION_NAME)); // NORES JPopupMenu popupMenu = new JPopupMenu(Res.getString("title.tray.information")); // Add DND Menus addStatusMenuItems(); // Add Open Menu openMenu.setFont(new Font("Dialog", Font.BOLD, 11)); popupMenu.add(openMenu); // Add Hide Menu popupMenu.add(hideMenu); popupMenu.addSeparator(); // Add Spark Home Menu popupMenu.add(statusMenu); // Add Listeners openMenu.addActionListener(this); hideMenu.addActionListener(this); Action logoutAction = new AbstractAction() { public void actionPerformed(ActionEvent actionEvent) { SparkManager.getMainWindow().logout(false); } }; logoutAction.putValue(Action.NAME, Res.getString("menuitem.logout.no.status")); logoutMenu.addActionListener(logoutAction); if (Spark.isWindows()) { popupMenu.add(logoutMenu); } // Add Exit Menu popupMenu.add(exitMenu); exitMenu.addActionListener(this); SparkManager.getMainWindow().addMainWindowListener(this); trayIcon.setPopupMenu(popupMenu); systemTray.addTrayIcon(trayIcon); trayIcon.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { showMainWindow(); } }); SparkManager.getSessionManager().addPresenceListener(new PresenceListener() { public void presenceChanged(Presence presence) { changePresence(presence); } }); } /** * Change the presence of the tray. * * @param presence the new presence. */ public void changePresence(Presence presence) { if (Spark.isMac()) { return; } if (presence.getMode() == Presence.Mode.available || presence.getMode() == Presence.Mode.chat) { setTrayIcon(availableIcon); } else if (presence.getMode() == Presence.Mode.away || presence.getMode() == Presence.Mode.xa) { setTrayIcon(awayIcon); } else { setTrayIcon(dndIcon); } // Get Status Text if (presence.isAvailable()) { String status = presence.getStatus(); trayIcon.setToolTip(Default.getString(Default.APPLICATION_NAME) + "\n" + status); } } /** * Stops the icon from flashing. */ public void stopFlashing() { Workspace workspace = SparkManager.getWorkspace(); StatusBar statusBox = workspace.getStatusBar(); Presence presence = statusBox.getPresence(); changePresence(presence); } public void actionPerformed(ActionEvent e) { Object o = e.getSource(); if (!(o instanceof MenuItem)) { /* MainWindow window = SparkManager.getMainWindow(); if (window.isVisible() && window.getState() == Frame.NORMAL) { long now = System.currentTimeMillis(); if (now - madeVisibleTime > 1000) { window.setVisible(false); return; } } madeVisibleTime = System.currentTimeMillis(); */ showMainWindow(); return; } final JMenuItem item = (JMenuItem)e.getSource(); if (item == openMenu) { showMainWindow(); } else if (item == hideMenu) { SparkManager.getMainWindow().setVisible(false); hideMenu.setEnabled(false); } else if (item == exitMenu) { SparkManager.getMainWindow().shutdown(); } else { final String status = item.getText(); // Change Status Workspace workspace = SparkManager.getWorkspace(); StatusItem statusItem = workspace.getStatusBar().getStatusItem(status); if (statusItem != null) { SparkManager.getSessionManager().changePresence(statusItem.getPresence()); } } } /** * Brings the <code>MainWindow</code> to the front. */ private void showMainWindow() { if (hideWindow != null) { hideWindow.dispose(); } SparkManager.getMainWindow().setState(Frame.NORMAL); SparkManager.getMainWindow().setVisible(true); notificationDialog.setVisible(false); hideMenu.setEnabled(true); SparkManager.getMainWindow().toFront(); } /** * Add all Registered DND's to MenuItems. */ private void addStatusMenuItems() { Workspace workspace = SparkManager.getWorkspace(); StatusBar statusBar = workspace.getStatusBar(); for (Object o : statusBar.getStatusList()) { StatusItem item = (StatusItem) o; final JMenuItem menuItem = new JMenuItem(item.getText()); menuItem.addActionListener(this); statusMenu.add(menuItem); } } public void shutdown() { systemTray.removeTrayIcon(trayIcon); } public void mainWindowActivated() { } public void mainWindowDeactivated() { } /** * Setup notification dialog. */ private void setupNotificationDialog() { notificationDialog = new JPopupMenu(); notificationDialog.setFocusable(false); notificationDialog.setLayout(new BorderLayout()); final Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize(); Point newLoc = new Point((int)screenSize.getWidth() - 200, (int)screenSize.getHeight() - 150); JPanel mainPanel = new JPanel(); mainPanel.setBackground(Color.white); mainPanel.setLayout(new GridBagLayout()); mainPanel.setBorder(BorderFactory.createLineBorder(Color.black, 1)); // Add Header Label mainPanel.add(headerLabel, new GridBagConstraints(0, 0, 1, 1, 1.0, 0.0, GridBagConstraints.CENTER, GridBagConstraints.HORIZONTAL, new Insets(0, 0, 0, 0), 0, 0)); // Add Message Label final JScrollPane messageScroller = new JScrollPane(messageLabel); mainPanel.add(messageScroller, new GridBagConstraints(0, 2, 1, 1, 1.0, 1.0, GridBagConstraints.CENTER, GridBagConstraints.BOTH, new Insets(5, 5, 5, 5), 0, 0)); messageScroller.setBackground(Color.white); messageScroller.setForeground(Color.white); messageLabel.setBackground(Color.white); messageScroller.getViewport().setBackground(Color.white); // JButton okButton = new JButton("Ok"); mainPanel.setPreferredSize(new Dimension(200, 150)); headerLabel.setTitle("Spark"); // NORES headerLabel.setTitleFont(new Font("Dialog", Font.BOLD, 10)); messageLabel.setFont(new Font("Dialog", Font.PLAIN, 11)); notificationDialog.add(mainPanel, BorderLayout.CENTER); notificationDialog.pack(); notificationDialog.setPreferredSize(new Dimension(200, 150)); notificationDialog.setLocation(newLoc); messageLabel.addMouseListener(new MouseAdapter() { public void mouseClicked(MouseEvent e) { notificationDialog.setVisible(false); showMainWindow(); } }); mainPanel.addMouseListener(new MouseAdapter() { public void mouseClicked(MouseEvent e) { notificationDialog.setVisible(false); showMainWindow(); } }); } private void setTrayIcon(ImageIcon icon) { trayIcon.setIcon(new ImageIcon(icon.getImage())); } }