用Gradle 構建你的android程序

<div class="span9"> <div class="content"><header class="page-header"> <div class="icon"></div> <time datetime="2013-05-19T00:00:00.000Z"><a href="/2013/05/19/android4gradle/">May 19 2013</a></time> <h1 class="title">用Gradle 構建你的android程序</h1> </header> <div id="post" class="entry"> <h2 id="menuIndex0">前言</h2> <p>android gradle 的插件終於把混淆代碼的task集成進去了,加上最近,android studio 用的是gradle 來構建項目, 下定決心把android gralde 構建項目的用戶指南所有看完, 讓不會用gradle 的人也用gradle構建android項目,讓打包(注意,打包和構建是兩碼事)多版本android再也不痛苦。最後,題外話:珍惜生命,遠離ant.... <a name="more"></a></p> <h2 id="menuIndex1">Gradle build android 歷史</h2> <p><a href="http://tools.android.com">Android Tools 主頁</a> ,大概是今年2月份發佈 adt21.1 的時候,突然在主頁發現了<a href="http://tools.android.com/tech-docs/new-build-system">New Build System</a> 原來是能夠用gradle 來構建android項目,至於<a href="http://en.wikipedia.org/wiki/Gradle">gradle</a>是什麼(既然點擊進來看了應該都知道了吧。) 。而後,又看了一下<a href="http://tools.android.com/tech-docs/new-build-system/roadmap">RoadMap</a> 那時候,還並不支持Proguard 打包,因而就沒看了。。。</p> <p>最近,android studio 發佈,終於gradle 0.4 也跟着出來了,因而,先把gradle 學了一遍,而後把<a href="http://tools.android.com/tech-docs/new-build-system/user-guide">Gradle Plugin User Guide</a>也認真閱讀了一下,根據個人我的體驗,若是你對gradle 毫無瞭解就去看<a href="http://tools.android.com/tech-docs/new-build-system/user-guide">Gradle Plugin User Guide</a> 可能不少地方都一頭霧水,可是並不妨礙你用gradle 打包android 應用,只是,出現問題,你就可能很頭疼。不過,本篇博文就是讓不會gradle 也能用上 gradle 打包android 程序,由於,我也不懂gradle,因此,我把我碰到的問題的解決方案都一一列出。</p> <p>順便貼上官方爲何使用gradle 的理由</p> <ul> <li>Domain Specific Language (DSL) to describe and manipulate the build logic </li> <li>Build files are Groovy based and allow mixing of declarative elements through the DSL and using code to manipulate the DSL elements to provide custom logic. </li> <li>Built-in dependency management through Maven and/or Ivy. </li> <li>Very flexible. Allows using best practices but doesn’t force its own way of doing things. </li> <li>Plugins can expose their own DSL and their own API for build files to use. </li> <li>Good Tooling API allowing IDE integration </li> </ul> html

<h2 id="menuIndex3">Gradle 基本概念</h2>

  <p>首先咱們學習幾個gradle 的腳本語法,掌握了這幾個語法,你就能很是簡單的用gradle構建打包android項目了。首先,咱們來看下一個最簡單android <code>build.gradle</code>。</p>

<figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>java

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17</pre> </td>android

<td class="code">
          <pre>

buildscript <span class="cell">{git

repositories {
        mavenCentral()
    }</span>

    dependencies <span class="cell">{
        classpath <span class="string">'com.android.tools.build:gradle:0.4'</span>
    }</span>
}

apply plugin: <span class="string">'android'</span>

android <span class="cell">{
    compileSdkVersion <span class="number">17</span>
}</span></pre>
        </td>
      </tr>
    </tbody></table>

</figure>github

