Support android.support.v4.Fragment classes
This commit is contained in:
@@ -38,6 +38,8 @@ public object AndroidConfigurationKeys {
|
||||
public val ANDROID_RES_PATH: CompilerConfigurationKey<String> = CompilerConfigurationKey.create<String>("android resources search path")
|
||||
|
||||
public val ANDROID_MANIFEST: CompilerConfigurationKey<String> = CompilerConfigurationKey.create<String>("android manifest file")
|
||||
|
||||
public val SUPPORT_V4: CompilerConfigurationKey<String> = CompilerConfigurationKey.create<String>("'true' if compiled with support-v4 library")
|
||||
}
|
||||
|
||||
public class AndroidCommandLineProcessor : CommandLineProcessor {
|
||||
@@ -46,16 +48,18 @@ public class AndroidCommandLineProcessor : CommandLineProcessor {
|
||||
|
||||
public val RESOURCE_PATH_OPTION: CliOption = CliOption("androidRes", "<path>", "Android resources path")
|
||||
public val MANIFEST_FILE_OPTION: CliOption = CliOption("androidManifest", "<path>", "Android manifest file")
|
||||
public val SUPPORT_V4_OPTION: CliOption = CliOption("supportV4", "<path>", "Support android-v4 library", required = false)
|
||||
}
|
||||
|
||||
override val pluginId: String = ANDROID_COMPILER_PLUGIN_ID
|
||||
|
||||
override val pluginOptions: Collection<CliOption> = listOf(RESOURCE_PATH_OPTION, MANIFEST_FILE_OPTION)
|
||||
override val pluginOptions: Collection<CliOption> = listOf(RESOURCE_PATH_OPTION, MANIFEST_FILE_OPTION, SUPPORT_V4_OPTION)
|
||||
|
||||
override fun processOption(option: CliOption, value: String, configuration: CompilerConfiguration) {
|
||||
when (option) {
|
||||
RESOURCE_PATH_OPTION -> configuration.put(AndroidConfigurationKeys.ANDROID_RES_PATH, value)
|
||||
MANIFEST_FILE_OPTION -> configuration.put(AndroidConfigurationKeys.ANDROID_MANIFEST, value)
|
||||
SUPPORT_V4_OPTION -> configuration.put(AndroidConfigurationKeys.SUPPORT_V4, value)
|
||||
else -> throw CliOptionProcessingException("Unknown option: ${option.name}")
|
||||
}
|
||||
}
|
||||
@@ -73,9 +77,13 @@ public class AndroidComponentRegistrar : ComponentRegistrar {
|
||||
public override fun registerProjectComponents(project: MockProject, configuration: CompilerConfiguration) {
|
||||
val androidResPath = configuration.get(AndroidConfigurationKeys.ANDROID_RES_PATH)
|
||||
val androidManifest = configuration.get(AndroidConfigurationKeys.ANDROID_MANIFEST)
|
||||
val supportV4 = configuration.get(AndroidConfigurationKeys.SUPPORT_V4) ?: "false"
|
||||
|
||||
if (androidResPath != null && androidManifest != null) {
|
||||
project.registerService(javaClass<AndroidUIXmlProcessor>(), CliAndroidUIXmlProcessor(project, androidManifest, androidResPath))
|
||||
val xmlProcessor = CliAndroidUIXmlProcessor(project, androidManifest, androidResPath)
|
||||
if (supportV4 == "true") xmlProcessor.supportV4 = true
|
||||
|
||||
project.registerService(javaClass<AndroidUIXmlProcessor>(), xmlProcessor)
|
||||
project.registerService(javaClass<AndroidResourceManager>(), CliAndroidResourceManager(project, androidManifest, androidResPath))
|
||||
|
||||
ExternalDeclarationsProvider.registerExtension(project, CliAndroidDeclarationsProvider(project))
|
||||
|
||||
@@ -44,12 +44,16 @@ import org.jetbrains.org.objectweb.asm.Type
|
||||
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter
|
||||
|
||||
private enum class AndroidClassType(val internalClassName: String, val supportsCache: Boolean = false) {
|
||||
ACTIVITY : AndroidClassType("android/app/Activity", true)
|
||||
FRAGMENT : AndroidClassType("android/app/Fragment", true)
|
||||
VIEW : AndroidClassType("android/view/View")
|
||||
ACTIVITY : AndroidClassType(AndroidConst.ACTIVITY_FQNAME.innerName, true)
|
||||
FRAGMENT : AndroidClassType(AndroidConst.FRAGMENT_FQNAME.innerName, true)
|
||||
SUPPORT_FRAGMENT : AndroidClassType(AndroidConst.SUPPORT_FRAGMENT_FQNAME.innerName, true)
|
||||
VIEW : AndroidClassType(AndroidConst.VIEW_FQNAME.innerName)
|
||||
UNKNOWN : AndroidClassType("")
|
||||
}
|
||||
|
||||
private val String.innerName: String
|
||||
get() = replace('.', '/')
|
||||
|
||||
public class AndroidExpressionCodegenExtension : ExpressionCodegenExtension {
|
||||
companion object {
|
||||
private val PROPERTY_NAME = "_\$_findViewCache"
|
||||
@@ -145,7 +149,7 @@ public class AndroidExpressionCodegenExtension : ExpressionCodegenExtension {
|
||||
v.getstatic(androidPackage.replace(".", "/") + "/R\$id", descriptor.getName().asString(), "I")
|
||||
v.invokevirtual(androidClassType.internalClassName, "findViewById", "(I)Landroid/view/View;", false)
|
||||
}
|
||||
AndroidClassType.FRAGMENT -> {
|
||||
AndroidClassType.FRAGMENT, AndroidClassType.SUPPORT_FRAGMENT -> {
|
||||
receiver.put(Type.getType("L${androidClassType.internalClassName};"), v)
|
||||
v.invokevirtual(androidClassType.internalClassName, "getView", "()Landroid/view/View;", false)
|
||||
v.getstatic(androidPackage.replace(".", "/") + "/R\$id", descriptor.getName().asString(), "I")
|
||||
@@ -169,9 +173,10 @@ public class AndroidExpressionCodegenExtension : ExpressionCodegenExtension {
|
||||
|
||||
private fun getClassType(descriptor: ClassifierDescriptor): AndroidClassType {
|
||||
fun getClassTypeInternal(name: String): AndroidClassType? = when (name) {
|
||||
"android.app.Activity" -> AndroidClassType.ACTIVITY
|
||||
"android.app.Fragment" -> AndroidClassType.FRAGMENT
|
||||
"android.view.View" -> AndroidClassType.VIEW
|
||||
AndroidConst.ACTIVITY_FQNAME -> AndroidClassType.ACTIVITY
|
||||
AndroidConst.FRAGMENT_FQNAME -> AndroidClassType.FRAGMENT
|
||||
AndroidConst.SUPPORT_FRAGMENT_FQNAME -> AndroidClassType.SUPPORT_FRAGMENT
|
||||
AndroidConst.VIEW_FQNAME -> AndroidClassType.VIEW
|
||||
else -> null
|
||||
}
|
||||
|
||||
@@ -291,7 +296,7 @@ public class AndroidExpressionCodegenExtension : ExpressionCodegenExtension {
|
||||
loadId()
|
||||
iv.invokevirtual(className, "findViewById", "(I)Landroid/view/View;", false)
|
||||
}
|
||||
AndroidClassType.FRAGMENT -> {
|
||||
AndroidClassType.FRAGMENT, AndroidClassType.SUPPORT_FRAGMENT -> {
|
||||
iv.invokevirtual(className, "getView", "()Landroid/view/View;", false)
|
||||
loadId()
|
||||
iv.invokevirtual("android/view/View", "findViewById", "(I)Landroid/view/View;", false)
|
||||
|
||||
+6
@@ -41,6 +41,12 @@ public object AndroidConst {
|
||||
|
||||
val CLEAR_FUNCTION_NAME = "clearFindViewByIdCache"
|
||||
|
||||
val VIEW_FQNAME = "android.view.View"
|
||||
val ACTIVITY_FQNAME = "android.app.Activity"
|
||||
val FRAGMENT_FQNAME = "android.app.Fragment"
|
||||
val SUPPORT_V4_PACKAGE = "android.support.v4"
|
||||
val SUPPORT_FRAGMENT_FQNAME = "$SUPPORT_V4_PACKAGE.app.Fragment"
|
||||
|
||||
val IGNORED_XML_WIDGET_TYPES = setOf("requestFocus", "merge", "tag", "check", "fragment")
|
||||
|
||||
val ESCAPED_IDENTIFIERS = (JetTokens.KEYWORDS.getTypes() + JetTokens.SOFT_KEYWORDS.getTypes())
|
||||
|
||||
+9
-3
@@ -66,6 +66,8 @@ public abstract class AndroidUIXmlProcessor(protected val project: Project) {
|
||||
|
||||
protected abstract val cachedSources: CachedValue<List<AndroidSyntheticFile>>
|
||||
|
||||
var supportV4 = false
|
||||
|
||||
private val cachedJetFiles: CachedValue<List<JetFile>> by Delegates.lazy {
|
||||
cachedValue {
|
||||
val psiManager = PsiManager.getInstance(project)
|
||||
@@ -90,8 +92,9 @@ public abstract class AndroidUIXmlProcessor(protected val project: Project) {
|
||||
val clearCacheFile = renderSyntheticFile("clearCache") {
|
||||
writePackage(AndroidConst.SYNTHETIC_PACKAGE)
|
||||
writeAndroidImports()
|
||||
writeClearCacheFunction("android.app.Activity")
|
||||
writeClearCacheFunction("android.app.Fragment")
|
||||
writeClearCacheFunction(AndroidConst.ACTIVITY_FQNAME)
|
||||
writeClearCacheFunction(AndroidConst.FRAGMENT_FQNAME)
|
||||
if (supportV4) writeClearCacheFunction(AndroidConst.SUPPORT_FRAGMENT_FQNAME)
|
||||
}
|
||||
|
||||
listOf(clearCacheFile,
|
||||
@@ -109,6 +112,7 @@ public abstract class AndroidUIXmlProcessor(protected val project: Project) {
|
||||
|
||||
val mainLayoutFile = renderMainLayoutFile(layoutName, resources)
|
||||
val viewLayoutFile = renderViewLayoutFile(layoutName, resources)
|
||||
|
||||
listOf(mainLayoutFile, viewLayoutFile)
|
||||
}.filterNotNull() + commonFiles
|
||||
}
|
||||
@@ -138,7 +142,9 @@ public abstract class AndroidUIXmlProcessor(protected val project: Project) {
|
||||
|
||||
for (res in resources) {
|
||||
properties(res).forEach {
|
||||
writeSyntheticProperty(it.first, res, it.second)
|
||||
if (supportV4 || !it.first.startsWith(AndroidConst.SUPPORT_V4_PACKAGE)) {
|
||||
writeSyntheticProperty(it.first, res, it.second)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -31,7 +31,8 @@ public abstract class AndroidResource(val id: String) {
|
||||
public class AndroidWidget(id: String, override val className: String) : AndroidResource(id) {
|
||||
override val mainProperties = listOf(
|
||||
"android.app.Activity" to "findViewById(0)",
|
||||
"android.app.Fragment" to "getView().findViewById(0)")
|
||||
"android.app.Fragment" to "getView().findViewById(0)",
|
||||
"android.support.v4.app.Fragment" to "getView().findViewById(0)")
|
||||
|
||||
override val viewProperties = listOf("android.view.View" to "findViewById(0)")
|
||||
|
||||
|
||||
Reference in New Issue
Block a user