2015-04-27 4 views
2

Я бы хотел показать предупреждение при нажатии на TrayIcon и показать главное окно при двойном щелчке по нему. У меня возникают проблемы с захватом события двойного щелчка: каждый раз, когда я дважды кликаю, запускаются два события с одним щелчком мыши.Java TrayIcon: addMouseListener -> различать один клик и двойной щелчок?

Я использую следующий код:

 trayIcon.addMouseListener(new MouseAdapter() { 
     public void mouseClicked(MouseEvent e) { 
      if (e.getClickCount() == 1 && e.getButton() == 1) {     
       trayIcon.displayMessage(...);    
      } else if (e.getClickCount() == 2 && e.getButton() == 1) { 
       frame.setVisible(true); 
      } 
     } 
    }); 

Как я могу предотвратить одно событие щелчка ворует двойной щелчок?

+0

Проверка двойной щелчок первой ... думать об этом, как это, двойной щелчок - это два щелчка кнопки мыши в короткой последовательности, то есть это приведет к срабатыванию вашего MouseListener дважды ... – MadProgrammer

+0

@MadProgrammer: Это первое, что я пробовал - это не имело значения! – Tim

+0

Хорошо, другая идея - использовать что-то вроде Swing Timer с небольшой задержкой, которая длиннее задержки двойного щелчка. При первом нажатии вы запускаете таймер, при двойном щелчке вы останавливаете таймер. Если таймер может завершиться, тогда у вас есть один клик .... но должен быть более чистый способ ... – MadProgrammer

ответ

0
if (e.getClickCount() == 2 && !e.isConsumed()) { 
    e.consume(); 
    ... 
} 
+0

Не забудьте [объяснить свое решение] (http://stackoverflow.com/help/how-to-answer) немного? Пожалуйста, примите [вступительный тур] (http://www.stackoverflow.com/tour). Возможно, вы захотите прочитать [Как написать хороший ответ] (http://stackoverflow.com/help/how-to-answer). –

+0

Это не работает - такая же проблема :(Код «if (e.getClickCount() == 2» никогда не запускается, потому что другой его крадет – Tim

1

Это несовершенное решение проблемы несовершенства. По своей природе двойной клик будет генерировать два события мыши, но двойной щелчок - это два клика, которые происходят в течение короткого промежутка времени между собой.

Таким образом, вы можете вставить небольшую задержку при первом щелчке, который, если будет запущен, будет «предполагать», что событие - всего лишь один клик.

В этом примере используется Swing Timer, установленный в 300 миллисекунд (вы можете попробовать 250-275, но я нашел 300, чтобы быть как раз справа). Когда он обнаруживает первый щелчок, он запускает таймер, если он обнаруживает второй щелчок, он останавливает таймер, в противном случае таймер может быть выполнен после задержки в 300 миллисекунд, что предполагает двойной щелчок ...

import java.awt.Dimension; 
import java.awt.EventQueue; 
import java.awt.GridBagLayout; 
import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 
import java.awt.event.MouseAdapter; 
import java.awt.event.MouseEvent; 
import javax.swing.JFrame; 
import javax.swing.JLabel; 
import javax.swing.JPanel; 
import javax.swing.Timer; 
import javax.swing.UIManager; 
import javax.swing.UnsupportedLookAndFeelException; 

public class JavaApplication314 { 

    public static void main(String[] args) { 
     new JavaApplication314(); 
    } 

    public JavaApplication314() { 
     EventQueue.invokeLater(new Runnable() { 
      @Override 
      public void run() { 
       try { 
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 
       } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { 
        ex.printStackTrace(); 
       } 

       JFrame frame = new JFrame("Testing"); 
       frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
       frame.add(new TestPane()); 
       frame.pack(); 
       frame.setLocationRelativeTo(null); 
       frame.setVisible(true); 
      } 
     }); 
    } 

    public class TestPane extends JPanel { 

     private JLabel label; 

     public TestPane() { 
      addMouseListener(new MouseHandler()); 
      label = new JLabel("..."); 
      setLayout(new GridBagLayout()); 
      add(label); 
     } 

     @Override 
     public Dimension getPreferredSize() { 
      return new Dimension(200, 200); 
     } 

     protected void doOneClick() { 
      label.setText("One Click"); 
     } 

     protected void doTwoClicks() { 
      label.setText("Two Clicks"); 
     } 

     public class MouseHandler extends MouseAdapter { 

      private Timer oneClickTimer; 

      public MouseHandler() { 
       oneClickTimer = new Timer(300, new ActionListener() { 
        @Override 
        public void actionPerformed(ActionEvent e) { 
         doOneClick(); 
        } 
       }); 
       oneClickTimer.setRepeats(false); 
      } 

      @Override 
      public void mouseClicked(MouseEvent e) { 
       if (e.getClickCount() == 2) { 
        oneClickTimer.stop(); 
        doTwoClicks(); 
       } else if (e.getClickCount() == 1) { 
        oneClickTimer.restart(); 
       } 
      } 



     } 

    } 

} 

Другим вариантом может быть будет использовать мета-ключ (как Alt), чтобы изменить состояние меню на один клик