рд╕рдВрдХрд▓рди рдХреЗ рджреМрд░рд╛рди рдПрдиреЛрдЯреЗрд╢рди рдХрд╛ рд╕рдВрдХрд▓рди

рдЬрд╛рджреВ рдореЗрдЯрд╛рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ рдПрдХ рдкреНрд░рдХрд╛рд░ рдХреА рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ рд╣реИ, рдЬреЛ рдкреНрд░реЛрдЧреНрд░рд╛рдореНрд╕ рдХреЗ рдирд┐рд░реНрдорд╛рдг рд╕реЗ рдЬреБрдбрд╝реА рд╣реЛрддреА рд╣реИ, рдЬреЛ рдЙрдирдХреЗ рдХрд╛рдо рдХреЗ рдкрд░рд┐рдгрд╛рдорд╕реНрд╡рд░реВрдк рдЕрдиреНрдп рдкреНрд░реЛрдЧреНрд░рд╛рдо рдЙрддреНрдкрдиреНрди рдХрд░рддреЗ рд╣реИрдВ (рд╡рд┐рд╢реЗрд╖ рд░реВрдк рд╕реЗ, рдЙрдирдХреЗ рд╕реЛрд░реНрд╕ рдХреЛрдб рдХреЗ рд╕рдВрдХрд▓рди рдЪрд░рдг рдореЗрдВ), рдпрд╛ рдРрд╕реЗ рдкреНрд░реЛрдЧреНрд░рд╛рдо рдЬреЛ рдЦреБрдж рдХреЛ рд░рдирдЯрд╛рдЗрдо рдореЗрдВ рдмрджрд▓рддреЗ рд╣реИрдВред

2004 рдореЗрдВ рдЬрд╛рд╡рд╛ 5 рдХреЗ рд░рд┐рд▓реАрдЬ рдХреЗ рд╕рд╛рде рдПрдХ рдореЗрдЯрд╛рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ рдЯреВрд▓ рдХреЗ рд░реВрдк рдореЗрдВ рдПрдиреЛрдЯреЗрд╢рди рджрд┐рдЦрд╛рдИ рджрд┐рдПред рдЙрдирдХреЗ рд╕рд╛рде, рдПрдиреЛрдЯреЗрд╢рди рдкреНрд░реЛрд╕реЗрд╕рд┐рдВрдЧ рдЯреВрд▓ рджрд┐рдЦрд╛рдИ рджрд┐рдпрд╛ , рдЬрд┐рд╕реЗ рдЬреЗрдПрд╕рдЖрд░ 269 рд╡рд┐рдирд┐рд░реНрджреЗрд╢ рдпрд╛ рдкреНрд▓рдЧ рдХрд░рдиреЗ рдпреЛрдЧреНрдп рдПрдиреЛрдЯреЗрд╢рди рдкреНрд░реЛрд╕реЗрд╕рд┐рдВрдЧ рдПрдкреАрдЖрдИ рджреНрд╡рд╛рд░рд╛ рдкреНрд░рддрд┐рд╕реНрдерд╛рдкрд┐рдд рдХрд┐рдпрд╛ рдЧрдпрд╛ рдерд╛ред рджрд┐рд▓рдЪрд╕реНрдк рдмрд╛рдд рдпрд╣ рд╣реИ рдХрд┐ рдпрд╣ рд╡рд┐рдирд┐рд░реНрджреЗрд╢ рд▓рдЧрднрдЧ 10 рд╕рд╛рд▓ рдкреБрд░рд╛рдирд╛ рд╣реИ, рд▓реЗрдХрд┐рди рдпрд╣ рдХреЗрд╡рд▓ рдПрдВрдбреНрд░реЙрдЗрдб рд╡рд┐рдХрд╛рд╕ рдореЗрдВ рдЕрдкрдиреА рд▓реЛрдХрдкреНрд░рд┐рдпрддрд╛ рд╣рд╛рд╕рд┐рд▓ рдХрд░рдирд╛ рд╢реБрд░реВ рдХрд░ рджрд┐рдпрд╛ред

рд╣рдо рдЙрди рд╕рдВрднрд╛рд╡рдирд╛рдУрдВ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдмрд╛рдд рдХрд░реЗрдВрдЧреЗ рдХрд┐ рдпрд╣ рд╡рд┐рдирд┐рд░реНрджреЗрд╢ рдереЛрдбрд╝реА рджреЗрд░ рдмрд╛рдж рдЦреБрд▓рддрд╛ рд╣реИ (рдмрд╣реБрдд рдХреЛрдб рд╣реЛрдЧрд╛), рд▓реЗрдХрд┐рди рдкрд╣рд▓реЗ, рдХреНрдпрд╛ рдЖрдк рдЬрд╛рд╡рд╛ рдХреЛрдб рдХреЛ рд╕рдВрдХрд▓рд┐рдд рдХрд░рдиреЗ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдмрд╛рдд рдХрд░рдирд╛ рдЪрд╛рд╣реЗрдВрдЧреЗ?

рдЬрд╛рд╡рд╛рдХ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдХреБрдЫ рд╢рдмреНрдж


