United StatesChange Country, Oracle Worldwide Web Sites Communities I am a... I want to...
JDK-4664415 : REGRESSION: double click jframe titlebar generating mouse events in panel

Details
Type:
Bug
Submit Date:
2002-04-08
Status:
Resolved
Updated Date:
2003-04-12
Project Name:
JDK
Resolved Date:
2002-08-22
Component:
client-libs
OS:
windows_2000
Sub-Component:
java.awt
CPU:
x86
Priority:
P4
Resolution:
Fixed
Affected Versions:
1.4.0
Fixed Versions:
1.4.2 (mantis)

Related Reports
Relates:
Relates:

Sub Tasks

Description

Name: jk109818			Date: 04/08/2002


FULL PRODUCT VERSION :
java version "1.4.0"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.0-b92)
Java HotSpot(TM) Client VM (build 1.4.0-b92, mixed mode)

FULL OPERATING SYSTEM VERSION :
Microsoft Windows 2000 [Version 5.00.2195]

EXTRA RELEVANT SYSTEM CONFIGURATION :
don't think anything is relevant...

A DESCRIPTION OF THE PROBLEM :
I have a JFrame.  Inside this JFrame I have added a
JPanel.  On the JPanel I have put a MouseListener.  When I
double click the JFrame's title bar to maximize the window,
a mousepressed event and 2 mousereleased events are
generated ON THE JPANEL.  If I maximize the JFrame using
the maximize button, this doesn't happen.  It also doesn't
happen when double clicking the title bar to take the
JFrame back to its "pre-maximized" size.

Here are some other bugs (sure you probably already know
about them, if not I have others, let me know):

Popup menus with many items scroll off the screen, it can't
be that hard to make the menu scrollable up and down
(something like the favorites menu does in internet
explorer).. ?

  Tooltips should not appear over (obscuring) a button's text.

  Tooltips should not go offscreen.

  Tooltips should be multiline enabled... ?

