@Override public void mouseMoved(MouseEvent e) { final MouseEvent event = SwingUtilities.convertMouseEvent(e.getComponent(), e, getParent()); final boolean insideRec = getBounds().contains(event.getPoint()); boolean buttonsNotPressed = (e.getModifiersEx() & (InputEvent.BUTTON1_DOWN_MASK | InputEvent.BUTTON2_DOWN_MASK | InputEvent.BUTTON3_DOWN_MASK)) == 0; if (!myPopupIsShowing && insideRec && buttonsNotPressed) { showPopup(null, false); } else if (myPopupIsShowing && !insideRec) { final Component over = SwingUtilities.getDeepestComponentAt(e.getComponent(), e.getX(), e.getY()); JPopupMenu popup = myUnderPopup.isShowing() ? myUnderPopup : myAbovePopup; if (over != null && popup.isShowing()) { final Rectangle rec = new Rectangle(popup.getLocationOnScreen(), popup.getSize()); int delta = 15; rec.x -= delta; rec.width += delta * 2; rec.y -= delta; rec.height += delta * 2; final Point eventPoint = e.getPoint(); SwingUtilities.convertPointToScreen(eventPoint, e.getComponent()); if (rec.contains(eventPoint)) { return; } } closePopup(); } }
/** Tests if the popup is on the screen. */ public static void isPopupOnScreen(JPopupMenu popup, Rectangle checkBounds) { Dimension dim = popup.getSize(); Point pt = new Point(); SwingUtilities.convertPointToScreen(pt, popup); Rectangle bounds = new Rectangle(pt, dim); if (!SwingUtilities.isRectangleContainingRectangle(checkBounds, bounds)) { throw new RuntimeException("We do not match! " + checkBounds + " / " + bounds); } }