рд╕рдВрдкреВрд░реНрдг рд╕рдВрдХрд▓рди рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдХреЛ com.sun.tools.javac рдкреИрдХреЗрдЬ рдХреЗ рдЯреВрд▓ рджреНрд╡рд╛рд░рд╛ рдирд┐рдпрдВрддреНрд░рд┐рдд рдХрд┐рдпрд╛ рдЬрд╛рддрд╛ рд╣реИ рдФрд░, OpenJDK рд╡рд┐рдирд┐рд░реНрджреЗрд╢реЛрдВ рдХреЗ рдЕрдиреБрд╕рд╛рд░, рд╕рд╛рдорд╛рдиреНрдп рд░реВрдк рд╕реЗ, рдпрд╣ рдЗрд╕ рддрд░рд╣ рджрд┐рдЦрддрд╛ рд╣реИ:

Android рдореЗрдЯрд╛рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ


рдПрдВрдбреНрд░реЙрдЗрдб рдбреЗрд╡рд▓рдкрдореЗрдВрдЯ рдореЗрдВ рдореЗрдЯрд╛рдкреНрд░реЛрдЧреНрд░рд╛рдорд┐рдВрдЧ рд╣рдореЗрдВ рдХрд╣рд╛рдВ рдорджрдж рдХрд░ рд╕рдХрддрд╛ рд╣реИ? рдЖрдк рдореЗрдВ рд╕реЗ рдмрд╣реБрдд рд╕реЗ рд▓реЛрдЧ рдЗрд╕ рдкреНрд░рд╢реНрди рдХрд╛ рдЙрддреНрддрд░ рдкрд╣рд▓реЗ рд╕реЗ рд╣реА рдЬрд╛рдирддреЗ рд╣реИрдВ - рдпрд╣ рдкреБрд╕реНрддрдХрд╛рд▓рдпреЛрдВ рдХреА рдПрдХ рдкрд░реНрдпрд╛рдкреНрдд рд╕рдВрдЦреНрдпрд╛ рд╣реИ рдЬреЛ рдХрд┐рд╕реА рддрд░рд╣ рдШрдЯрдХреЛрдВ рдХреЛ рдЗрдВрдЬреЗрдХреНрд╢рди рд▓рдЧрд╛рдиреЗ, рд╢реНрд░реЛрддрд╛рдУрдВ рдХреЛ рд╕реНрдерд╛рдкрд┐рдд рдХрд░рдиреЗ, рдФрд░ рдмрд╣реБрдд рдХреБрдЫ рдкреНрд░рджрд╛рди рдХрд░рддреЗ рд╣реИрдВред
public class MainActivity extends AppCompatActivity { @Bind(R.id.fab) private FloatingActionButton mFab; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.ac_main); mFab.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { } }); ButterKnife.bind(this); } } 

рдЗрд╕ рдХреЛрдб рдореЗрдВ рдХреНрдпрд╛ рд╕рдорд╕реНрдпрд╛рдПрдВ рд╣реИрдВ? рд╕рдмрд╕реЗ рдкрд╣рд▓реЗ, рд╡рд╣ рдПрдХ рд╕рд╛рде рдирд╣реАрдВ рдорд┐рд▓реЗрдЧрд╛! рд╕рдВрдХрд▓рди рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдПрдХ рддреНрд░реБрдЯрд┐ рд╕реЗ рдмрд╛рдзрд┐рдд рд╣реЛрдЧреА
 Error:(15, 34) error: @Bind fields must not be private or static. (moscow.droidcon2015.activity.MainActivity.mFab) 

рдорд╣рд╛рди, рдирд┐рдЬреА рдирд┐рдХрд╛рд▓реЗрдВ рдФрд░ рд╡рд╣, рдХреЛрдб рд╕рдВрдХрд▓рд┐рдд рд╣реИред рд▓реЗрдХрд┐рди, рдЗрд╕рдХреЗ рдЕрд▓рд╛рд╡рд╛, рд╣рдо OOP рдХреЗ рдореВрд▓ рд╕рд┐рджреНрдзрд╛рдВрддреЛрдВ рдореЗрдВ рд╕реЗ рдПрдХ рдХрд╛ рдЙрд▓реНрд▓рдВрдШрди рдХрд░рддреЗ рд╣реИрдВ - рдЗрдирдХреИрдкреНрд╕реБрд▓реЗрд╢рди ред рджреВрд╕рд░реЗ, рд╕реНрдЯрд╛рд░реНрдЯрдЕрдк рдкрд░, рдПрдкреНрд▓рд┐рдХреЗрд╢рди рдПрдирдкреАрдИ рдХреЗ рд╕рд╛рде рджреБрд░реНрдШрдЯрдирд╛рдЧреНрд░рд╕реНрдд рд╣реЛ рдЬрд╛рдПрдЧрд╛, рдХреНрдпреЛрдВрдХрд┐ рдПрдордлреИрдм рдХреНрд╖реЗрддреНрд░ рдХреЛ рдЗрдирд┐рд╢рд┐рдпрд▓рд╛рдЗрдЬрд╝ рдХрд┐рдпрд╛ рдЬрд╛рддрд╛ рд╣реИ рдЬрдм рдмрдЯрд░рдХрд╛рдЗрдиреА.рдмрд╛рдЗрдВрдб (рдпрд╣) рдХрд╣рд╛ рдЬрд╛рддрд╛ рд╣реИред рддреАрд╕рд░рд╛, рдкреНрд░реЛрдЧрд╛рд░реНрдб рдмрдЯрд░рдХрдиреАрдл рд▓рд╛рдЗрдмреНрд░реЗрд░реА рджреНрд╡рд╛рд░рд╛ рдЙрддреНрдкрдиреНрди рд╡рд░реНрдЧреЛрдВ рдореЗрдВ рдХрдЯреМрддреА рдХрд░ рд╕рдХрддрд╛ рд╣реИред рдЖрдк рдХрд╣ рд╕рдХрддреЗ рд╣реИрдВ рдХрд┐ рдпреЗ рд╕рднреА рджреВрд░ рдХреА рд╕рдорд╕реНрдпрд╛рдПрдБ рд╣реИрдВ рдФрд░ рдпреЗ рд╕рднреА рдкрд╛рдБрдЪ рдорд┐рдирдЯ рдореЗрдВ рд╣рд▓ рд╣реЛ рдЬрд╛рддреА рд╣реИрдВред рдмреЗрд╢рдХ, рдпрд╣ рд╕рдЪ рд╣реИ, рд▓реЗрдХрд┐рди рдЗрди рд╕рдВрднрд╛рд╡рд┐рдд рд╕рдорд╕реНрдпрд╛рдУрдВ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рд╕реЛрдЪрдиреЗ рдХреА рдЬрд░реВрд░рдд рд╕реЗ рдЦреБрдж рдХреЛ рджреВрд░ рдХрд░рдирд╛ рдмрд╣реБрдд рдЕрдЪреНрдЫрд╛ рд╣реЛрдЧрд╛ред

