سؤال

Inside build.gradle for Android project

task runAndroidApplication(type: Exec, dependsOn: ':installDebug') {
    //TODO update Activity name below or find a way to get it from AndroidManifest.xml
    if (System.properties['os.name'].toLowerCase().contains('windows')) {
        // windows
        commandLine 'cmd', '/c', 'adb', 'shell', 'am', 'start', '-n', "com.example.androidapptorun.MainActivity"      
    } else {
        // linux 
        commandLine 'adb', 'shell', 'am', 'start', '-n', "com.example.androidapptorun.MainActivity"
    }
}

How to get value for main Activity from AndroidManifest for the default Activity? (Also if there are several activities, making logic to select one would make it long, while processing is to be inside Android tools)

Is there better way from android plugin then parsing AndroidManifest.xml ?

UPDATE: https://github.com/novoda/gradle-android-command-plugin can possible suit some needs, but I needed no-argument version to make quick run in Eclipse via http://marketplace.eclipse.org/content/gradle

هل كانت مفيدة؟

المحلول 2

I just wrote this for ADT 20 (L), Gradle 1.12 and com.android.tools.build:gradle:0.12.2.

It works with flavors, build types (don't forget myBuildType.initWith(existingBuildType)), and applicationIdSuffix.

Put the following at the end of android { ... }:

applicationVariants.all { variant ->
    if (variant.install) {
         tasks.create(name: "run${variant.name.capitalize()}", type: Exec, dependsOn: variant.install) {
            description "Installs the APK for ${variant.description}, and then runs the main launcher activity."
            def getMainActivity = { file ->
                new XmlSlurper().parse(file).application.activity.find{ it.'intent-filter'.find{ filter ->
                    return filter.action  .find{it.@name.text() == 'android.intent.action.MAIN'} \
                        && filter.category.find{it.@name.text() == 'android.intent.category.LAUNCHER'}
                }}.@name
            }
            doFirst {
                def activityClass = getMainActivity(variant.processManifest.manifestOutputFile)
                commandLine android.adbExe, 'shell', 'am', 'start', '-n', "${variant.packageName}/${activityClass}"
            }
        }
    }
}

For libraries you need to change applicationVariants to libraryVariants: see manual.

Update: ADT 20, Gradle 2.1 and com.android.tools.build:gradle:0.13.1:

applicationVariants.all { variant ->
    if (variant.install) {
        tasks.create(name: "run${variant.name.capitalize()}", type: Exec, dependsOn: variant.install) {
            description "Installs the APK for ${variant.description}, and then runs the main launcher activity."
            def getMainActivity = { file ->
                new XmlSlurper().parse(file).application.activity.find{ it.'intent-filter'.find{ filter ->
                    return filter.action  .find{it.'@android:name'.text() == 'android.intent.action.MAIN'      } \
                        && filter.category.find{it.'@android:name'.text() == 'android.intent.category.LAUNCHER'}
                }}.'@android:name'
            }
            doFirst {
                def activityClass = getMainActivity(variant.outputs.processManifest.manifestOutputFile)
                commandLine android.adbExe, 'shell', 'am', 'start', '-n', "${variant.applicationId}/${activityClass}"

                // or without the XML hacking: commandLine android.adbExe, 'shell', 'monkey', '-p', variant.applicationId, '1'
            }
        }
    }
}

نصائح أخرى

You can use XmlSlurper class.

example:

AndroidManifest.xml

<manifest package="com.example.your.app">

and retrieve it in gradle

def manifest = new XmlSlurper().parse(file("AndroidManifest.xml"))

// returns "com.exmaple.your.app"
manifest.@package.text()
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top