My question is :: I regiester windowsEvent two times one is from baseclass JFrame( all windowsEvent will be caught and process by processWindowEvent which is JFrame's method second i register windows by a anonymous class in line 94) why if i comment out CallInterface.java line 105 then line 97 will not be invoked when window was closed, only line 106 will be invoked? thx for attention import java.awt.*; import java.awt.event.*; import javax.swing.*; import java.awt.*; import java.awt.event.*; import javax.swing.*; public class CallInterface extends JFrame { JPanel contentPane; JPanel jPanel1 = new JPanel(); //jpanel1 contains jpanel1a, //jpanel1a contains jpanel1aa,jpanel1ab,jPanel1ac jpanelaa //add label,jpanelab add label and textfields jpanelac add //label and textfields JPanel jPanel1a= new JPanel(new BorderLayout()); JPanel jPanel1aa=new JPanel(); JPanel jPanel1ab=new JPanel(); JPanel jPanel1ac=new JPanel(); JLabel label=new JLabel("Please Enter IP address and Port Number "); JLabel audiolabel=new JLabel("Audio"); JLabel vediolabel=new JLabel("Vedio"); JLabel portlabel1 = new JLabel("Port"); JLabel portlabel2 = new JLabel("Port"); JTextField jTextField1 = new JTextField(5); JTextField jTextField2 = new JTextField(5); JTextField jTextField3 = new JTextField(5); JTextField jTextField4 = new JTextField(5); JTextField jTextField5 = new JTextField(5); JPanel jPanel2 = new JPanel(new BorderLayout()); JTextField jTextField6 = new JTextField(5); JTextField jTextField7 = new JTextField(5); JTextField jTextField8 = new JTextField(5); JTextField jTextField9 = new JTextField(5); JTextField jTextField10 = new JTextField(5); JPanel jPanel3 = new JPanel(); JButton jButton1 = new JButton(); JButton jButton2 = new JButton(); /**Construct the frame*/ public CallInterface() { enableEvents(AWTEvent.WINDOW_EVENT_MASK); try { jbInit(); setVisible(true); } catch(Exception e) { e.printStackTrace(); } } /**Component initialization*/ private void jbInit() throws Exception { //setIconImage(Toolkit.getDefaultToolkit().createImage(Frame1.class.getResource("[Your Icon]"))); contentPane = (JPanel) this.getContentPane(); contentPane.setLayout(new BorderLayout()); this.setSize(new Dimension(450, 500)); this.setTitle("Call Setting Interface"); jButton1.setText(" Connect "); contentPane.add(jPanel1, BorderLayout.NORTH); contentPane.add(jPanel2, BorderLayout.CENTER); contentPane.add(jPanel3, BorderLayout.SOUTH ); jPanel1.add(jPanel1a); jPanel1a.add(jPanel1aa,BorderLayout.NORTH); jPanel1a.add(jPanel1ab,BorderLayout.CENTER); jPanel1a.add(jPanel1ac,BorderLayout.SOUTH); jPanel3.add(jButton1, null); jPanel2.add(new CallTabbedPane(), BorderLayout.CENTER); //jPanel2.setSize(400,300); jPanel1a.add(jPanel1aa, BorderLayout.NORTH); jPanel1a.add(jPanel1ac, BorderLayout.SOUTH); jPanel1aa.add(label); jPanel1ab.add(vediolabel); jPanel1ab.add(jTextField1, null); jPanel1ab.add(jTextField2, null); jPanel1ab.add(jTextField3, null); jPanel1ab.add(jTextField4, null); jPanel1ab.add(portlabel2, null); jPanel1ab.add(jTextField5, null); jPanel1ac.add(audiolabel, null); jPanel1ac.add(jTextField6, null); jPanel1ac.add(jTextField7, null); jPanel1ac.add(jTextField8, null); jPanel1ac.add(jTextField9, null); jPanel1ac.add(portlabel1, null); jPanel1ac.add(jTextField10, null);
addWindowListener // Line 94 (new WindowAdapter() { public void windowClosing(WindowEvent e) { System.out.println("windowClosing was invoked");//line 97 e.getWindow().dispose(); } }); } protected void processWindowEvent(WindowEvent e) { //if commenet out this line,why windowClosing method will not be invoke? super.processWindowEvent(e);//line 105 System.out.println("processWindowEvent was invoked");//line 106 } public static void main(String args[]){ new CallInterface(); } }
public class Walter{
public boolean is_Working_Now(boolean is_boss_Coming){
return is_boss_Coming;
}
Sean MacLean
author
Ranch Hand
Joined: Nov 07, 2000
Posts: 621
posted
0
Walter, I think you may have more luck with this question in the Swing... forum so I'm moving you post there. Sean
Manfred Leonhardt
Ranch Hand
Joined: Jan 09, 2001
Posts: 1492
posted
0
Hi Walter, That is because you are overriding the processWindowEvent method. The default functionality is to notify all the component's registered listeners. Since you are overridding that functionality and not performing it the windowClosing method will not be called. By calling the parent processWindowEvent you are restoring the default functionality. It is not normal to override processXXXXEvent methods unless you want to change the default behavior or have some need to be the first to know when an event is about to happen. Regards, Manfred.
walter wang
Ranch Hand
Joined: Jun 02, 2001
Posts: 144
posted
0
Originally posted by Manfred Leonhardt: Hi Walter, That is because you are overriding the processWindowEvent method. The default functionality is to notify all the component's registered listeners. Since you are overridding that functionality and not performing it the windowClosing method will not be called. By calling the parent processWindowEvent you are restoring the default functionality. It is not normal to override processXXXXEvent methods unless you want to change the default behavior or have some need to be the first to know when an event is about to happen. Regards, Manfred.
Dear Manfred Thx for your explaination yeah i checked processWindowEvent in java.awt.Window.java After analyse code i find ,if i close window processWindowEvent will notify all reigestered windowsListerner by windowListener.windowClosing(e); but if i subclass(CallInterface.java) i register two WindowsListerners , so when i close windows two WindowsListerners will be notified but look code windowListener.windowClosing(e), seems only could notify one windowListener i check windowListener in java.awt.Window.java it is transient (transient WindowListener windowListener How does it work out? just declaring windowListener as transient then by calling windowListener.windowClosing(e) then it will notfiy all the registered WindowListeners just by one line ? regards protected void processWindowEvent(WindowEvent e) { if (windowListener != null) { switch(e.getID()) case WindowEvent.WINDOW_OPENED: windowListener.windowOpened(e); break; case WindowEvent.WINDOW_CLOSING: windowListener.windowClosing(e); break;
Dear Manfred thx for your hints, follow your hints i explore a little bit, i 'd like to share my explored result with everyone. Window.java has one method processWindowEvent has a transient WindowListener windowListener; /* Window.java if u did set enableWindowEvent to ture,then when WindowEvent ocurring processWindowEvent will send WindowEvent to the registered WindowEvent listeners example.if WindowEvent.WINDOW_CLOSING: it will call windowListener.windowClosing(e),by calling this, all registered listeners, what ever how many, all will be notified. When u closing Window how does windowListener.windowClosing(e) will notify all registered listners just by one line code? Now we discuss what is the machanisim behind it. //Window 's method protected void processWindowEvent(WindowEvent e) { if (windowListener != null) { switch(e.getID()) { case WindowEvent.WINDOW_OPENED: windowListener.windowOpened(e); break; case WindowEvent.WINDOW_CLOSING: windowListener.windowClosing(e); break; // Window 's method public synchronized void addWindowListener(WindowListener l) { if (l == null) { return; } windowListener = AWTEventMulticaster.add(windowListener, l); .... } */ So if you have a SubWindow extends Window in SubWindow's constructor you regsiter 3 different listerners like this public SubWindow(){ addWindowListener(listernerA); addWindowListener(listernerB); addWindowListener(listernerC); .... } so you will call 3 times addWindowListener method in Window.java first time you call addWindowListener windowListener(variable in Window.java)= listenerA; second time windowListener= new AWTEventMulticaster(frist time's windowListener,listenerB); third time windowListener= new AWTEventMulticaster(second time'swindowListener,listenerC); for details you should check AWTEventMulticaster.java when u closing SubWindow you will invoke Window.java's processWindowEvent'method's line windowListener.windowClosing(e); at this time windowListener is new AWTEventMulticaster(second time'swindowListener,listenerC); you could take it as new AWTEventMulticaster(new AWTEventMulticaster(listenerA,listenerB),listenerC); so at this moment calling windowListener.windowClosing(e) will invoke AWTEventMulticaster's windowClosing method firstly, then it was invoking like this //AWTEventMulticaster' method public void windowClosing(WindowEvent e) { //actually(WindowListener)new AWTEventMulticaster(listenerA,listenerB) is still AWTEventMulticaster type // so it will recursively invoke AWTEventMultcaster's windowClosing method until it was decompressed to // listenerA and listenerB,then will invoke listenerA and listenerB's own windowClosing method seperately ((WindowListener)new AWTEventMulticaster(listenerA,listenerB) ).windowClosing(e);
//inovke it's self 's windowClosing(e) in this case. invoke listenerC's windowClosing() ((WindowListener)listenerC).windowClosing(e);//because it is not AWTEventMulticaster type anymore,so it will
} but this way. you could register any listeners to Window.java , then in Window.java's by simply calling windowListener.windowClosing(e) once, it will invoke all listeners windowClosing methods / ****************** AWTEventMulticaster.java 's method******************* protected AWTEventMulticaster(EventListener a, EventListener b) { this.a = a; this.b = b; } public static WindowListener add(WindowListener a, WindowListener b) { return (WindowListener)addInternal(a, b); } protected static EventListener addInternal(EventListener a, EventListener b) { if (a == null) return b; if (b == null) return a; return new AWTEventMulticaster(a, b); } public void windowClosing(WindowEvent e) { ((WindowListener)a).windowClosing(e); ((WindowListener)b).windowClosing(e); } *******************************************************************/