<p><strong>英語的介紹都來自與 gradle官方文檔, 主要後邊的中文不是翻譯,是補充介紹。。</strong></p>

  <p><code>buildscript{}</code></p>

  <blockquote>
    <p>Configures the build script classpath for this project. 說白了就是設置腳本的運行環境</p>
  </blockquote>

  <p><code>repositories{}</code></p>

  <blockquote>
    <p>Returns a handler to create repositories which are used for retrieving dependencies and uploading artifacts produced by the project. 大意就是支持java 依賴庫管理(maven/ivy),用於項目的依賴。這也是gradle 強力的地方。。。 </p>
  </blockquote>

  <p><code>dependencies{}</code></p>

  <blockquote>
    <p>The dependency handler of this project. The returned dependency handler instance can be used for adding new dependencies. For accessing already declared dependencies, the configurations can be used. 依賴包的定義。支持maven/ivy,遠程,本地庫,也支持單文件,若是前面定義了<code>repositories{}</code>maven 庫,使用maven的依賴(我沒接觸過ivy。。)的時候只須要按照用相似於<code>com.android.tools.build:gradle:0.4</code>,gradle 就會自動的往遠程庫下載相應的依賴。</p>
  </blockquote>

  <p><code>apply plugin:</code></p>

  <blockquote>
    <p>聲明構建的項目類型,這裏固然是android了。。。</p>
  </blockquote>

  <p><code>android{}</code></p>

  <blockquote>
    <p>設置編譯android項目的參數,接下來,咱們的構建android項目的全部配置都在這裏完成。</p>
  </blockquote>

  <h2 id="menuIndex4">構建一個Gradle android項目</h2>

  <p>首先,你要安裝<a href="http://www.gradle.org/downloads">Gradle 1.6</a> 而且,寫進系統的環境變量裏面,全部的命令都是默認你已經配好了gradle 的環境。並且,已經已經升級了android sdk 22</p>

  <p>要用gradle構建你的有兩種方式:(<strong>build.gradle 放到項目目錄下</strong>)</p>

  <ol>
    <li>利用adt 22導出 build.gradle. </li>

    <li>複製別人寫好的build.gradle 文件. </li>

    <li>根據gradle 規則,手寫android 的build.gradle 文件。 </li>
  </ol>

  <p>我的推薦1,2 方法。。。。</p>

  <p>一個android build.gradle 最基本基本文件</p>

<figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>shell

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39</pre> </td>app

<td class="code">
          <pre>buildscript {

repositories {
    mavenCentral()
}

dependencies {
    classpath <span class="comment">'com.android.tools.build:gradle:0.4'</span>
}

}maven

apply plugin: <span class="comment">'android'</span>ide

dependencies { }post

android {

compileSdkVersion <span class="number">17</span>
buildToolsVersion <span class="string">&quot;17&quot;</span>

defaultConfig {
    minSdkVersion <span class="number">8</span>
    targetSdkVersion <span class="number">17</span>
}
sourceSets {
    main {
        manifest.srcFile <span class="comment">'AndroidManifest.xml'</span>
        java.srcDirs = [<span class="comment">'src']</span>
        resources.srcDirs = [<span class="comment">'src']</span>
        aidl.srcDirs = [<span class="comment">'src']</span>
        renderscript.srcDirs = [<span class="comment">'src']</span>
        res.srcDirs = [<span class="comment">'res']</span>
        assets.srcDirs = [<span class="comment">'assets']</span>
    }

    instrumentTest.setRoot(<span class="comment">'tests')</span>
}

}</pre> </td> </tr> </tbody></table>

</figure>

<p>接着在命令行cd 到項目目錄下</p>

  <blockquote>
    <p>例如: cd e:\workplace\andoridGradle</p>
  </blockquote>

  <p>若是你是第一次使用gradle 構建android項目建議你先使用<code>gradle clean</code> 把android gradle 插件,還有相關依賴包下載下來而且對環境進行初始化,若是出錯了,通常多是下載超時,試多幾回便可,最後你會看到以下提示:<code>BUILD SUCCESSFUL</code></p>

  <p>The TaskContainer.add() method has been deprecated and is scheduled to be remove d in Gradle 2.0. Please use the create() method instead.</p>

  <p>:clean UP-TO-DATE</p>

  <p>BUILD SUCCESSFUL</p>

  <p>Total time: 7.847 secs</p>

  <p>完成以上的步驟,就能夠正式使用gralde 構建你的android項目了。</p>

  <p>而後使用<code>gradle build</code> 就完成了android 項目的構建了。若是,你是照着以上步驟走的話,你將會想項目目錄裏面看到一個build 的目錄,裏面就是用gradle 構建android項目的所有例如了,結構目錄看附錄。</p>

  <p>最終打包的apk 就在build/apk 目錄下了。而後,你會發現,兩個apk 一個是 <em>[項目名]-debug-unaligned </em>[項目名]-release-unsigned</p>

  <p>若是以上內容你都掌握的話,接下來就將詳細說說如何利用gralde 打包android apk。</p>

  <h2 id="menuIndex5">Gralde 打包參數詳解</h2>

  <p>上面說了一大堆東西,其實並不吸引人去使用gradle,若是隻是構建項目的話,adt不是更合適嗎?若是,你看完如下內容仍是這麼以爲的話,你就不必折騰gradle了。。。。。。</p>

  <h3 id="menuIndex6">打簽名包</h3>

  <p>看附錄 默認輸出 <em>release</em> apk 是沒有簽名的,那麼咱們須要簽名的很簡單,只須要在android{}裏面補充加上加上便可。完整<a href="https://gist.github.com/youxiachai/5608223">build.gradle 請點擊個人gist</a></p>

<figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3 4 5 6 7 8 9 10 11 12 13 14 15</pre> </td>

<td class="code">
          <pre>signingConfigs <span class="cell">{

myConfig{ storeFile file("gradle.keystore") storePassword "gradle" keyAlias "gradle" keyPassword "gradle" }</span> }

buildTypes<span class="cell">{ release { signingConfig signingConfigs.myConfig }</span> } </pre> </td> </tr> </tbody></table>

</figure>而後,運行<code>gradle clean</code> <code>gradle build</code> ,此次在build/apk 你看到了多了一個[項目名]-release-unaligned, 從字面上面我就能夠知道,這個只是沒有進行zipAlign 優化的版本而已。而[項目名]-release 就是咱們簽名,而且zipAlign 的apk包了. ###打混淆包### 只須要在原來的基礎上加上,完整的<a href="https://gist.github.com/youxiachai/5608223">proguad.gradle 代碼</a> <figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3 4 5 6 7 8</pre> </td>

<td class="code">
          <pre>buildTypes{

release { signingConfig signingConfigs.myConfig runProguard <span class="literal">true</span> proguardFile <span class="comment">'proguard-android.txt'</span> } }</pre> </td> </tr> </tbody></table>

</figure>

<p><code>gradle clean</code></p>

  <p><code>gradle build</code></p>

  <h3 id="menuIndex7">打多渠道包(Product Flavor)</h3>

  <p>如今來解釋一下上一節的問題,<strong>apk目錄下的兩個apk 的含義</strong></p>

  <p><strong>爲何產生了兩個apk?</strong></p>

  <p>默認的android gralde 插件定義了兩種apk 的類型<strong>debug</strong>, <strong>release</strong>,這兩種類型的詳細對比看附錄。</p>

  <p>這個是android gralde 插件 <code>buildTypes{}</code> 方法產生的,默認配置好了兩個默認模板,固然你也能夠修改,前面咱們就是在修改默認的release 的配置,讓輸出release類型的的apk,具備簽名和混淆。</p>

  <p>對於多渠道包,android 插件提供了一個名爲<code>Product Flavor{}</code> 的配置,用於進行多渠道打包。</p>

  <p>例如,個人android應用有海外版,和國內版本,並且這兩個版本的包名是不同的!!(我就舉兩個市場的例子安裝這個思路,你要打包100個不一樣的市場只是幾行代碼的事情。)。</p>

  <p>你只須要在<code>android{}</code> 補充上</p>

<figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3 4 5 6 7 8</pre> </td>

<td class="code">
          <pre>productFlavors {
playstore {
		packageName=<span class="comment">'com.youxiachai.androidgradle.playstore'</span>
}
hiapk {
		packageName=<span class="comment">'com.youxiachai.androidgradle.amazonappstore'</span>
}

}</pre> </td> </tr> </tbody></table>

</figure>

<p>而後<code>gradle clean</code>,<code>gradle build</code>,在build/apk 下面你會看到一堆的包,命名格式[項目名]-[渠道名]-release</p>

  <p><strong>僅此而已?</strong></p>

  <p><code>Product Flavor{}</code> 不僅是能改包名那麼簡單,還可以對編譯的源碼目錄進行切換。</p>

  <p>什麼意思? 不知道各位有沒有用過友盟作用戶統計,若是,你用的是分發渠道分析,你須要修改AndroidManifest.xml 添加上 <code>&lt;meta-data android:value=&quot;hiapk&quot; android:name=&quot;UMENG_CHANNEL&quot;/&gt;</code></p>

  <p>若是,你不少渠道,,而後你就會很痛苦,如今用gradle 就很是舒服,你只須要在<code>android.sourceSets</code>指定咱們的渠道名就行,android gradle 插件,會自動打包!!!例如</p>

<figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21</pre> </td>

<td class="code">
          <pre>sourceSets {
main {
    manifest.srcFile <span class="comment">'AndroidManifest.xml'</span>
    java.srcDirs = [<span class="comment">'src']</span>
    resources.srcDirs = [<span class="comment">'src']</span>
    aidl.srcDirs = [<span class="comment">'src']</span>
    renderscript.srcDirs = [<span class="comment">'src']</span>
    res.srcDirs = [<span class="comment">'res']</span>
    assets.srcDirs = [<span class="comment">'assets']</span>
}
    
hiapk {
  	manifest.srcFile <span class="comment">'hiapk/AndroidManifest.xml'</span>
}    	
   	playstore {
   		manifest.srcFile <span class="comment">'hiapk/AndroidManifest.xml'</span>
}
   
instrumentTest.setRoot(<span class="comment">'tests')</span>

}</pre> </td> </tr> </tbody></table>

</figure>而後運行<code>gradle clean</code>,<code>gradle build</code>,省下的時間去喝杯咖啡,睡個覺什麼的都好。。。 ###外部依賴### android gradle 對於外部jar 包的應用支持maven/ivy 管理的包,也支持指定具體文件,前面已經在上文說過。上面演示的完整 build.gradle gist 裏面也有寫。你須要加上以下代碼便可: <figure class="highlight lang-groovy"><figcaption><span>build.gradle </span></figcaption>

<table><tbody>
      <tr>
        <td class="gutter">
          <pre>1

2 3</pre> </td>

<td class="code">
          <pre><span class="title">dependencies</span> {
<span class="title">compile</span> files(<span class="string">'libs/android-support-v4.jar'</span>)

}</pre> </td> </tr> </tbody></table>

</figure>

