This article has participated in the “Digitalstar Project” and won a creative gift package to challenge the creative incentive money.

This article has launched the first wechat public account “Code Xiaosheng”, you can search for attention, focus on Android technology sharing.

Necessary instructions

This article is only a case demonstration, easy to learn and master the basic knowledge, not source level exploration. Let’s first clarify the functions that can be realized and the technical points used and the environment.

Technical points:

  • Multi-module project, including Base ELIb, main APP and multi-business Module
  • Multiple modules, to achieve a module can run independently
  • To jump between modules, use the ARouter framework
  • The ARouter interceptor is used

Environment:

  • Android Studio4.1.2
  • Language: the Java
  • Phone: Samsung A6s Android10

Routing Application Scenarios

The development of Android project structure tends to be more and more multi-module, and the jump between modules will grow with the development of the project if the Intent jump is used, which will eventually lead to complex import XXX, which will bring great trouble to maintenance, as shown in the following figure:

Black lines: Indicates dependencies. With dependencies, you can reference another module’s class in the current module, so you can jump with an Intent.

Blue line: indicates that to jump to a page of login, Live and Work modules from app module, you must rely on the corresponding module to reference to relevant classes, so as to realize the jump. Red line: Business needs, the work module can directly enter the live broadcast room, so the work module must rely on the live module; And vice versa. Green line: when the user does not login, or the login status is invalid, or the account is logged in elsewhere, the user needs to jump from the current module to the login module, so the other basic modules rely on the login module.

As the functionality of the project expands, the problems become apparent.

And the emergence of ARouter is very good solve the problem, website address: https://github.com/alibaba/ARouter/, its function is very strong, for more module project, no matter whether componentization, with good performance are mutually dependent and jump of maintenance costs. Here is a simple diagram:

Black line: represents dependencies, where the dependency resolves resource sharing issues rather than jumps. If you are not using the resources in Baselib, there is no dependency.

Other dotted lines: Indicates that you can jump to and communicate with each other without relying on each other. This is the power of routing.

Engineering Module Configuration

New construction

New Module: baseLib, Circle, home select Android Library type. After compiling, it will be normal.

Adding dependencies

In Windows, use the shortcut keys Ctrl+Shift+Alt+S to bring up the Project Structure panel. Of course, you can also open this panel by clicking File->Project Structure in the menu bar.

As shown in the figure, select different modules and add dependency modules. My dependency here is like this:

  • App module dependency:baseLib,circle,home
  • BaseLib module: Does not depend on any functional modules
  • Circle module dependencies:baseLib
  • Home module dependencies:baseLib

The module specification

  • baseLibThe common base modules of the project, which can include common utility classes, common resources, common code snippets, common references, etc., can be placed here to avoid a lot of code duplication, improve code readability, and easy maintenance of the program.
  • app: is the host module of the entire project, that is, this module has priority over other functional modules, because the main entry of the program is here.
  • Other modules are divided according to business functions and are responsible for specific business.

Project ARouter configuration

The first step:baseLibThe module configuration

Open the build.gradle file under baseLib and add the following code to dependencies

api 'com. Alibaba: arouter - API: 1.5.2'
Copy the code

Then create a new BaseApplication class under baseLib. The complete code is as follows:

public class BaseApplication extends Application {

    @Override
    public void onCreate(a) {
        super.onCreate();

        initRouter(this);
    }

    public static void initRouter(Application application) {
        if(BuildConfig.DEBUG) { ARouter.openLog(); ARouter.openDebug(); } ARouter.init(application); }}Copy the code

Then create a new class called ARouterPath, which provides a unified route to the page path, that is, the value of path in ARouter.

public class ARouterPath {

    public static final String CIRCLE_CIRCLE="/circle/home";

}
Copy the code

Step 2: Configure other modules

Open the corresponding build.gradle file in app, Circle, and Home modules

  • independenciesAdd the following code below
annotationProcessor 'com. Alibaba: arouter - compiler: 1.5.2'
Copy the code
  • indefaultConfigAdd the following code below
javaCompileOptions {
    annotationProcessorOptions {
        arguments = [AROUTER_MODULE_NAME: project.getName()]
    }
}
Copy the code

At this point, the reference configuration for the route is complete, but we haven’t added the Application yet. It’s easy. In the app module, create a New AppApplication that inherits from BaseApplication and add it to the manifest file in that module.

public class AppApplication extends BaseApplication {}Copy the code

This is not done because the demo demo, the use of third-party things, the actual development according to the needs of the initialization can be. Inheritance is done because we initialized the routing configuration earlier.

Test the ARouter jump

We have finished the configuration work, the main purpose of this article is to test the page jump, of course, the jump will include whether to carry parameters, whether the jump need to return values, and whether modules without dependencies can jump, the following group test:

In order to avoid writing findViewById(), I used ViewBinding here. The usage is easy to understand and I won’t go into details here.

The module uses route hops

In an app module, a new page named MyInfoActivity is created to display the default value, and an example is shown by carrying the parameter “jump” assignment in the MainActivity.

