java - How to access AbstractButton's method from anonymous inner class? -


here class:

public class buttonpanel extends jpanel {     public buttonpanel () {         makebutton ("button1");         makebutton ("button2");         makebutton ("button3");     }      void makebutton (string name) {         jbutton button =new jbutton(name);         add(button);          button.addactionlistener(new actionlistener() {             public void actionperformed(actionevent e) {                 settext("i clicked");             }         });     } } 

when button clicked, text should change "i clicked". however, don't know how access settext method. tried button.settext("i clicked") not possible.

by making reference of jbutton final, :

void makebutton(string name) {     final jbutton button =new jbutton(name);     add(button);      button.addactionlistener(new actionlistener()     {         public void actionperformed(actionevent e)         {             button.settext("i clicked");         }     }); } 

here 1 related example :

add action button created button


edit 1:

here 1 updated version of code, works mentioned before :

import java.awt.*; import java.awt.event.*; import javax.swing.*;  public class buttonexample1 extends jpanel {      private jbutton makebutton (string name) {         final jbutton button =new jbutton(name);         add(button);          button.addactionlistener(new actionlistener() {             public void actionperformed(actionevent e) {                 button.settext("i clicked");             }         });          return button;     }      private void displaygui() {         jframe frame = new jframe("button example");         frame.setdefaultcloseoperation(jframe.dispose_on_close);          jpanel contentpane = new jpanel();         contentpane.add(makebutton("one"));         contentpane.add(makebutton("two"));         contentpane.add(makebutton("three"));                 frame.setcontentpane(contentpane);           frame.pack();         frame.setlocationbyplatform(true);         frame.setvisible(true);     }      public static void main(string[] args) {         runnable runnable = new runnable() {             @override             public void run() {                 new buttonexample1().displaygui();             }         };         eventqueue.invokelater(runnable);     } } 

edit 2 :

here answer tries explain reason, why need declare final

to answer question, need understand basics, how jvm use work. when classes compiled contain inner classes, byte code gets generated not implement inner classes class within class.

why error : local variable accessed inner class, needs declare final

import java.awt.event.mouseadapter; import java.awt.event.mouseevent; import javax.swing.jmenu; import javax.swing.jpanel;  public class foo extends jpanel {     public foo()   {     final jmenu edit = new jmenu();     edit.getitem(0).addmouselistener(new mouseadapter(){      @override         public void mouseclicked(mouseevent e)          {             if (e.getclickcount() == 1) {                 edit.getitem(0).setenabled(true);             }         }      });   } } 

when compile program, 2 files created, foo.class , foo$1.class. problem comes, since second class i.e. foo$1.class doesn't know variable edit present inside first class i.e. foo.class.

so how solve problem ? jvm does, that, it makes requirement developer make variable of outer class declared final.

now being done, jvm quietly places hidden variable name val$edit inside 2nd compiled class file, here output got javap

ouput foo.class

c:\mine\java\j2se\folder>javap foo.class compiled "foo.java" public class foo extends javax.swing.jpanel {   public foo(); } 

now since, edit local constructor, hence output above.

c:\mine\java\j2se\folder>javap foo$1.class compiled "foo.java" class foo$1 extends java.awt.event.mouseadapter {   final javax.swing.jmenu val$edit;   final foo this$0;   foo$1(foo, javax.swing.jmenu);   public void mouseclicked(java.awt.event.mouseevent); } 

the variable val$edit assigned same value has been assigned edit since compiler knows value cannot changed has been declared final , hence works time.

now if change edit variable being local being instance. object of class knows variable edit, if gets changed. changing above program likewise :

import java.awt.event.mouseadapter; import java.awt.event.mouseevent; import javax.swing.jmenu; import javax.swing.jpanel;  public class foo extends jpanel {       jmenu edit = new jmenu();      public foo()     {            edit.getitem(0).addmouselistener(new mouseadapter(){          @override             public void mouseclicked(mouseevent e)              {             if (e.getclickcount() == 1) {                     edit.getitem(0).setenabled(true);                 }             }          });     } } 

here in case, not suppose declare , define being final, because in case since variable being local whole class, variable send inner class along object reference i.e. this

c:\mine\java\j2se\folder>javap foo.class compiled "foo.java" public class foo extends javax.swing.jpanel {   javax.swing.jmenu edit;   public foo(); } 

here how variable send in case i.e. this$0 :

c:\mine\java\j2se\folder>javap foo$1.class compiled "foo.java" class foo$1 extends java.awt.event.mouseadapter {   final foo this$0;   foo$1(foo);   public void mouseclicked(java.awt.event.mouseevent); } 

seems interpretation, how situation works, according me. found wonderful explanation on internet regarding mystery of accessibility in local inner classes, might understand situation in better way :-)


Comments

Popular posts from this blog

c++ - Creating new partition disk winapi -

Android Prevent Bluetooth Pairing Dialog -

VBA function to include CDATA -