{"id":790,"date":"2021-01-11T18:42:34","date_gmt":"2021-01-11T18:42:34","guid":{"rendered":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/?page_id=790"},"modified":"2021-01-11T19:00:28","modified_gmt":"2021-01-11T19:00:28","slug":"windows","status":"publish","type":"page","link":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/course-topics\/events\/windows\/","title":{"rendered":"Windows"},"content":{"rendered":"<div id=\"ez-toc-container\" class=\"ez-toc-v2_0_84 counter-hierarchy ez-toc-counter ez-toc-grey ez-toc-container-direction\">\n<p class=\"ez-toc-title\" style=\"cursor:inherit\">Table of Contents<\/p>\n<label for=\"ez-toc-cssicon-toggle-item-6a21c317454bf\" class=\"ez-toc-cssicon-toggle-label\"><span class=\"\"><span class=\"eztoc-hide\" style=\"display:none;\">Toggle<\/span><span class=\"ez-toc-icon-toggle-span\"><svg style=\"fill: #999;color:#999\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" class=\"list-377408\" width=\"20px\" height=\"20px\" viewBox=\"0 0 24 24\" fill=\"none\"><path d=\"M6 6H4v2h2V6zm14 0H8v2h12V6zM4 11h2v2H4v-2zm16 0H8v2h12v-2zM4 16h2v2H4v-2zm16 0H8v2h12v-2z\" fill=\"currentColor\"><\/path><\/svg><svg style=\"fill: #999;color:#999\" class=\"arrow-unsorted-368013\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" width=\"10px\" height=\"10px\" viewBox=\"0 0 24 24\" version=\"1.2\" baseProfile=\"tiny\"><path d=\"M18.2 9.3l-6.2-6.3-6.2 6.3c-.2.2-.3.4-.3.7s.1.5.3.7c.2.2.4.3.7.3h11c.3 0 .5-.1.7-.3.2-.2.3-.5.3-.7s-.1-.5-.3-.7zM5.8 14.7l6.2 6.3 6.2-6.3c.2-.2.3-.5.3-.7s-.1-.5-.3-.7c-.2-.2-.4-.3-.7-.3h-11c-.3 0-.5.1-.7.3-.2.2-.3.5-.3.7s.1.5.3.7z\"\/><\/svg><\/span><\/span><\/label><input type=\"checkbox\"  id=\"ez-toc-cssicon-toggle-item-6a21c317454bf\"  aria-label=\"Toggle\" \/><nav><ul class='ez-toc-list ez-toc-list-level-1 ' ><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-1\" href=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/course-topics\/events\/windows\/#Frame_as_Listener\" >Frame as Listener<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-2\" href=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/course-topics\/events\/windows\/#Separate_Class_as_Listener\" >Separate Class as Listener<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-3\" href=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/course-topics\/events\/windows\/#Member_Class_as_Listener\" >Member Class as Listener<\/a><\/li><li class='ez-toc-page-1 ez-toc-heading-level-3'><a class=\"ez-toc-link ez-toc-heading-4\" href=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/course-topics\/events\/windows\/#Anonymous_Class_as_Listener\" >Anonymous Class as Listener<\/a><\/li><\/ul><\/nav><\/div>\n\n<p class=\"wp-block-paragraph\">Window events are generated when the user performs certain actions on a Java <em>frame<\/em>:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>Opening<\/li><li>Closing<\/li><li>Closed<\/li><li>Iconified (i.e. minimized)<\/li><li>Deiconified (i.e. restored)<\/li><li>Activated<\/li><li>Deactivated<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">All of these cause a&nbsp;<code><strong>WindowEvent<\/strong><\/code>&nbsp;to be generated by the frame, and if you wish to handle such events, you must specify a&nbsp;<code><strong>WindowListener<\/strong><\/code>&nbsp;for them.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\"><span class=\"ez-toc-section\" id=\"Frame_as_Listener\"><\/span>Frame as Listener<span class=\"ez-toc-section-end\"><\/span><\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Here&#8217;s a first cut at a class that listens to window events.&nbsp; It uses the frame class itself as the listener:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: java; auto-links: false; highlight: [3,4,9,14,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39]; title: ; quick-code: false; notranslate\" title=\"\">\npackage swingExamples;\n\nimport java.awt.event.WindowEvent;\nimport java.awt.event.WindowListener;\n\nimport javax.swing.JFrame;\n\npublic class CloseableFrame1 extends JFrame\n    implements WindowListener\n{\n  public CloseableFrame1()\n  {\n    setTitle(&quot;CloseableFrame1&quot;);\n    addWindowListener(this);\n  }\n  \n  \/\/ Methods required by WindowListener interface\n  public void windowActivated(WindowEvent e)\n  {\n  }\n  public void windowClosed(WindowEvent e)\n  {\n  }\n  public void windowClosing(WindowEvent e)\n  {\n    System.exit(0); \/\/ Exit program\n  }\n  public void windowDeactivated(WindowEvent e)\n  {\n  }\n  public void windowDeiconified(WindowEvent e)\n  {\n  }\n  public void windowIconified(WindowEvent e)\n  {\n  }\n  public void windowOpened(WindowEvent e)\n  {\n  }\n  \n  public static void main(String&#x5B;] args)\n  {\n    CloseableFrame1 frame = new CloseableFrame1();\n    frame.setSize(300, 200);\n    frame.setVisible(true);\n  }\n}\n<\/pre><\/div>\n\n\n<p class=\"wp-block-paragraph\">which produces the following (again, fascinating) output:<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"alignleft size-large\"><img fetchpriority=\"high\" decoding=\"async\" width=\"300\" height=\"200\" src=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-content\/uploads\/2021\/01\/CloseableFrame1.gif\" alt=\"\" class=\"wp-image-794\"\/><\/figure><\/div>\n\n\n\n<div style=\"height:28px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">Do you notice how many methods we had to implement that are empty &#8212; that is, they do nothing?<\/p>\n\n\n\n<h3 class=\"wp-block-heading\"><span class=\"ez-toc-section\" id=\"Separate_Class_as_Listener\"><\/span>Separate Class as Listener<span class=\"ez-toc-section-end\"><\/span><\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Here&#8217;s another example, where we&#8217;ve moved the responsibility for listening for windows events into a separate class:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: java; auto-links: false; highlight: [13,24,25,26,27,28,29,30,41,42,43,59]; title: ; quick-code: false; notranslate\" title=\"\">\npackage swingExamples;\n\nimport java.awt.event.WindowEvent;\nimport java.awt.event.WindowListener;\n\nimport javax.swing.JFrame;\n\npublic class CloseableFrame2 extends JFrame\n{\n  public CloseableFrame2()\n  {\n    setTitle(&quot;CloseableFrame2&quot;);\n    addWindowListener( new WindowCloser(this) );\n  }\n  \n  public static void main(String&#x5B;] args)\n  {\n    CloseableFrame2 frame = new CloseableFrame2();\n    frame.setSize(300, 200);\n    frame.setVisible(true);\n  }\n}\n\nclass WindowCloser implements WindowListener\n{\n  \/\/ Constructor\n  WindowCloser(JFrame frame)\n  {\n    m_frame = frame;\n  }\n  \n  \/\/ Methods required by WindowListener interface\n  public void windowActivated(WindowEvent e)\n  {\n  }\n  public void windowClosed(WindowEvent e)\n  {\n  }\n  public void windowClosing(WindowEvent e)\n  {\n    m_frame.setVisible(false); \/\/ Make the frame invisible\n    m_frame.dispose(); \/\/ Clean it up\n    System.exit(0); \/\/ Exit program\n  }\n  public void windowDeactivated(WindowEvent e)\n  {\n  }\n  public void windowDeiconified(WindowEvent e)\n  {\n  }\n  public void windowIconified(WindowEvent e)\n  {\n  }\n  public void windowOpened(WindowEvent e)\n  {\n  }\n  \n  \/\/\/\/ Private data \/\/\/\/\n  private JFrame m_frame;\n}\n<\/pre><\/div>\n\n\n<p class=\"wp-block-paragraph\">which produces the dazzlingly interesting result:<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"alignleft size-large\"><img decoding=\"async\" width=\"300\" height=\"200\" src=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-content\/uploads\/2021\/01\/CloseableFrame2.gif\" alt=\"\" class=\"wp-image-795\"\/><\/figure><\/div>\n\n\n\n<div style=\"height:21px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">Note that, in the above example, I&#8217;ve emphasized that you really should make the frame invisible, and then call&nbsp;<code><strong>dispose()<\/strong><\/code>&nbsp;on it, to clean it up.&nbsp;&nbsp;<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">This isn&#8217;t so important if all you&#8217;re going to do is exit, but it is if you simply want to dismiss the frame and continue doing work.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Also, note that, in order to use these frame methods, I needed to save a reference to the frame, by passing it into the constructor.&nbsp;&nbsp;<\/p>\n\n\n\n<p class=\"wp-block-paragraph\"><strong>Does that technique sound familiar from somewhere?<\/strong><\/p>\n\n\n\n<h3 class=\"wp-block-heading\"><span class=\"ez-toc-section\" id=\"Member_Class_as_Listener\"><\/span>Member Class as Listener<span class=\"ez-toc-section-end\"><\/span><\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Yet another example.&nbsp; Here, we move the separate class inside the frame class, and make it an&nbsp;<em>inner class &#8212; specifically, a member class<\/em>:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: java; auto-links: false; highlight: [23,27]; title: ; quick-code: false; notranslate\" title=\"\">\npackage swingExamples;\n\nimport java.awt.event.WindowEvent;\nimport java.awt.event.WindowListener;\n\nimport javax.swing.JFrame;\n\npublic class CloseableFrame3 extends JFrame\n{\n  public CloseableFrame3()\n  {\n    setTitle(&quot;CloseableFrame3&quot;);\n    addWindowListener(new WindowCloser());\n  }\n  \n  public static void main(String&#x5B;] args)\n  {\n    CloseableFrame3 frame = new CloseableFrame3();\n    frame.setSize(300, 200);\n    frame.setVisible(true);\n  }\n  \n  \/\/\/\/\/\/\/\/ Inner class \/\/\/\/\/\/\/\/\/\n  \n  class WindowCloser implements WindowListener\n  {\n    \/\/ No explicit constructor needed\n\n    \/\/ Methods required by WindowListener interface\n    public void windowActivated(WindowEvent e)\n    {\n    }\n    public void windowClosed(WindowEvent e)\n    {\n    }\n    public void windowClosing(WindowEvent e)\n    {\n      setVisible(false); \/\/ Make the frame invisible\n      dispose(); \/\/ Clean it up\n      System.exit(0); \/\/ Exit program\n    }\n    public void windowDeactivated(WindowEvent e)\n    {\n    }\n    public void windowDeiconified(WindowEvent e)\n    {\n    }\n    public void windowIconified(WindowEvent e)\n    {\n    }\n    public void windowOpened(WindowEvent e)\n    {\n    }\n  }\n}\n<\/pre><\/div>\n\n\n<p class=\"wp-block-paragraph\">which produces the amazing result:<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"alignleft size-large\"><img decoding=\"async\" width=\"300\" height=\"200\" src=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-content\/uploads\/2021\/01\/CloseableFrame3.gif\" alt=\"\" class=\"wp-image-796\"\/><\/figure><\/div>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">Notice how we no longer need to pass an explicit reference to the frame into the inner class&#8217;s constructor, because we have an implicit reference to the outer class automatically, as a result of it being a member class.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">As a consequence, there are also fewer lines of code in this example, when compared with the previous example.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\"><span class=\"ez-toc-section\" id=\"Anonymous_Class_as_Listener\"><\/span>Anonymous Class as Listener<span class=\"ez-toc-section-end\"><\/span><\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Here&#8217;s the equivalent program using an <em>anonymous clas<\/em>s as the windows event listener.&nbsp;&nbsp;<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">This time, however, the anonymous class uses a&nbsp;<code><strong>WindowAdapter<\/strong><\/code>&nbsp;class to make the implementation even more succinct.&nbsp; This has the great convenience of not forcing us to write a large number of empty, do-nothing methods in our listener class.<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: java; auto-links: false; highlight: [14,15,16,17,18,19,20,21,22]; title: ; quick-code: false; notranslate\" title=\"\">\npackage swingExamples;\n\nimport java.awt.event.WindowEvent;\nimport java.awt.event.WindowAdapter;\n\nimport javax.swing.JFrame;\n\npublic class CloseableFrame4\n    extends JFrame\n{\n  public CloseableFrame4()\n  {\n    setTitle(&quot;CloseableFrame4&quot;);\n    addWindowListener(new WindowAdapter()\n    {\n      public void windowClosing(WindowEvent e)\n      {\n        setVisible(false);\n        dispose();\n        System.exit(0);\n      }\n    }\n    );\n  }\n  \n  public static void main(String&#x5B;] args)\n  {\n    CloseableFrame4 frame = new CloseableFrame4();\n    frame.setSize(300, 200);\n    frame.setVisible(true);\n  }\n}\n<\/pre><\/div>\n\n\n<div class=\"wp-block-image\"><figure class=\"alignleft size-large\"><img loading=\"lazy\" decoding=\"async\" width=\"300\" height=\"200\" src=\"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-content\/uploads\/2021\/01\/CloseableFrame4.gif\" alt=\"\" class=\"wp-image-797\"\/><\/figure><\/div>\n\n\n\n<div style=\"height:21px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">This time, we have the shortest version.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">See how inner classes, and in particular, anonymous classes can really shorten your code, and once you understand them, also simplify your code, and make it more cohesive?<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Window events are generated when the user performs certain actions on a Java frame: Opening Closing Closed Iconified (i.e. minimized) Deiconified (i.e. restored) Activated Deactivated All of these cause a&nbsp;WindowEvent&nbsp;to be generated by the frame, and if you wish to handle such events, you must specify a&nbsp;WindowListener&nbsp;for them. Frame as Listener Here&#8217;s a first cut [&hellip;]<\/p>\n","protected":false},"author":2,"featured_media":0,"parent":69,"menu_order":0,"comment_status":"closed","ping_status":"closed","template":"","meta":{"_eb_attr":"","_uag_custom_page_level_css":"","ocean_post_layout":"left-sidebar","ocean_both_sidebars_style":"","ocean_both_sidebars_content_width":0,"ocean_both_sidebars_sidebars_width":0,"ocean_sidebar":"ocs-course-topics-sidebar","ocean_second_sidebar":"0","ocean_disable_margins":"enable","ocean_add_body_class":"","ocean_shortcode_before_top_bar":"","ocean_shortcode_after_top_bar":"","ocean_shortcode_before_header":"","ocean_shortcode_after_header":"","ocean_has_shortcode":"","ocean_shortcode_after_title":"","ocean_shortcode_before_footer_widgets":"","ocean_shortcode_after_footer_widgets":"","ocean_shortcode_before_footer_bottom":"","ocean_shortcode_after_footer_bottom":"","ocean_display_top_bar":"default","ocean_display_header":"default","ocean_header_style":"","ocean_center_header_left_menu":"0","ocean_custom_header_template":"0","ocean_custom_logo":0,"ocean_custom_retina_logo":0,"ocean_custom_logo_max_width":0,"ocean_custom_logo_tablet_max_width":0,"ocean_custom_logo_mobile_max_width":0,"ocean_custom_logo_max_height":0,"ocean_custom_logo_tablet_max_height":0,"ocean_custom_logo_mobile_max_height":0,"ocean_header_custom_menu":"0","ocean_menu_typo_font_family":"0","ocean_menu_typo_font_subset":"","ocean_menu_typo_font_size":0,"ocean_menu_typo_font_size_tablet":0,"ocean_menu_typo_font_size_mobile":0,"ocean_menu_typo_font_size_unit":"px","ocean_menu_typo_font_weight":"","ocean_menu_typo_font_weight_tablet":"","ocean_menu_typo_font_weight_mobile":"","ocean_menu_typo_transform":"","ocean_menu_typo_transform_tablet":"","ocean_menu_typo_transform_mobile":"","ocean_menu_typo_line_height":0,"ocean_menu_typo_line_height_tablet":0,"ocean_menu_typo_line_height_mobile":0,"ocean_menu_typo_line_height_unit":"","ocean_menu_typo_spacing":0,"ocean_menu_typo_spacing_tablet":0,"ocean_menu_typo_spacing_mobile":0,"ocean_menu_typo_spacing_unit":"","ocean_menu_link_color":"","ocean_menu_link_color_hover":"","ocean_menu_link_color_active":"","ocean_menu_link_background":"","ocean_menu_link_hover_background":"","ocean_menu_link_active_background":"","ocean_menu_social_links_bg":"","ocean_menu_social_hover_links_bg":"","ocean_menu_social_links_color":"","ocean_menu_social_hover_links_color":"","ocean_disable_title":"default","ocean_disable_heading":"default","ocean_post_title":"","ocean_post_subheading":"","ocean_post_title_style":"","ocean_post_title_background_color":"","ocean_post_title_background":0,"ocean_post_title_bg_image_position":"","ocean_post_title_bg_image_attachment":"","ocean_post_title_bg_image_repeat":"","ocean_post_title_bg_image_size":"","ocean_post_title_height":0,"ocean_post_title_bg_overlay":0.5,"ocean_post_title_bg_overlay_color":"","ocean_disable_breadcrumbs":"default","ocean_breadcrumbs_color":"","ocean_breadcrumbs_separator_color":"","ocean_breadcrumbs_links_color":"","ocean_breadcrumbs_links_hover_color":"","ocean_display_footer_widgets":"default","ocean_display_footer_bottom":"default","ocean_custom_footer_template":"0","footnotes":""},"class_list":["post-790","page","type-page","status-publish","hentry","entry"],"uagb_featured_image_src":{"full":false,"thumbnail":false,"medium":false,"medium_large":false,"large":false,"1536x1536":false,"2048x2048":false,"ocean-thumb-m":false,"ocean-thumb-ml":false,"ocean-thumb-l":false},"uagb_author_info":{"display_name":"Bryan Higgs","author_link":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/author\/bryan\/"},"uagb_comment_info":0,"uagb_excerpt":"Window events are generated when the user performs certain actions on a Java frame: Opening Closing Closed Iconified (i.e. minimized) Deiconified (i.e. restored) Activated Deactivated All of these cause a&nbsp;WindowEvent&nbsp;to be generated by the frame, and if you wish to handle such events, you must specify a&nbsp;WindowListener&nbsp;for them. Frame as Listener Here&#8217;s a first cut&hellip;","_links":{"self":[{"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/pages\/790","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/comments?post=790"}],"version-history":[{"count":8,"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/pages\/790\/revisions"}],"predecessor-version":[{"id":804,"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/pages\/790\/revisions\/804"}],"up":[{"embeddable":true,"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/pages\/69"}],"wp:attachment":[{"href":"https:\/\/bhiggs.x10hosting.com\/PracticalJavaProgramming\/wp-json\/wp\/v2\/media?parent=790"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}