<h2 id="menuIndex8">結語</h2>

  <p>至此,對於用android gradle 構建android應用程序,打包android 程序,所須要的全部知識,在以上已經說明,只要你是認真看上面文章的,對於,如何打依賴於android library project 的包,能夠看附錄提供的那個德國人寫的例子,而對於<code>build.gradle</code> 裏面的代碼你須要把<code>0.2</code>, 改成<code>0.4</code>便可。至於用gradle 運行android test case部分的教程,我的感受寫了也白寫(我寫過關於andorid 測試相關的文章,也錄製過視頻,因此有這個感受。),估計不會有人關注,因此,若是你對用gradle 進行android test的話,能夠看附錄裏面提供的官方gradle手冊。</p>

  <h2 id="menuIndex9">擴展閱讀</h2>

  <p>對於這部份內容,你讀與不讀,並不影響你使用gradle 打包android 項目。至於讀了的好處就是你可以更好的使用gradle。。</p>

  <ul>
    <li>
      <p>完整的<a href="http://tools.android.com/tech-docs/new-build-system/user-guide">Gradle Plugin User Guide</a> 其中裏面有個錯誤是<code>compile files('libs/android-support-v4.jar')</code> 不是<code>compile file('libs/android-support-v4.jar')</code> 教程是基於android gradle0.3 ,在0.4中只是多了<strong>混淆打包,這塊已經在文中補充了。</strong></p>
    </li>

    <li>
      <p>一個德國人寫的<a href="https://github.com/Goddchen/Android-Gradle-Examples">Android-Gradle-Examples</a></p>
    </li>

    <li>
      <p><a href="http://www.gradle.org/docs/current/userguide/artifact_dependencies_tutorial.html"><code>dependencies{}</code></a> 更多的介紹。</p>
    </li>

    <li>
      <p><strong>debug</strong>, <strong>release</strong>,這兩種類型的默認配置以下:</p>

      <table style="border-bottom-color: rgb(136,136,136); border-right-width: 1px; border-top-color: rgb(136,136,136); border-collapse: collapse; border-top-width: 1px; border-bottom-width: 1px; border-right-color: rgb(136,136,136); border-left-color: rgb(136,136,136); border-left-width: 1px" border="1" cellspacing="0" bordercolor="#080808"><tbody>
          <tr>
            <td style="width: 198px; height: 19px">Property name</td>

            <td style="width: 195px; height: 19px">Default values for debug</td>

            <td style="width: 241px; height: 19px">Default values for release / other</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>debuggable</b></font></td>

            <td style="width: 195px; height: 20px">true</td>

            <td style="width: 241px; height: 20px">false</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>jniDebugBuild</b></font></td>

            <td style="width: 195px; height: 20px">false</td>

            <td style="width: 241px; height: 20px">false</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 19px">&#160;<b><font color="#38761d" face="courier new, monospace">renderscriptDebugBuild</font></b></td>

            <td style="width: 195px; height: 19px">false</td>

            <td style="width: 241px; height: 19px">false</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<b><font color="#38761d" face="courier new, monospace">renderscriptOptimLevel</font></b></td>

            <td style="width: 195px; height: 20px">3</td>

            <td style="width: 241px; height: 20px">3</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<b><font color="#38761d" face="courier new, monospace">packageNameSuffix</font></b></td>

            <td style="width: 195px; height: 20px">null</td>

            <td style="width: 241px; height: 20px">null</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<b><font color="#38761d" face="courier new, monospace">versionNameSuffix</font></b></td>

            <td style="width: 195px; height: 20px">null</td>

            <td style="width: 241px; height: 20px">null</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<b><font color="#38761d" face="courier new, monospace">signingConfig</font></b></td>

            <td style="width: 195px; height: 20px">android.signingConfigs.debug</td>

            <td style="width: 241px; height: 20px">null</td>
          </tr>

          <tr>
            <td style="width: 198px; height: 20px">&#160;<b><font color="#38761d" face="courier new, monospace">zipAlign</font></b></td>

            <td style="width: 195px; height: 20px">false</td>

            <td style="width: 241px; height: 20px">true</td>
          </tr>
        </tbody></table>
    </li>
  </ul>

  <ul>
    <li>
      <p><strong>defaultConfig {}</strong> 配置參數列表</p>

      <table style="border-bottom-color: rgb(136,136,136); border-right-width: 1px; border-top-color: rgb(136,136,136); border-collapse: collapse; border-top-width: 1px; border-bottom-width: 1px; border-right-color: rgb(136,136,136); border-left-color: rgb(136,136,136); border-left-width: 1px" border="1" cellspacing="0" bordercolor="#080808"><tbody>
          <tr>
            <td style="width: 208px; height: 19px">Property Name</td>

            <td style="width: 168px; height: 19px">Default value in DSL object</td>

            <td style="width: 251px; height: 19px">Default value</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>versionCode</b></font></td>

            <td style="width: 168px; height: 20px">-1</td>

            <td style="width: 251px; height: 20px">value from manifest if present</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>versionName</b></font></td>

            <td style="width: 168px; height: 20px">null</td>

            <td style="width: 251px; height: 20px">value from manifest if present</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>minSdkVersion</b></font></td>

            <td style="width: 168px; height: 20px">-1</td>

            <td style="width: 251px; height: 20px">value from manifest if present</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>targetSdkVersion</b></font></td>

            <td style="width: 168px; height: 20px">-1</td>

            <td style="width: 251px; height: 20px">value from manifest if present</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>packageName</b></font></td>

            <td style="width: 168px; height: 20px">null</td>

            <td style="width: 251px; height: 20px">value from manifest if present</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>testPackageName</b></font></td>

            <td style="width: 168px; height: 20px">null</td>

            <td style="width: 251px; height: 20px">app package name + 「.test」</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>testInstrumentationRunner</b></font></td>

            <td style="width: 168px; height: 20px">null</td>

            <td style="width: 251px; height: 20px">android.test.InstrumentationTestRunner</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 19px">&#160;<font color="#38761d" face="courier new, monospace"><b>signingConfig</b></font></td>

            <td style="width: 168px; height: 19px">null</td>

            <td style="width: 251px; height: 19px">null</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 20px">&#160;<font color="#38761d" face="courier new, monospace"><b>runProguard</b></font></td>

            <td style="width: 168px; height: 20px">false</td>

            <td style="width: 251px; height: 20px">false</td>
          </tr>

          <tr>
            <td style="width: 208px; height: 19px">&#160;<font color="#38761d" face="courier new, monospace"><b>proguardFile</b></font></td>

            <td style="width: 168px; height: 19px">&#160; 'proguard-android.txt' or 'proguard-android-optimize.txt'</td>

            <td style="width: 251px; height: 19px">&#160; 'proguard-android.txt' or 'proguard-android-optimize.txt'</td>
          </tr>
        </tbody></table>
    </li>

    <li>
      <p>build 結構目錄</p>