рдЖрдЧреЗ рдмрдврд╝реЛ! рднрд╛рд░реА рдкрджрд╛рд░реНрдереЛрдВ рдХреЗ рд▓рд┐рдП!


рддреЛ, рдЪрд▓реЛ рдкрд╣рд┐рдпрд╛ рдХреЛ рдлрд┐рд░ рд╕реЗ рд╢реБрд░реВ рдХрд░рдирд╛ рд╢реБрд░реВ рдХрд░реЗрдВ! рдкрд╣рд▓реА рдЪреАрдЬ рдЬрд┐рд╕рдХреА рд╣рдореЗрдВ рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ, рд╡рд┐рдЪрд┐рддреНрд░ рд░реВрдк рд╕реЗ рдкрд░реНрдпрд╛рдкреНрдд рд╣реИ, рд╡рд╣ рдПрдиреЛрдЯреЗрд╢рди рд╣реА рд╣реИ, рдЬрд┐рд╕реЗ рд╣рдо рдмрд╛рдж рдореЗрдВ рдкреНрд░реЛрд╕реЗрд╕ рдХрд░реЗрдВрдЧреЗ:
 @Retention(RetentionPolicy.SOURCE) @Target({ElementType.FIELD}) public @interface BindView { int value(); } 

RetentionPolicy.SOURCE рдХрд╛ рдЕрд░реНрде рд╣реИ рдХрд┐ рдпрд╣ рдПрдиреЛрдЯреЗрд╢рди рдХреЗрд╡рд▓ рд╕реНрд░реЛрдд рдХреЛрдб (рдЬреЛ рд╣рдореЗрдВ рдкреВрд░реА рддрд░рд╣ рд╕реЗ рд╕реВрдЯ рдХрд░рддрд╛ рд╣реИ) рдореЗрдВ рдЙрдкрд▓рдмреНрдз рд╣реИ рдФрд░ рдЖрдк рдЗрд╕реЗ рдкреНрд░рддрд┐рдмрд┐рдВрдм рдХреЗ рдорд╛рдзреНрдпрдо рддрдХ рдирд╣реАрдВ рдкрд╣реБрдВрдЪрд╛ рдкрд╛рдПрдВрдЧреЗред ElementType.FIELD рдХрд╛ рдХрд╣рдирд╛ рд╣реИ рдХрд┐ рдПрдиреЛрдЯреЗрд╢рди рдХреЗрд╡рд▓ рд╡рд░реНрдЧ рдХреЗ рдХреНрд╖реЗрддреНрд░реЛрдВ рдкрд░ рд▓рд╛рдЧреВ рд╣реЛрддрд╛ рд╣реИред

рдЕрдЧрд▓рд╛, рд╣рдореЗрдВ рд╕реНрд╡рдпрдВ рдкреНрд░реЛрд╕реЗрд╕рд░ рдмрдирд╛рдиреЗ рдФрд░ рдЗрд╕реЗ рдПрдХ рд╡рд┐рд╢реЗрд╖ рдлрд╝рд╛рдЗрд▓ рдореЗрдВ рдкрдВрдЬреАрдХреГрдд рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ:
 src/main/resources/META-INF.services/javax.annotation.processing.Processor 
рдЗрд╕ рдлрд╝рд╛рдЗрд▓ рдХреА рд╕рд╛рдордЧреНрд░реА рдПрдХ рдПрдХрд▓ рдкрдВрдХреНрддрд┐ рд╣реИ рдЬрд┐рд╕рдореЗрдВ рдХрдиреЗрдХреНрдЯреЗрдб рдкреНрд░реЛрд╕реЗрд╕рд░ рдХреЗ рдкреВрд░реА рддрд░рд╣ рд╕реЗ рдпреЛрдЧреНрдп рд╡рд░реНрдЧ рдХрд╛ рдирд╛рдо рд╣реИ:
 moscow.droidcon2015.processor.DroidConProcessor 