(This maybe something I'm doing wrong).  JButtons with
images will not be repainted when offscreen for a long
time.  When the window is reshown, the buttons are all gray.

Sorry for the whining, I really do like Java and think you
guys are doing a great job

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
1.Make a JFrame
2. put a JPanel in it
3. put a mouse listener on the jpanel
4. put a system.out in the mousePressed/released methods
5. double click the jframe title bar to maximize it

EXPECTED VERSUS ACTUAL BEHAVIOR :
i expect no mouse events to be generated

ERROR MESSAGES/STACK TRACES THAT OCCUR :
there are no error messages

This bug can be reproduced always.

---------- BEGIN SOURCE ----------
can supply if requested

my class basically just extends jframe, and has an inner class that extends
jpanel.
---------- END SOURCE ----------

CUSTOMER WORKAROUND :
I don't know... I was thinking about removing the
mouselistener in a component listener on the frame, but im
not sure that would even work

Release Regression From : 1.3.1_03
The above release value was the last known release where this 
bug was known to work. Since then there has been a regression.

(Review ID: 144973) 
======================================================================

                                    

Comments
CONVERTED DATA

BugTraq+ Release Management Values

COMMIT TO FIX:
mantis
mantis-b02

FIXED IN:
mantis
mantis-b02

INTEGRATED IN:
mantis
mantis-b02


                                     
2004-06-14
SUGGESTED FIX

------- awt_Component.cpp -------
*** /tmp/sccs.Ctayev    Thu Aug  8 13:50:27 2002
--- awt_Component.cpp   Thu Aug  8 13:33:48 2002
***************
*** 1141,1146 ****
--- 1141,1148 ----
      LRESULT retValue = 0;
      MsgRouting mr = mrDoDefault;
  
+       static BOOL ignoreNextLBTNUP = FALSE; //Ignore next LBUTTONUP msg?
+ 
      lastMessage = message;
  
      if (message == WmAwtIsComponent) {
***************
*** 1361,1369 ****
        case WM_VSCROLL:    
            mr = WmVScroll(LOWORD(wParam), HIWORD(wParam), (HWND)lParam); 
            break;
        case WM_LBUTTONDOWN:
        case WM_LBUTTONDBLCLK: 
-       case WM_LBUTTONUP: 
        case WM_RBUTTONDOWN:
        case WM_RBUTTONDBLCLK: 
        case WM_RBUTTONUP: 
--- 1363,1388 ----
        case WM_VSCROLL:    
            mr = WmVScroll(LOWORD(wParam), HIWORD(wParam), (HWND)lParam); 
            break;
+       // 4664415: We're seeing a WM_LBUTTONUP when the user releases the 
+       // mouse button after a WM_NCLBUTTONDBLCLK.  We want to ignore this
+       // WM_LBUTTONUP, so we set a flag in WM_NCLBUTTONDBLCLK and look for the
+       // flag on a WM_LBUTTONUP.  -bchristi
+       case WM_NCLBUTTONDBLCLK:
+           ignoreNextLBTNUP = TRUE;
+           break;
+       case WM_NCLBUTTONDOWN: 
+           ignoreNextLBTNUP = FALSE;
+           break;
+       case WM_LBUTTONUP: 
+           if (ignoreNextLBTNUP) {
+               ignoreNextLBTNUP = FALSE;
+               return mrDoDefault;
+           }
+           //fall-through
        case WM_LBUTTONDOWN:
+           ignoreNextLBTNUP = FALSE;
+           //fall-through
        case WM_LBUTTONDBLCLK: 
        case WM_RBUTTONDOWN:
        case WM_RBUTTONDBLCLK: 
        case WM_RBUTTONUP: 

###@###.### 2002-08-08
                                     
2002-08-08
EVALUATION

Easily reproducible with the following little test case:

import javax.swing.*;
import java.awt.event.*;
import java.awt.*;

public class MyTest extends JFrame implements MouseListener {

    JPanel jp;

    public MyTest() {
        super("MyTest");
        jp = new JPanel();
        jp.addMouseListener(this);
        jp.setBackground(Color.red);
        getContentPane().add(jp);
    }

    public static void main(String[] args) {
        MyTest mt = new MyTest();
        mt.setSize(400, 400);
        mt.show();
    }

    public void mousePressed(MouseEvent e) {
        System.out.println("mousePressed");
    }
    public void mouseReleased(MouseEvent e) {
        System.out.println("mouseReleased");
    }
    public void mouseClicked(MouseEvent e) {
        System.out.println("mouseClicked");
    }
    public void mouseEntered(MouseEvent e) {
        System.out.println("mouseEnter");
    }
    public void mouseExited(MouseEvent e) {
        System.out.println("mouseExit");
    }
}

One interesting behavior: if the JFrame is at the top of the screen, such that the titlebar is already at the top of the screen, the mouseReleased/mouseClicked are not sent to the JPanel.  However, with the JFrame towards the bottom of the screen, the events are sent.  In any case, this could be serious, and should be looked at soon.
###@###.### 2002-04-19

The problem is that when a window is maximized by double-clicking the titlebar on Windows, the window becomes maximized on the second button PRESS.  This can be seen using any top-level window on Windows, such as an Explorer window - you can keep holding the second click.  The window maximizes underneath the mouse cursor.  This bug happens in part because this second mouse release is being delievered to the JFrame.

Spy++ has uncovered something else interesting  -  WM_NCLBUTTONUP events don't ever seem to occur.  For the action of double-clicking a titlebar to maximize the window, you'd expect to see the following events:

WM_NCLBUTTONDOWN
WM_NCLBUTTONUP
WM_NCLBUTTONDBLCLK
WM_NCLBUTTONUP (or possibly WM_LBUTTONUP, since the window maximizes on the click)

But you get WM_LBUTTONUP messages instead of WM_NCLBUTTONUP.

The first WM_LBUTTONUP is uninteresting to AWT, as it occurs in the non-client area.  The cause of this bug is the second WM_LBUTTONUP, which as of 1.4 beta, is handled as a normal MOUSE_RELEASED.  I haven't determined why it is that this problem does not exist in 1.3.1 and previous, but it's clear enough that we should be ignoring this WM_LBUTTONUP.  It's simple enough to remember where and when the last WM_NCLBUTTONDBLCLK happened, and if the next WM_LBUTTONUP occurs in the same place shortly after, it should be ignored.
###@###.### 2002-08-01


Name: dmR10075			Date: 08/02/2002


This is not a regression. Using the test below I was able to reproduce the bug in
JDK1.2(didn't try earlier versions though). It seems to be very general problem caused
by a Windows quirk.

import java.awt.*;
import java.awt.event.*;

public class Test extends Frame {
    public Test() {
        super("Test for double-click");
        Panel pan;
        MouseAdapter ad = new MouseAdapter() {
                public void mousePressed(MouseEvent e) {
                    System.err.println(e);
                }
                public void mouseReleased(MouseEvent e) {
                    System.err.println(e);
                }
            };
        add(pan = new Panel());
        addMouseListener(ad);
        pan.addMouseListener(ad);
        pack();
        setBounds(10, 10, 100, 100);
        setVisible(true);
    }
    public static void main(String[] args) {
        new Test();
    }
}
###@###.### 2002-08-02

======================================================================
                                     
2002-08-02



Hardware and Software, Engineered to Work Together