Zasadniczo istnieje JPanel, o którym chcę wiedzieć, kiedy mysz wchodzi w obszar JPanel i opuszcza obszar JPanel. Dodałem więc słuchacza myszy, ale jeśli w JPanelu znajdują się komponenty, a myszka przejdzie nad jednym z nich, zostanie to wykryte jako wyjście na JPanel, nawet jeśli komponent znajduje się na JPanelu. Zastanawiam się, czy ktoś nie wie, jak rozwiązać ten problem, nie robiąc czegoś takiego, jak dodawanie słuchaczy do wszystkich komponentów w JPanelu?Wykrywanie zdarzeń wejścia/wyjścia myszy w dowolnym miejscu na JPanel
Odpowiedz
Jeśli chcesz, aby wszystkie zdarzenia były wysyłane do okna najwyższego poziomu, możesz dodać detektor do tafli szkła JFrame. Zobacz: http://java.sun.com/j2se/1.4.2/docs/api/javax/swing/RootPaneContainer.html#getGlassPane%28%29
Pytanie dotyczyło JPanel, a nie JFrame. Możesz odpowiedzieć na to pytanie, ale tylko częściowo, więc odpowiedź nie jest odpowiednia dla początkującego. PS: nawet w 2010 roku, myślę, że jest lepszy link do dokumentów w Javie 1.6. – PhiLho
Oto jeden ze sposobów, aby to zrobić dla składnika, który może zawierać inne składniki:
Dodaj globalną detektor zdarzeń AWT, aby wszystkie zdarzenia myszy. Na przykład:
Toolkit.getDefaultToolkit().addAWTEventListener( new TargetedMouseHandler(panel), AWTEvent.MOUSE_EVENT_MASK);
Wdrożenie
TargetedMouseHandler
ignorować zdarzeń, które nie są pozyskiwane przez centralę lub przez jedno z dzieci na panelu (można użyćSwingUtilities.isDescendingFrom
przetestować na ten temat).Śledź, czy mysz znajduje się już poza granicami twojego panelu. Kiedy otrzymasz zdarzenie
MouseEvent.MOUSE_ENTERED
w swoim panelu lub jednym z jego elementów podrzędnych, ustaw flagę na true.Po uzyskaniu zdarzenia
MouseEvent.MOUSE_EXITED
, zresetuj tylko flagę, jeśli punkt wMouseEvent
znajduje się poza granicami panelu docelowego.SwingUtilities.convertPoint
iComponent.getBounds().contains()
będzie przydatna tutaj.
Próbowałem zaimplementować twój pomysł (mieć globalny handler kliknięciem prawym przyciskiem myszy (menu kontekstowe) na panelu z komponentami), ale odkryłem, że jest naprawdę globalny, tj. na poziomie całej aplikacji, co może być denerwujące z wewnętrznymi ramkami, tak jak mamy, i musimy usunąć program obsługi podczas zamykania odpowiedniej wewnętrznej ramki. Wciąż ciekawa i pouczająca odpowiedź, która może być dostosowana do prostszych przypadków. – PhiLho
Oto przykładowy kod implementujący rozwiązanie Asha. Dla mnie JFrame nie wykrył poprawnie wszystkich zdarzeń wyjściowych, ale zrobił to wewnętrzny JPanel, więc przekazałem dwa komponenty - jeden do testowania potomków i jeden do testowania granicy.
Toolkit.getDefaultToolkit().addAWTEventListener(
new TargetedMouseHandler(this, this.jPanel),
AWTEvent.MOUSE_EVENT_MASK);
}
public class TargetedMouseHandler implements AWTEventListener
{
private Component parent;
private Component innerBound;
private boolean hasExited = true;
public TargetedMouseHandler(Component p, Component p2)
{
parent = p;
innerBound = p2;
}
@Override
public void eventDispatched(AWTEvent e)
{
if (e instanceof MouseEvent)
{
if (SwingUtilities.isDescendingFrom(
(Component) e.getSource(), parent))
{
MouseEvent m = (MouseEvent) e;
if (m.getID() == MouseEvent.MOUSE_ENTERED)
{
if (hasExited)
{
System.out.println("Entered");
hasExited = false;
}
} else if (m.getID() == MouseEvent.MOUSE_EXITED)
{
Point p = SwingUtilities.convertPoint(
(Component) e.getSource(),
m.getPoint(),
innerBound);
if (!innerBound.getBounds().contains(p))
{
System.out.println("Exited");
hasExited = true;
}
}
}
}
}
}
Jest bardzo proste rozwiązanie tego problemu, które mogą działać:
public class MyJPanel implements MouseListener {
public void mouseExited(MouseEvent e) {
java.awt.Point p = new java.awt.Point(e.getLocationOnScreen());
SwingUtilities.convertPointFromScreen(p, e.getComponent());
if(e.getComponent().contains(p)) {return;}
...//the rest of your code
}
...
}
ten sposób można po prostu zignorować to wydarzenie mouseExited gdy występuje na elemencie dziecięcej.
- 1. Obsługa zdarzenia myszy w dowolnym miejscu z JavaFX
- 2. Zamknij okno dialogowe kliknięcia (w dowolnym miejscu)
- 3. Wyszukiwanie w dowolnym miejscu treści zamiast uruchamiania
- 4. Pierwsze lokalizatora usług w dowolnym miejscu ZF2
- 5. Swift wykrywa dotyk w dowolnym miejscu na ekranie.
- 6. Wykrywanie zdarzeń dotyku na UILabelu
- 7. jak wywołać zdarzenie, gdy ktoś kliknie w dowolnym miejscu na ekranie w aplikacji na Androida?
- 8. W jaki sposób pola kombi podczas wyświetlania elementów listy przechwytują zdarzenia myszy w dowolnym miejscu formularza, aby ukryć listę?
- 9. Umożliwia zaznaczanie kursora w dowolnym miejscu w UITextView
- 10. Wykrywanie zdarzeń połączeń w ios
- 11. Czy widzisz wartości NSUserDefaults w dowolnym miejscu w debugerze xcode?
- 12. Mapowanie zdarzeń dotykowych JavaScript na zdarzenia myszy
- 13. Niestandardowe składanie kodu - składanie kodu w dowolnym miejscu (Notepad ++)
- 14. Sprawdź, czy ciąg ma spację pomiędzy (lub w dowolnym miejscu).
- 15. Nginx Php-fpm nie rejestruje 500 błędów w dowolnym miejscu
- 16. Wykrywanie Zdarzenia myszy na wielu nakładających się elementów SVG
- 17. Czy Java definiuje rozmiar swoich typów pierwotnych w dowolnym miejscu?
- 18. Naciśnięcie myszy Java - bez zdarzeń
- 19. Wysyłanie zdarzeń myszy i klawiatury
- 20. wykrywanie kliknięć myszy w OpenGL C++
- 21. LinqPad właśnie rozbił się na mnie. Czy mój kod znajduje się w dowolnym miejscu na dysku?
- 22. Subskrybowanie zdarzeń myszy wszystkich formantów w formularzu
- 23. Autouzupełnianie dla ComboBox w WPF w dowolnym miejscu w tekście (nie tylko na początku)
- 24. Wykrywanie w czasie rzeczywistym szczytów częstotliwości zdarzeń
- 25. W jaki sposób można programowo wywoływać obsługę zdarzeń myszy na myszy w JavaScript
- 26. Wykrywanie zdarzeń dotknięcia/dotknięcia w okienku podglądu
- 27. Wykrywanie zdarzeń w ramce danych pandy
- 28. Wyrażenie regularne, aby znaleźć dwa ciągi w dowolnym miejscu na wejściu
- 29. Masz kliknięcie w dowolnym miejscu na stronie internetowej, a następnie wybierz rozwijane menu.
- 30. Wykrywanie zdarzenia kliknięcia środkowym przyciskiem myszy jQuery
Odpowiedzi na to pytanie dotyczą Twojego problemu: http://stackoverflow.com/questions/1882055/java-swing-change-background-color-on-mouse-over – Ash