DroidConProcessor.java
 @SupportedAnnotationTypes({"moscow.droidcon2015.processor.BindView"}) public class DroidConProcessor extends AbstractProcessor { private final Map<TypeElement, BindViewVisitor> mVisitors = new HashMap<>(); @Override public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) { if (annotations.isEmpty()) { return false; } final Set<? extends Element> elements = roundEnv.getElementsAnnotatedWith(BindView.class); for (final Element element : elements) { // element == MainActivity.mFab final TypeElement object = (TypeElement) element.getEnclosingElement(); // object == MainActivity BindViewVisitor visitor = mVisitors.get(object); if (visitor == null) { visitor = new BindViewVisitor(processingEnv, object); mVisitors.put(object, visitor); } element.accept(visitor, null); } for (final BindViewVisitor visitor : mVisitors.values()) { visitor.brewJava(); } return true; } @Override public SourceVersion getSupportedSourceVersion() { return SourceVersion.latestSupported(); } } 


рд╡рд┐рд░реЛрдзрд╛рднрд╛рд╕ рдЬреИрд╕рд╛ рдХрд┐ рдпрд╣ рд▓рдЧ рд╕рдХрддрд╛ рд╣реИ, рд╣рдо рдкреНрд░реЛрд╕реЗрд╕рд░ рдХреЛ рдПрдХ рдПрдиреЛрдЯреЗрд╢рди рдХреЗ рд╕рд╛рде рдЪрд┐рд╣реНрдирд┐рдд рдХрд░рддреЗ рд╣реИрдВ, рдЬреЛ рдЗрдВрдЧрд┐рдд рдХрд░рддрд╛ рд╣реИ рдХрд┐ рдкреНрд░реЛрд╕реЗрд╕рд░ рдХрд┐рд╕ рдПрдиреЛрдЯреЗрд╢рди рдХреЛ рд╕рдВрд╕рд╛рдзрд┐рдд рдХрд░ рд╕рдХрддрд╛ рд╣реИред рдпрд╣ рдЕрдиреБрдорд╛рди рд▓рдЧрд╛рдирд╛ рдХрдард┐рди рдирд╣реАрдВ рд╣реИ рдХрд┐ рдореБрдЦреНрдп рд╡рд┐рдзрд┐ рдкреНрд░рдХреНрд░рд┐рдпрд╛ рд╡рд┐рдзрд┐ рд╣реИред рдкрд╣рд▓рд╛ рдкреИрд░рд╛рдореАрдЯрд░ рд╣рдорд╛рд░реЗ рдкреНрд░реЛрд╕реЗрд╕рд░ рджреНрд╡рд╛рд░рд╛ рд╕рдорд░реНрдерд┐рдд рд╕реВрдЪреА рд╕реЗ рдмрд╣реБрдд рд╕рд╛рд░реЗ рдПрдиреЛрдЯреЗрд╢рди рд╣реИрдВ, рдЬрд┐рдиреНрд╣реЗрдВ рд╕рдВрдХрд▓рди рдХреЗ рдкрд╣рд▓реЗ рджреЛ рдЪрд░рдгреЛрдВ рдореЗрдВ рдЦреЛрдЬрд╛ рдЧрдпрд╛ рдерд╛ред рджреВрд╕рд░рд╛ рдкреИрд░рд╛рдореАрдЯрд░ рд╕рдВрдХрд▓рдХ рд╡рд╛рддрд╛рд╡рд░рдг рд╣реИред рдПрдХ рдЕрдЪреНрдЫреЗ рддрд░реАрдХреЗ рд╕реЗ, рд╡рд┐рдзрд┐ рдХреЗ рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди рдореЗрдВ, рд╣рдореЗрдВ рдПрдиреЛрдЯреЗрд╢рди рдХреЗ рдкреВрд░реЗ рд╕реЗрдЯ рдХреЗ рдорд╛рдзреНрдпрдо рд╕реЗ рдЬрд╛рдирд╛ рд╣реЛрдЧрд╛ рдФрд░ рдЙрди рд╕рднреА рдХреЛ рд╕рдВрд╕рд╛рдзрд┐рдд рдХрд░рдирд╛ рд╣реЛрдЧрд╛, рд▓реЗрдХрд┐рди рдЗрд╕ рдорд╛рдорд▓реЗ рдореЗрдВ, рдкреНрд░реЛрд╕реЗрд╕рд░ рдХреЗрд╡рд▓ рдПрдХ рд╣реА рдПрдиреЛрдЯреЗрд╢рди рдХрд╛ рд╕рдорд░реНрдерди рдХрд░рддрд╛ рд╣реИ, рдЗрд╕рд▓рд┐рдП рд╣рдо рдЗрд╕реЗ "рдорд╛рдереЗ" рд╕рдВрд╕рд╛рдзрд┐рдд рдХрд░реЗрдВрдЧреЗред рдЪрд░рдгреЛрдВ рдореЗрдВ рдкреНрд░рдХреНрд░рд┐рдпрд╛ рд╡рд┐рдзрд┐ рдкрд░ рд╡рд┐рдЪрд╛рд░ рдХрд░реЗрдВ:

BindViewVisitor.java
 public class BindViewVisitor extends ElementScanner7<Void, Void> { private final CodeBlock.Builder mFindViewById = CodeBlock.builder(); private final Trees mTrees; private final Messager mLogger; private final Filer mFiler; private final TypeElement mOriginElement; private final TreeMaker mTreeMaker; private final Names mNames; public BindViewVisitor(ProcessingEnvironment env, TypeElement element) { super(); mTrees = Trees.instance(env); mLogger = env.getMessager(); mFiler = env.getFiler(); mOriginElement = element; final JavacProcessingEnvironment javacEnv = (JavacProcessingEnvironment) env; mTreeMaker = TreeMaker.instance(javacEnv.getContext()); mNames = Names.instance(javacEnv.getContext()); } } 


рдЕрдм рдЖрдЗрдП рдЙрд╕ рд╡рд░реНрдЧ рдХреЛ рджреЗрдЦреЗрдВ рдЬрд┐рд╕рдореЗрдВ рд╕рднреА рдореБрдЦреНрдп рдХрд╛рд░реНрдп рдХрд┐рдП рдЬрд╛рддреЗ рд╣реИрдВред рдкрд╣рд▓реА рдмрд╛рдд рдпрд╣ рд╣реИ рдХрд┐ рдЖрдВрдЦреЛрдВ рдХреА рд▓рдЯреЗрдВ рдПрд▓реАрдореЗрдВрдЯрд╕реЗрдирд░ 7 рд╣реИрдВ ред рдпрд╣ ElementVisitor рдЗрдВрдЯрд░рдлрд╝реЗрд╕ рдХрд╛ рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди рд╣реИ, рдФрд░ 7 рдЙрд╕ JDK рдХрд╛ рдиреНрдпреВрдирддрдо рд╕рдВрд╕реНрдХрд░рдг рд╣реИ рдЬрд┐рд╕рдХрд╛ рд╣рдо рдЙрдкрдпреЛрдЧ рдХрд░рдирд╛ рдЪрд╛рд╣рддреЗ рд╣реИрдВред рдЖрдЗрдП рдЦреЗрддреЛрдВ рдХреЗ рдорд╛рдзреНрдпрдо рд╕реЗ рдЬрд╛рдПрдВ (рдЙрдирдХреЗ рдкреНрд░рдХрд╛рд░реЛрдВ рд╕реЗ рдЕрдзрд┐рдХ рд╕рдЯреАрдХ):

рдЬреИрд╕рд╛ рдХрд┐ рдЖрдкрдХреЛ рдпрд╛рдж рд╣реИ, рд╣рдордиреЗ рдХреНрд▓рд╛рд╕ рдлреАрд▓реНрдб рдореЗрдВ рдПрд▓рд┐рдореЗрдВрдЯрд╡рд┐рдЬрд╝рд┐рдЯрд░ рд▓рд╛рдЧреВ рдХрд┐рдпрд╛, рдЗрд╕рд▓рд┐рдП рд╡рд╣ рд╡рд┐рдзрд┐ рдЬреЛ рд╣рдореЗрдВ рд░реБрдЪрддреА рд╣реИ
visitVariable
  @Override public Void visitVariable(VariableElement field, Void aVoid) { ((JCTree) mTrees.getTree(field)).accept(new TreeTranslator() { @Override public void visitVarDef(JCTree.JCVariableDecl jcVariableDecl) { super.visitVarDef(jcVariableDecl); jcVariableDecl.mods.flags &= ~Flags.PRIVATE; } }); final BindView bindView = field.getAnnotation(BindView.class); mFindViewById.addStatement("(($T) this).$L = ($T) findViewById($L)", ClassName.get(mOriginElement), field.getSimpleName(), ClassName.get(field.asType()), bindView.value()); return super.visitVariable(field, aVoid); } 


рдЖрдЧреЗ рдХреНрдпрд╛ рд╣реЛрдЧрд╛ рдпрд╣ рд╕рдордЭрдиреЗ рдХреЗ рд▓рд┐рдП рдПрдХ рдЫреЛрдЯрд╛ рд╡рд┐рд╖рдпрд╛рдВрддрд░: javax.lang.model.element (VariableElement, TypeElement, рдЖрджрд┐) рд╕реЗ рдХрдХреНрд╖рд╛рдПрдВ рд╣реИрдВ, рдЪрд▓реЛ рдХрд╣рддреЗ рд╣реИрдВ, рдПрдПрд╕рдЯреА рдкрд░ рдПрдХ рдЙрдЪреНрдЪ-рд╕реНрддрд░реАрдп рдЕрдореВрд░реНрддрддрд╛ред рдЯреНрд░реАрдЬрд╝ рдХреНрд▓рд╛рд╕ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рддреЗ рд╣реБрдП, рд╣рдо рдПрдХ рдирд┐рдореНрди-рд╕реНрддрд░реАрдп рдЕрдореВрд░реНрддрддрд╛ рдкреНрд░рд╛рдкреНрдд рдХрд░рддреЗ рд╣реИрдВ, рдЙрд╕ рдкрд░ рдЯреНрд░реА-рд╡рд┐рдЬрд┐рдЯрд░ рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди рдирд┐рд░реНрдзрд╛рд░рд┐рдд рдХрд░рддреЗ рд╣реИрдВ, рдФрд░ рд╡рд┐рдЬрд┐рдЯрд╡рд░реНрдл рдкрджреНрдзрддрд┐ рдореЗрдВ рдорд┐рд▓рддреЗ рд╣реИрдВ, рдЬрд┐рд╕рдХреЗ рдорд╛рдкрджрдВрдбреЛрдВ рдореЗрдВ рд╣рдорд╛рд░реЗ рдХреНрд╖реЗрддреНрд░ рдХрд╛ рдПрдПрд╕рдЯреА рдкреНрд░рддрд┐рдирд┐рдзрд┐рддреНрд╡ ( JCTree.JCVariableDl ) рд╢рд╛рдорд┐рд▓ рд╣реИред рдлрд┐рд░ рдЧрдВрджреЗ рд╣реИрдХ - рд╣рдо рдирд┐рдЬреА рдЭрдВрдбреЗ рдХреЛ рдореИрджрд╛рди рд╕реЗ рд╣рдЯрд╛ рджреЗрддреЗ рд╣реИрдВред рд╣рд╛рдВ, рд╣рд╛рдВ, рд╣рдо рдПрдирдХреИрдкреНрд╕реБрд▓реЗрд╢рди рдХреЗ рд╕рд┐рджреНрдзрд╛рдВрдд рдХрд╛ рдЙрд▓реНрд▓рдВрдШрди рдХрд░рддреЗ рд╣реИрдВ, рд▓реЗрдХрд┐рди рд╣рдо рдЗрд╕реЗ рдХрдВрдкрд╛рдЗрд▓рд░ рд╕реНрддрд░ рдкрд░ рдХрд░рддреЗ рд╣реИрдВ (рдЬрд╣рд╛рдВ рд╣рдо рдкрд╣рд▓реЗ рд╕реЗ рд╣реА, рд╕рд┐рджреНрдзрд╛рдВрдд рд░реВрдк рдореЗрдВ, рдмрдЧрд╝рд▓ рдореЗрдВ рдХреНрдпрд╛ рд╣реЛрддрд╛ рд╣реИ)ред рд╕реНрд░реЛрдд рдХреЛрдб рд╕реНрддрд░ рдкрд░ рдПрдирдХреИрдкреНрд╕реБрд▓реЗрд╢рди рдХреЛ рд╕рдВрд░рдХреНрд╖рд┐рдд рдХрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ: рдЖрдИрдбреАрдИ рдЖрдкрдХреЛ рдмрд╛рд╣рд░ рд╕реЗ рдХреНрд╖реЗрддреНрд░ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдиреЗ рдХреА рдЕрдиреБрдорддрд┐ рдирд╣реАрдВ рджреЗрдЧрд╛, рдФрд░ рд╕реНрдереИрддрд┐рдХ рд╡рд┐рд╢реНрд▓реЗрд╖рдХ рд╢рд╛рдВрддрд┐ рд╕реЗ рд░рд┐рдкреЛрд░реНрдЯ рдХрд░реЗрдВрдЧреЗ рдХрд┐ рдЗрд╕ рдХреНрд╖реЗрддреНрд░ рдХреЗ рд╕рд╛рде рдХреЛрдИ рд╕рдорд╕реНрдпрд╛ рдирд╣реАрдВ рд╣реИред рдлрд╝реАрд▓реНрдб рдкреНрд░рд╛рд░рдВрдн рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП CodeBlock.Builder рдореЗрдВ рдПрдХ рдЕрднрд┐рд╡реНрдпрдХреНрддрд┐ рдЬреЛрдбрд╝реЗрдВ рдФрд░ рдпрд╣ рдмрд╛рдд рд╣реИред

рд╕реНрд░реЛрдд рдХреЛрдб рдлрд╝рд╛рдЗрд▓ рдЬрдирд░реЗрдЯ рдХрд░реЗрдВ


рд╣рдордиреЗ рдЕрдкрдиреА рдХрдХреНрд╖рд╛ рдХреЗ рд╕рднреА рдХреНрд╖реЗрддреНрд░реЛрдВ рдХрд╛ рджреМрд░рд╛ рдХрд░рдиреЗ рдХреЗ рдмрд╛рдж, рд╕реНрд░реЛрдд рдХреЛрдб рдлрд╝рд╛рдЗрд▓ рдЙрддреНрдкрдиреНрди рдХрд░рдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реИред
brewJava
  public void brewJava() { final TypeSpec typeSpec = TypeSpec.classBuilder(mOriginElement.getSimpleName() + "$$Proxy") // MainActivity$$Proxy .addModifiers(Modifier.ABSTRACT) .superclass(ClassName.get(mOriginElement.getSuperclass())) // extends AppCompatActivity .addOriginatingElement(mOriginElement) .addMethod(MethodSpec.methodBuilder("setContentView") .addAnnotation(Override.class) .addModifiers(Modifier.PUBLIC) .addParameter(TypeName.INT, "layoutResId") .addStatement("super.setContentView(layoutResId)") .addCode(mFindViewById.build()) // findViewById... .build()) .build(); final JavaFile javaFile = JavaFile.builder(mOriginElement.getEnclosingElement().toString(), typeSpec) .addFileComment("Generated by DroidCon processor, do not modify") .build(); try { final JavaFileObject sourceFile = mFiler.createSourceFile( javaFile.packageName + "." + typeSpec.name, mOriginElement); try (final Writer writer = new BufferedWriter(sourceFile.openWriter())) { javaFile.writeTo(writer); } // TODO: MAGIC } catch (IOException e) { mLogger.printMessage(Diagnostic.Kind.ERROR, e.getMessage(), mOriginElement); } } 


рд╕реНрд░реЛрдд рдХреЛрдб рдЬрдирд░реЗрдЯ рдХрд░рдиреЗ рдХрд╛ рд╕рд╛рд░рд╛ рдХрд╛рдо javapoet рд▓рд╛рдЗрдмреНрд░реЗрд░реА рдиреЗ рд▓рд┐рдпрд╛ред рдмреЗрд╢рдХ, рдХреЛрдИ рднреА рдЗрд╕рдХреЗ рдмрд┐рдирд╛ рдХрд░ рд╕рдХрддрд╛ рдерд╛, рд▓реЗрдХрд┐рди рддрдм рдкреВрд░реЗ рд╕реНрд░реЛрдд рдХреЛрдб рдХреЛ рдореИрдиреНрдпреБрдЕрд▓ рд░реВрдк рд╕реЗ рд╕реНрдЯреНрд░рд┐рдВрдЧ рдХреЙрдиреНрдлреИрдиреЗрдЯреЗрд╢рди рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдХреЗ рдЙрддреНрдкрдиреНрди рдХрд░рдирд╛ рд╣реЛрдЧрд╛, рдЬреЛ рдХрд┐ рдЖрдк рджреЗрдЦрддреЗ рд╣реИрдВ, рдмрд╣реБрдд рд╕реБрд╡рд┐рдзрд╛рдЬрдирдХ рдирд╣реАрдВ рд╣реИред рдЗрд╕ рдмрд┐рдВрджреБ рдкрд░, рдмрдЯрд░рдХрдиреАрдлрд╝ рдЬреИрд╕реЗ рдкреБрд╕реНрддрдХрд╛рд▓рдпреЛрдВ рдХреЗ рд╕рднреА рдирд┐рд░реНрдорд╛рддрд╛ рдЦрддреНрдо рд╣реЛ рдЬрд╛рддреЗ рд╣реИрдВ ред рд╣рдореЗрдВ рдПрдХ рдХреНрд▓рд╛рд╕ рдлрд╛рдЗрд▓ рдорд┐рд▓реА, рдЬрд┐рд╕реЗ рд╣рдо рдлрд┐рд░ рд░рд┐рдлреНрд▓реЗрдХреНрд╢рди рдХреА рдорджрдж рд╕реЗ рдвреВрдВрдврддреЗ рд╣реИрдВ рдФрд░ рдЗрд╕рдХреА рдорджрдж рд╕реЗ рд╣рдо рд╕рдВрдмрдВрдзрд┐рдд рд╡рд┐рдзрд┐ рдХреЛ рдЦреАрдВрдЪрддреЗ рд╣реИрдВ, рдЬреЛ рдЙрдкрдпреЛрдЧреА рдХрд╛рдо рдХрд░рддрд╛ рд╣реИред рд▓реЗрдХрд┐рди рдореИрдВрдиреЗ рд╡рд╛рджрд╛ рдХрд┐рдпрд╛ рдХрд┐ рд╣рдо рдЗрд╕ рдЬрд╝рд░реВрд░рдд рд╕реЗ рдЫреБрдЯрдХрд╛рд░рд╛ рдкрд╛ рд▓реЗрдВрдЧреЗ!

рд╣рдореЗрдВ рдФрд░ рдЧрд╣рд░реЗ рдЬрд╛рдиреЗ рдХреА рдЬрд░реВрд░рдд рд╣реИ!


TODO: рдЬрд╛рджреВ
 JCTree.JCExpression selector = mTreeMaker.Ident(mNames.fromString(javaFile.packageName)); selector = mTreeMaker.Select(selector, mNames.fromString(typeSpec.name)); ((JCTree.JCClassDecl) mTrees.getTree(mOriginElement)).extending = selector; 


рд╣рд╛рдБ! рддреАрди рд▓рд╛рдЗрдиреЗрдВред рдЙрдирдореЗрдВ рдХреНрдпрд╛ рд╣реЛрддрд╛ рд╣реИ:

рдПрдХ рдФрд░ рднреА рд╕рд░рд▓ рднрд╛рд╖рд╛ рдореЗрдВ - рд╣рдо рдЙрддреНрдкрдиреНрди рд╡рд░реНрдЧ рдХреЛ рд╡рдВрд╢рд╛рдиреБрдЧрдд рдкрджрд╛рдиреБрдХреНрд░рдо рдореЗрдВ рдПрдореНрдмреЗрдб рдХрд░рддреЗ рд╣реИрдВ:
 MainActivity extends MainActivity$$Proxy extends AppCompatActivity 

MainActivity $$ Proxy.java
 // Generated by DroidCon processor, do not modify package moscow.droidcon2015.activity; import android.support.design.widget.FloatingActionButton; import android.support.v7.app.AppCompatActivity; import java.lang.Override; abstract class MainActivity$$Proxy extends AppCompatActivity { @Override public void setContentView(int layoutResId) { super.setContentView(layoutResId); ((MainActivity) this).mFab = (FloatingActionButton) findViewById(2131492965); } } 


MainActivity.class (рд╡рд┐рдШрдЯрд┐рдд)
 // // Source code recreated from a .class file by IntelliJ IDEA // (powered by Fernflower decompiler) // package moscow.droidcon2015.activity; import android.os.Bundle; import android.support.design.widget.FloatingActionButton; import android.view.View; import android.view.View.OnClickListener; import moscow.droidcon2015.activity.MainActivity$$Proxy; public class MainActivity extends MainActivity$$Proxy { FloatingActionButton mFab; public MainActivity() { } protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); this.setContentView(2130968600); this.mFab.setOnClickListener(new OnClickListener() { public void onClick(View v) { } }); } } 



рдирд┐рд╖реНрдХрд░реНрд╖


рджреБрд░реНрднрд╛рдЧреНрдп рд╕реЗ, рдПрдХ рд▓реЗрдЦ рдХреЗ рдврд╛рдВрдЪреЗ рдХреЗ рднреАрддрд░ рдПрдиреЛрдЯреЗрд╢рди рдкреНрд░реЛрд╕реЗрд╕рд┐рдВрдЧ рдХреА рд╕рднреА рдкреЗрдЪреАрджрдЧрд┐рдпреЛрдВ рдФрд░ com.sun.tools.javac рдХреЗ рдЕрдВрджрд░ рдЭреВрда рдмреЛрд▓рдиреЗ рд╡рд╛рд▓реЗ рдЦрдЬрд╛рдиреЗ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдмрддрд╛рдирд╛ рдЕрд╕рдВрднрд╡ рд╣реИ ред * ред рдЗрд╕рд╕реЗ рднреА рдЕрдзрд┐рдХ рдкрд░реЗрд╢рд╛рди рдХрд░рдиреЗ рд╡рд╛рд▓реА рдмрд╛рдд рдпрд╣ рд╣реИ рдХрд┐ рдЗрди рдЦрдЬрд╛рдиреЗ рдкрд░ рдХрд┐рд╕реА рднреА рджрд╕реНрддрд╛рд╡реЗрдЬ рдХреА рдкреВрд░реА рдХрдореА рд╣реИ рдФрд░ рд░рд┐рд▓реАрдЬ рдХреЗ рдмреАрдЪ рд╕рдВрдЧрддрддрд╛ рдХреА рдХрдореА рд╣реИред рдЗрд╕рдХреЗ рдмрд╛рдж, рдбрд░рд╛рд╡рдиреЗ рд╢рдмреНрджреЛрдВ рдХреЛ рд╕реБрдирд╛ рдЬрд╛рдПрдЧрд╛: java7 рдФрд░ java8 рд╕рдВрдХрд▓рдХ рдХреЗ рд▓рд┐рдП рд╕рдорд░реНрдерди рдкреНрд░рджрд╛рди рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рд╕рдВрдХрд▓рди рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдореЗрдВ рдкреНрд░рддрд┐рдмрд┐рдВрдм рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реЛрдЧрд╛! рдЗрд╕рд╕реЗ рдПрдХ рдЯреНрд╡рд┐рд╕реНрдЯ рд╣реИ! рд╕рдЪ? рд▓реЗрдХрд┐рди рдПрдХ рдмрд╛рд░ рдлрд┐рд░, рдпрд╣ рдХреЗрд╡рд▓ com.sun.tools.javac рдкрд░ рд▓рд╛рдЧреВ рд╣реЛрддрд╛ рд╣реИред

DroidCon рдкрд░ рдЖрдзрд╛рд░рд┐рдд рд╣реИ


рдкреНрд░рд╕реНрддреБрддрд┐ рдХреЗ рдорд╛рдзреНрдпрдо рд╕реЗ рдлрд╝реНрд▓рд┐рдк рдХрд░рддреЗ рд╣реБрдП рд▓реЗрдЦ рдХреЛ рдкрдврд╝рдирд╛ рдЕрдзрд┐рдХ рд╕реБрд╡рд┐рдзрд╛рдЬрдирдХ рд╣реИред
рдпрд╣рд╛рдВ рдкреНрд░реЛрдЬреЗрдХреНрдЯ рд░рд┐рдкреЛрдЬрд┐рдЯрд░реАред

рд╕рд╡рд╛рд▓реЛрдВ рдХреЗ рдЬрд╡рд╛рдм:


рдЕрдзрд┐рдХ рдХрдЯреНрдЯрд░!


visitMethodDef
 @Override public void visitMethodDef(JCTree.JCMethodDecl methodDecl) { super.visitMethodDef(methodDecl); methodDecl.body.stats = com.sun.tools.javac.util.List.<JCTree.JCStatement>of( mTreeMaker.Try( mTreeMaker.Block(0, methodDecl.body.stats), com.sun.tools.javac.util.List.<JCTree.JCCatch>nil(), mTreeMaker.Block(0, com.sun.tools.javac.util.List.<JCTree.JCStatement>of( mTreeMaker.Exec(mTreeMaker.Apply( com.sun.tools.javac.util.List.<JCTree.JCExpression>nil(), ident(mPackageName, mHelperClassName, "update"), com.sun.tools.javac.util.List.of( mTreeMaker.Literal(TypeTag.CLASS, mColumnName), mTreeMaker.Select(mTreeMaker.Ident(mNames._this), mNames.fromString(mFieldName)), mTreeMaker.Select(mTreeMaker.Ident(mNames._this), mNames.fromString(mPrimaryKey.call())) ) )) )) ) ); } 


рдпрд╣рд╛рдВ рдкрд╣рд▓реА рдирдЬрд╝рд░ рдореЗрдВ рдРрд╕рд╛ рднрдпрд╛рдирдХ рдХреЛрдб рд╣реИ, рдпрд╣ рдХреЗрд╡рд▓ рд╕реЗрдЯрд░ рд╡рд┐рдзрд┐ рдХреЗ рдХреЛрдб рдХреЛ рд╕рдВрд╢реЛрдзрд┐рдд рдХрд░рддрд╛ рд╣реИ рддрд╛рдХрд┐ рдбреЗрдЯрд╛рдмреЗрд╕ рдореЗрдВ рддреБрд░рдВрдд рдкрд░рд┐рд╡рд░реНрддрди рд▓рд┐рдЦрд╛ рдЬрд╛рдПред

рдкрддрд▓реВрди рдЖрд╕рд╛рдиреА рд╕реЗ рдмрд╛рд░реА ...
 //  public void setText(String text) { mText = text; } //  public void setText(String text) { try { this.mText = text; } finally { Foo$$SQLiteHelper.update("text", this.mText, this.mId); } } 



рд╕реВрддреНрд░реЛрдВ рдХрд╛ рдХрд╣рдирд╛ рд╣реИ


Source: https://habr.com/ru/post/In206208/


All Articles