<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Swing


    天行健 君子以自強不息

    posts - 69, comments - 215, trackbacks - 0, articles - 16
       :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理

    監(jiān)聽JComponent顯示事件

    Posted on 2010-02-04 22:09 zht 閱讀(1510) 評論(1)  編輯  收藏 所屬分類: Swing

        很多時候,我們需要在界面初始化以后對程序進行某些設置,舉個例子,當界面呈現(xiàn)出來以后,設置下SplitPane的的百分比(關于這個為什么必須這么處理請參考java源代碼)。很容易我們就想到給程序添加ComponentListener監(jiān)聽,然后在監(jiān)聽中作處理,如下所示

    panel.addComponentListener(new ComponentAdapter() {

                         public void componentShown(ComponentEvent e) {

                                System.out.println("panel:shown");

                         }

                  });

    但是并沒有和我們想象的那樣,當組件在界面上顯示出來的時候firecomponentShown類型的事件的,下面我們通過研究源代碼分析下原因

    首先的問題是在什么地方會fireComponentEvent

    通過查看源代碼,我們可以看到實在Componentshow()方法中

    ComponentEvent e = new ComponentEvent(this,ComponentEvent.COMPONENT_SHOWN);

    Toolkit.getEventQueue().postEvent(e);

    具體代碼,請參考java源程序

    也就是說只有在組件調(diào)用到setVisible(true)的時候才會fireComponentEvent

    但是你會發(fā)現(xiàn),即便是我們調(diào)用JComponentsetVisible(true),也不會監(jiān)聽到shown事件

    原因主要是JComponent重載了setVisible方法

    如下

    public void setVisible(boolean aFlag) {

            if(aFlag != isVisible()) {

                super.setVisible(aFlag);

                Container parent = getParent();

                if(parent != null) {

                    Rectangle r = getBounds();

                    parent.repaint(r.x,r.y,r.width,r.height);

                }

               // Some (all should) LayoutManagers do not consider components

               // that are not visible. As such we need to revalidate when the

               // visible bit changes.

               revalidate();

            }

    }

    因為JComponentvisible屬性默認就是true,所以不會調(diào)用到ComponentsetVisible方法,所以也不會fireComponentEvent,當然,如果你調(diào)用下JComponentsetVisible(false)+setVisible(true)是會fireComponentEvent.COMPONENT_SHOWN事件的,(但是在里面很可能得不到當前組件的大小信息或者不能SplitPane設置分割比例,因為這個時候界面還沒有初始化),而且如果是JFrameJDialogJApplet等也是沒問題的,因為他們調(diào)用的都是ComponentsetVisible方法(所以給這些頂層組件添加ComponentListener是沒有問題的,都會監(jiān)聽到)

    如果不想使用上述方法,還有另外一種方式就是添加HierarchyListener監(jiān)聽,因為當頂層組件(JFrame,JDialog)setVisible(true)界面顯示的時候,里面都會fireHierarchyEvent,具體代碼如下(詳細代碼請參考Componentshow()方法)

           createHierarchyEvents(HierarchyEvent.HIERARCHY_CHANGED,

                                         this, parent,

                                         HierarchyEvent.SHOWING_CHANGED,

                                              Toolkit.enabledOnToolkit(AWTEvent.HIERARCHY_EVENT_MASK));

    createHierarchyEvents方法會在每個組件上fireHierarchyEvent,至于具體細節(jié),有時間的可以dubug下,具體的解決方法如下

           panel.addHierarchyListener(new HierarchyListener() {

                         public void hierarchyChanged(HierarchyEvent e) {

                                if ((e.getChangeFlags() & HierarchyEvent.SHOWING_CHANGED) != 0) {

                                       if (e.getComponent().isShowing()) {

                                              System.out.println(panel.getBounds());

                                              System.out.println("panel:hshow");

                                       }

                                       else {

                                              System.out.println("panel:hhide");

                                       }

                                }

                         }

                  });

    測試代碼如下
    public class Test {
        
    public static void main(String[] args) {
            
    new Test();
        }


        
    public Test() {
            
    final JPanel panel = new JPanel();
            panel.addComponentListener(
    new ComponentAdapter() {
                
    public void componentShown(ComponentEvent e) {
                    System.out.println(panel.getBounds());
                    System.out.println(
    "panel:shown");
                }

            }
    );
            
    //        panel.setVisible(false);
            
    //        panel.setVisible(true);
            panel.addHierarchyListener(new HierarchyListener() {
                
    public void hierarchyChanged(HierarchyEvent e) {
                    
    if ((e.getChangeFlags() & HierarchyEvent.SHOWING_CHANGED) != 0{
                        
    if (e.getComponent().isShowing()) {
                            System.out.println(panel.getBounds());
                            System.out.println(
    "panel:hshow");
                        }

                        
    else {
                            System.out.println(
    "panel:hhide");
                        }

                    }

                }

            }
    );

            JFrame frame 
    = new JFrame();

            frame.addComponentListener(
    new ComponentAdapter() {
                
    public void componentShown(ComponentEvent e) {
                    System.out.println(
    "frame:shown");
                }

            }
    );

            frame.setContentPane(panel);
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.setSize(
    500400);
            frame.setVisible(
    true);
        }

    }

    主站蜘蛛池模板: 亚洲an日韩专区在线| 一个人免费观看视频www| 亚洲AV日韩AV无码污污网站| 亚洲精品乱码久久久久久久久久久久| 成**人免费一级毛片| 84pao国产成视频免费播放| 国产乱子伦精品免费视频| 亚洲日韩AV无码一区二区三区人 | 亚洲国产成人久久综合| 亚洲电影中文字幕| 国产亚洲精aa成人网站| 国产乱子伦精品免费女| 国产在线国偷精品产拍免费| 最近中文字幕国语免费完整| 暖暖在线视频免费视频| 久久最新免费视频| 一区视频免费观看| 女人裸身j部免费视频无遮挡| 亚洲国产区男人本色| 亚洲精品GV天堂无码男同| 国产日本亚洲一区二区三区| 亚洲精品欧洲精品| 亚洲高清美女一区二区三区| 亚洲人成网站影音先锋播放| 亚洲国产精品无码成人片久久| 亚洲乱码国产一区网址| 伊在人亚洲香蕉精品区麻豆| 国产高清免费的视频| 国产成人无码免费视频97| 日本无卡码免费一区二区三区| 日韩a在线观看免费观看| 四虎在线免费播放| 日韩a在线观看免费观看| 又大又粗又爽a级毛片免费看| 国产传媒在线观看视频免费观看| 日韩人妻无码免费视频一区二区三区| 高清国语自产拍免费视频国产 | 国产亚洲一区二区手机在线观看 | 特黄特色的大片观看免费视频| 婷婷国产偷v国产偷v亚洲| 国产亚洲视频在线观看网址|