If your configuration is correct, you still cannot jump, then uninstall APP and run again, it is Ok, because the route address path is mapped, cache down, although later changed, but go to the cache.

The ginseng that

ARouter provides a variety of ways to pass parameters and also supports native parameter value types, as shown below:

I will not demonstrate the use of all methods here, as long as I know the following common ones, the rest are similar.

  • with(Bundle bundle): This method is recommended if you want to pass multiple parameters.
  • withBundle(String key, Bundle bundle): Still passes a Bundle, but you can customize the key.
  • With encapsulates the data type (String key, base data type value)These methods are useful if you pass only one parameter and it is a basic data type.

Other common uses like passing serialized objects, collections, etc., are for you to try. Now let’s talk about how to take arguments. The following code is passed to our MyInfoActivity:

ARouter.getInstance().build(ARouterPath.APP_MY_INFO)
          .withInt(KEY_TYPE, 100)
          .withString(KEY_NAME, "codexiaosheng")
          .withString(KEY_WEIXIN, "xiaoshengcode")
          .navigation();
Copy the code

Add: there may be careful friends noticed that the return value of the jump how to write?

  • The third method is equivalent to our native writingstartActivityForResult()
  • The fourth method also provides listening, which is used by the interception feature I’ll share later.

Take ginseng show

Corresponding to the above three parameter transmission methods:

  • with(Bundle bundle): Takes the parameter and passesgetIntent().getExtras()Get the Bundle, and we’ll use it the same way we used it native.
  • withBundle(String key, Bundle bundle)With encapsulates the data type (String key, base data type value): The method of taking parameters is the same, you can first look at the above givenMyInfoActivityThe code:
@Route(path = ARouterPath.APP_MY_INFO)
public class MyInfoActivity extends AppCompatActivity {

    private ActivityMyInfoBinding myInfoBinding;

    @Autowired
    public int u_type;
    @Autowired(name = MainActivity.KEY_NAME)
    public String uName;
    @Autowired(name = MainActivity.KEY_WEIXIN)
    public String uWeixin;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        myInfoBinding = ActivityMyInfoBinding.inflate(getLayoutInflater());
        setContentView(myInfoBinding.getRoot());

        ARouter.getInstance().inject(this);

        myInfoBinding.tvName.setText("name:" + uName + "User Type:" + u_type);
        myInfoBinding.tvWeixin.setText("weixin:"+ uWeixin); }}Copy the code

We can see that there are several differences between this parameter and our usual parameter:

  1. Using the@Autowiredannotations
  2. Much moreARouter.getInstance().inject(this);This line of code
  3. Fields for receiving parameters arepublicThe modifier
  4. There is no explicit getXXX value code

Note to @autowired:

  • The annotated variable must bepublicthe
  • If the name of the variable is different from the key passed to the parameter, you need to manually add it to the annotationnameValue, which is the key of the parameter.

In addition to the with(Bundle Bundle) method, add the following line to the page that receives the parameter:

ARouter.getInstance().inject(this);
Copy the code

GetIntent ().getextras () if the with(Bundle Bundle) method is used, get the Bundle from getIntent().

Overall, it is relatively simple, with a lot less judgment code.

Modules jump to each other

Here I use the with(Bundle Bundle) method to pass arguments to demonstrate. Let’s take a look at the overall effect:

This way you pass parameters without adding @autoWired annotations or arouter.getInstance ().inject(this) on the received page; GetIntent ().getextras ().

In the demo above, the app module jumps to home and Circle, and the home and Circle modules jump to each other. Remember the previous dependencies? There is no dependency between home and circle directly, but it can be directly jumped through the route. If there are many modules in our project, this will be very convenient and reduce the code coupling.

Look at the code for the jump home module:

// Go to the home module page
mainBinding.jumpHomePage.setOnClickListener(v -> {
    if (mainBinding.cbHome.isChecked()) {
        Bundle bundle = new Bundle();
        bundle.putInt(KEY_TYPE, 500);
        bundle.putString(KEY_NAME, "home module");
        bundle.putString(KEY_WEIXIN, "is home module~");

        ARouter.getInstance().build(ARouterPath.HOME_HOME).with(bundle).navigation();
    } else{ ARouter.getInstance().build(ARouterPath.HOME_HOME).navigation(); }});Copy the code

The core code is posted, and the basic demonstration function is complete. This article is demonstrated in Java, and the Kotlin configuration reference website.

Advanced uses of routing, such as intercepts and modules that can be run separately, will be covered in the next blog post.

Jump principle

ARouter automatically registers with annotations and generates mappings at compile time, loading files at run time and jumping to target pages with path.

This paper summarizes

  1. I can’t see the correspondingR.layout.xxx_layoutFile name, you can clickXXXBinding.getRoot()Jump to the corresponding XML
  2. If there are many hops between modules in a project, you are advised to use route hops
  3. ARouter can also jumpfragmentTo view the official demo
  4. ARouter jump is also possible, passing in the animation resource file ID

Follow wechat public account code xiao Sheng reply to Arouter