feat(templates): add ability to configure various elements in AndroidManifest

This commit is contained in:
Akash Yadav
2023-05-25 19:11:24 +05:30
parent a3f31659e8
commit 663900f86b
5 changed files with 111 additions and 1 deletions
@@ -0,0 +1,21 @@
/*
* This file is part of AndroidIDE.
*
* AndroidIDE is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* AndroidIDE is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with AndroidIDE. If not, see <https://www.gnu.org/licenses/>.
*/
package org.eclipse.lemminx.dom.builder
typealias XmlConfigurator = XmlBuilder.() -> Unit
typealias IndentedXmlConfigurator = IndentedXmlBuilder.() -> Unit
@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="utf-8"?><!--
Sample backup rules file; uncomment and customize as necessary.
See https://developer.android.com/guide/topics/data/autobackup
for details.
Note: This file is ignored for devices older that API 31
See https://developer.android.com/about/versions/12/backup-restore
-->
<full-backup-content>
<!--
<include domain="sharedpref" path="."/>
<exclude domain="sharedpref" path="device.xml"/>
-->
</full-backup-content>
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?><!--
Sample data extraction rules file; uncomment and customize as necessary.
See https://developer.android.com/about/versions/12/backup-restore#xml-changes
for details.
-->
<data-extraction-rules>
<cloud-backup>
<!-- TODO: Use <include> and <exclude> to control what is backed up.
<include .../>
<exclude .../>
-->
</cloud-backup>
<!--
<device-transfer>
<include .../>
<exclude .../>
</device-transfer>
-->
</data-extraction-rules>
@@ -17,12 +17,23 @@
package com.itsaky.androidide.templates.base.modules.android
import org.eclipse.lemminx.dom.builder.IndentedXmlConfigurator
/**
* Model for activities declared in [AndroidManifestBuilder].
*
* @param name The name of the activity (for `android:name` attribute).
* @param isExported Sets the `android:exported` attribute.
* @param isLauncher Adds the `intent-filter` for setting this activity as the launcher activity.
* @param configureAttrs Function for configuring additional attributes for this activity.
* @param configureInside Function for configuring additional elements inside this activity tag.
* @author Akash Yadav
*/
data class ManifestActivity(val name: String, val isExported: Boolean, val isLauncher: Boolean = false)
data class ManifestActivity(val name: String, val isExported: Boolean,
val isLauncher: Boolean = false,
val configureAttrs: IndentedXmlConfigurator? = null,
val configureInside: IndentedXmlConfigurator? = null
)
/**
* Model for icon values in [AndroidManifestBuilder].
@@ -30,8 +30,13 @@ import com.android.SdkConstants.XMLNS
import com.itsaky.androidide.templates.RecipeExecutor
import com.itsaky.androidide.templates.base.modules.android.ManifestActivity
import com.itsaky.androidide.templates.base.modules.android.ManifestIcon
import com.itsaky.androidide.templates.base.util.AndroidManifestBuilder.ConfigurationType.APPLICATION_ATTR
import com.itsaky.androidide.templates.base.util.AndroidManifestBuilder.ConfigurationType.APPLICATION_CONTENT
import com.itsaky.androidide.templates.base.util.AndroidManifestBuilder.ConfigurationType.MANIFEST_ATTR
import com.itsaky.androidide.templates.base.util.AndroidManifestBuilder.ConfigurationType.MANIFEST_CONTENT
import com.itsaky.androidide.xml.permissions.Permission
import org.eclipse.lemminx.dom.builder.IndentedXmlBuilder
import org.eclipse.lemminx.dom.builder.IndentedXmlConfigurator
import java.io.File
/**
@@ -41,6 +46,31 @@ import java.io.File
*/
class AndroidManifestBuilder {
enum class ConfigurationType {
/**
* For configuring attributes for the `<manifest>` tag.
*/
MANIFEST_ATTR,
/**
* For configuring elements inside the `<manifest>` tag.
*/
MANIFEST_CONTENT,
/**
* For configuring attributes for the `<application>` tag.
*/
APPLICATION_ATTR,
/**
* For configuring elements inside the `<application>` tag.
*/
APPLICATION_CONTENT
}
private val configurators =
hashMapOf<ConfigurationType, HashSet<IndentedXmlConfigurator>>()
private val permissions = hashSetOf<Permission>()
private val activities = hashSetOf<ManifestActivity>()
@@ -94,6 +124,11 @@ class AndroidManifestBuilder {
activities.add(activity)
}
fun configure(type: ConfigurationType, configurator: IndentedXmlConfigurator
) {
configurators.computeIfAbsent(type) { hashSetOf() }.add(configurator)
}
/**
* Generates the manifest and saves the content to the given file.
*/
@@ -110,9 +145,13 @@ class AndroidManifestBuilder {
private fun IndentedXmlBuilder.buildManifest() {
createElement(TAG_MANIFEST) {
attr(name = ANDROID_NS_NAME, value = ANDROID_URI, ns = XMLNS)
configurators[MANIFEST_ATTR]?.forEach { configurator -> configurator() }
closeStartElement()
permissions()
configurators[MANIFEST_CONTENT]?.forEach { configurator -> configurator() }
application()
}
}
@@ -141,9 +180,12 @@ class AndroidManifestBuilder {
androidAttr("label", "@string/${appLabelRes}")
androidAttr("supportsRtl", rtl.toString())
androidAttr("theme", "@style/${themeRes}")
configurators[APPLICATION_ATTR]?.forEach { configurator -> configurator() }
closeStartElement()
activities()
configurators[APPLICATION_CONTENT]?.forEach { configurator -> configurator() }
}
}
@@ -159,10 +201,14 @@ class AndroidManifestBuilder {
androidAttr("exported", "true")
}
activity.configureAttrs?.invoke(this@activities)
closeStartElement()
if (activity.isLauncher) {
intentFilter()
}
activity.configureInside?.invoke(this@activities)
}
}
}