<figure class="highlight lang-shell"><figcaption><span>tree </span></figcaption>

<table><tbody>
          <tr>
            <td class="gutter">
              <pre>1

2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90</pre> </td>

<td class="code">
              <pre>build/

├── apk ├── assets │   ├── debug │   └── <span class="keyword">release</span> ├── classes │   ├── debug │   │   └── com │   │   └── example │   │   └── gradle │   └── <span class="keyword">release</span> │   └── com │   └── example │   └── gradle ├── dependency-cache │   ├── debug │   └── <span class="keyword">release</span> ├── incremental │   ├── aidl │   │   ├── debug │   │   └── <span class="keyword">release</span> │   ├── dex │   │   ├── debug │   │   └── <span class="keyword">release</span> │   ├── mergeAssets │   │   ├── debug │   │   └── <span class="keyword">release</span> │   └── mergeResources │   ├── debug │   └── <span class="keyword">release</span> ├── libs ├── manifests │   ├── debug │   └── <span class="keyword">release</span> ├── res │   ├── <span class="keyword">all</span> │   │   ├── debug │   │   │   ├── drawable-hdpi │   │   │   ├── drawable-mdpi │   │   │   ├── drawable-xhdpi │   │   │   ├── drawable-xxhdpi │   │   │   ├── layout │   │   │   ├── menu │   │   │   ├── values │   │   │   ├── values-sw720dp-land │   │   │   ├── values-v11 │   │   │   └── values-v14 │   │   └── <span class="keyword">release</span> │   │   ├── drawable-hdpi │   │   ├── drawable-mdpi │   │   ├── drawable-xhdpi │   │   ├── drawable-xxhdpi │   │   ├── layout │   │   ├── menu │   │   ├── values │   │   ├── values-sw720dp-land │   │   ├── values-v11 │   │   └── values-v14 │   └── rs │   ├── debug │   └── <span class="keyword">release</span> ├── source │   ├── aidl │   │   ├── debug │   │   └── <span class="keyword">release</span> │   ├── buildConfig │   │   ├── debug │   │   │   └── com │   │   │   └── example │   │   │   └── gradle │   │   └── <span class="keyword">release</span> │   │   └── com │   │   └── example │   │   └── gradle │   ├── r │   │   ├── debug │   │   │   └── com │   │   │   └── example │   │   │   └── gradle │   │   └── <span class="keyword">release</span> │   │   └── com │   │   └── example │   │   └── gradle │   └── rs │   ├── debug │   └── <span class="keyword">release</span> └── symbols ├── debug └── <span class="keyword">release</span> <span class="number">88</span> directories</pre> </td> </tr> </tbody></table>

</figure></li> </ul>

<h2 id="menuIndex10">最後的吐槽</h2>

  <p>吐槽一下。。。用ant腳本的(也許你沒有接觸過。。)。在之前你用ant 腳本打包apk的時候須要打包不一樣包名,你須要用ant 讀取<code>AndroidManifest.xml</code> 而後又正則匹配替換裏面packagename 參數。。雖然描述得過程很簡單,你真去寫的時候你就蛋疼了(對於一個ant外行人來講,我的感受ant的學習曲線太陡峭了,若是是兩年前的我,可能還寫得出這樣的ant腳本(當年費了很大的功夫學習了一個多星期),不過,由於不多用到(後來知道maven了。。果斷放棄了ant,爲何不在android使用maven? 由於,android 的maven 插件式非官方的,並且如今看來maven 的xml實在很複雜,看起來就頭疼))*</p>
</div>

<p></p>

</div>

<p></p> </div>

相關文章
相關標籤/搜索