How to speed up development by using MVP templates for Android studio
Hello again dear Android developers. We hope that you’ve read our blog post about basic Android templates. If you haven’t, please do so because it will help you understand today’s topic. In this blog post, we will show you how to make Android MVP group templates for Android Studio. This will save you a lot of time and make Android development much more exciting.
Why should I use MVP templates?
Manually writing activity or fragment MVP structure will take you about 10-20 minutes, but if you use templates it’s a matter of seconds.
What do I need for MVP templates?
You need Dagger 2 and some will power.
Android group templates basics
This is an example of Group templates files structure:
and files are located in (MacOs) ANDROID_STUDIO_LOCATION/plugins/android/lib/templates/activities
The idea is to create variables which will be used for package structure generating and class generating.
Variables are declared in template.xml
template.xml should have <template> root tag, and variables should be described by <parameter> tags.
<parameter id="folderName" name="Folder Name" type="string" constraints="class|unique|nonempty" default="demo" help="Activity root folder" />
Variables should have:
id – this is the variable name which will be used for substitution
name – this will be shown in creational templates pop-up
type – variable input type
constraints – describes entry property
help – used for input variable description
also, variables can be prefilled if other entries are filled. This is done with the “suggest” attribute.
The structure is generated with recipe.xml.ftl
Recipe has root tag <recipe> and structure is declared by <instantiate> tags
Instantiate from="src/app_package/classes/Activity.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/view/${activityClass}.java"
recipe should have:
from – used for finding class ftl file. This file will be used for class generating later.
to – used for creating folder structure and class name. Class will be created inside folder structure.
The class template is defined by xxx.ftl file and class template making logic is already explained in previous tutorial.
Let’s make a MVP template step by step
I assume that you know how to use and setup Dagger 2, so I will skip this part.
Step 1
Navigate to ANDROID_STUDIO_LOCATION/plugins/android/lib/templates/activities
Step 2
Create files structure like in the picture below.
3. Creating files
activity_layout_recipe.xml.ftl <recipe> <instantiate from="src/app_package/layout/activity_layout.xml.ftl" to="${escapeXmlAttribute(resOut)}/layout/${layoutName}.xml" /> </recipe>
This file is used for making activity layout.
globals.xml.ftl <?xml version="1.0"?> <globals> <global id="hasNoActionBar" type="boolean" value="false" /> <global id="parentActivityClass" value="" /> <global id="simpleLayoutName" value="${layoutName}" /> <global id="excludeMenu" type="boolean" value="true" /> <global id="generateActivityTitle" type="boolean" value="false" /> <global id="relativePackage" type="string" value=".${folderName}.activity.view"/> <#include "../common/common_globals.xml.ftl" /> </globals>
This file is used for creating global variables. Global variables are used for updating the manifest file when new MVP activity is created.
recipe.xml.ftl <?xml version="1.0"?> <recipe> <#include "../common/recipe_manifest.xml.ftl" /> <#include "activity_layout_recipe.xml.ftl" /> <instantiate from="src/app_package/classes/Activity.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/view/${activityClass}.java" /> <instantiate from="src/app_package/classes/View.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/view/${viewClass}.java" /> <instantiate from="src/app_package/classes/Component.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/${componentClass}.java" /> <instantiate from="src/app_package/classes/Module.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/${moduleClass}.java" /> <instantiate from="src/app_package/classes/PresenterImpl.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/presenter/${presenterClass}Impl.java" /> <instantiate from="src/app_package/classes/Presenter.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/presenter/${presenterClass}.java" /> <instantiate from="src/app_package/classes/InteractorImpl.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/interactor/${interactorClass}Impl.java" /> <instantiate from="src/app_package/classes/Interactor.java.ftl" to="${escapeXmlAttribute(srcOut)}/${folderName}/activity/interactor/${interactorClass}.java" /> </recipe>
Recipe is a key component that is used for generating packages and classes.
template.xml <?xml version="1.0"?> <template format="2" revision="2" name="MVP Activity" minApi="7" minBuildApi="14" description="Generate MVP structure, classes and interfaces"> <category value="MVP blog" /> <formfactor value="Mobile" /> <parameter id="folderName" name="Folder Name" type="string" constraints="class|unique|nonempty" default="demo" help="Activity root folder" /> <parameter id="isLauncher" name="Launcher Activity" type="boolean" default="false"/> <parameter id="activityClass" name="Activity Name" type="string" constraints="class|unique|nonempty" suggest="${layoutToActivity(folderName)}" default="MainActivity" help="Activity name" /> <parameter id="layoutName" name="Layout Name" type="string" constraints="layout|unique|nonempty" suggest="${activityToLayout(activityClass)}" default="activity_main" help="Activity layout name" /> <parameter id="packageName" name="Package name" type="string" constraints="package.${folderName}" default="com.test.test" help="Enter package name" /> <parameter id="applicationpackage" name="Application package name" type="string" constraints="package" default="com.test.test" /> <parameter id="viewClass" name="View Name" type="string" constraints="class|nonempty|unique" default="MainView" suggest="${underscoreToCamelCase(activityClass)}View" help="View interface name" /> <parameter id="presenterClass" name="Presenter Name" type="string" constraints="class|nonempty|unique" default="MainPresenter" suggest="${underscoreToCamelCase(activityClass)}Presenter" help="Presenter name" /> <parameter id="interactorClass" name="Interactor Name" type="string" constraints="class|nonempty|unique" default="MainInteractor" suggest="${underscoreToCamelCase(activityClass)}Interactor" help="Interactor name" /> <parameter id="componentClass" name="Component Name" type="string" constraints="class|nonempty|unique" default="MainComponent" suggest="${underscoreToCamelCase(activityClass)}Component" help="Component name" /> <parameter id="moduleClass" name="Module Name" type="string" constraints="class|nonempty|unique" default="MainModule" suggest="${underscoreToCamelCase(activityClass)}Module" help="Module name" /> <globals file="globals.xml.ftl" /> <execute file="recipe.xml.ftl" /> </template>
This file is used for variable declaration, autosuggest is also used.
Files in app_package are single templates which you can find on GitHub repo.
These templates will generate all classes declared in recipe.xml.ftl file, and it will use variables declared in template.xml file.
How to use MVP templates?
Press right mouse button on the package where you want to generate activity (keep in mind that group templates will create the MVP activity package automatically), then select news/MVP blog/MVP Activity. After that pop up will be displayed.
Enter Folder name and all other fields should be prefilled (except Application package name), then hit finish and all classes and interfaces for MVP would be generated.
Conclusion
Android MVP templates are simple for made and save a lot of time. Now you can make fragment MVP and save even more time. This blog post is last blog post of templates series, I hope that you will start using templates, and start saving time.