summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--android/guiTestSrc/com/android/tools/idea/tests/gui/CentralBuildDirectoryTest.java96
-rw-r--r--android/src/com/android/tools/idea/gradle/compiler/PostProjectBuildTasksExecutor.java12
-rw-r--r--android/src/com/android/tools/idea/gradle/customizer/AbstractContentRootModuleCustomizer.java16
-rw-r--r--android/src/com/android/tools/idea/gradle/customizer/android/ContentRootModuleCustomizer.java6
-rw-r--r--android/src/com/android/tools/idea/gradle/customizer/java/ContentRootModuleCustomizer.java2
-rw-r--r--android/src/com/android/tools/idea/gradle/util/FilePaths.java30
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/.gitignore10
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/.gitignore1
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/build.gradle26
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/proguard-rules.pro17
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/androidTest/java/com/android/centralizebuilddirectory/ApplicationTest.java13
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/AndroidManifest.xml21
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/java/com/android/centralizebuilddirectory/MyActivity.java36
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/drawable/ic_launcher.xml2
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/layout/activity_my.xml16
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/menu/my.xml8
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values-w820dp/dimens.xml6
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/dimens.xml5
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/strings.xml8
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/styles.xml8
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/build.gradle19
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/gradle.properties18
-rw-r--r--android/testData/guiTests/CentralBuildDirectory/settings.gradle1
23 files changed, 346 insertions, 31 deletions
diff --git a/android/guiTestSrc/com/android/tools/idea/tests/gui/CentralBuildDirectoryTest.java b/android/guiTestSrc/com/android/tools/idea/tests/gui/CentralBuildDirectoryTest.java
new file mode 100644
index 00000000000..b7b9a3b7391
--- /dev/null
+++ b/android/guiTestSrc/com/android/tools/idea/tests/gui/CentralBuildDirectoryTest.java
@@ -0,0 +1,96 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.tools.idea.tests.gui;
+
+import com.android.tools.idea.gradle.util.FilePaths;
+import com.android.tools.idea.tests.gui.framework.GuiTestCase;
+import com.android.tools.idea.tests.gui.framework.annotation.IdeGuiTest;
+import com.android.tools.idea.tests.gui.framework.fixture.IdeFrameFixture;
+import com.intellij.openapi.module.Module;
+import com.intellij.openapi.roots.ContentEntry;
+import com.intellij.openapi.roots.ModifiableRootModel;
+import com.intellij.openapi.roots.ModuleRootManager;
+import com.intellij.openapi.util.io.FileUtil;
+import com.intellij.openapi.vfs.VfsUtil;
+import com.intellij.openapi.vfs.VirtualFile;
+import org.fest.swing.edt.GuiActionRunner;
+import org.fest.swing.edt.GuiQuery;
+import org.junit.Test;
+
+import java.io.File;
+import java.io.IOException;
+
+import static com.android.tools.idea.tests.gui.framework.GuiTests.getTestProjectsRootDirPath;
+import static com.intellij.openapi.util.io.FileUtil.delete;
+import static com.intellij.openapi.vfs.VfsUtilCore.isAncestor;
+import static junit.framework.Assert.assertNotNull;
+import static junit.framework.Assert.assertTrue;
+import static org.fest.assertions.Assertions.assertThat;
+
+/**
+ * Tests fix for issue <a href="https://code.google.com/p/android/issues/detail?id=74259">74259</a>.
+ */
+public class CentralBuildDirectoryTest extends GuiTestCase {
+
+ @Test @IdeGuiTest
+ public void testImportProjectWithCentralBuildDirectoryInRootModule() throws IOException {
+ // In issue 74259, project sync fails because the "app" build directory is set to "CentralBuildDirectory/central/build", which is
+ // outside the content root of the "app" module.
+ String projectDirName = "CentralBuildDirectory";
+ File projectPath = new File(getTestProjectsRootDirPath(), projectDirName);
+
+ // The bug appears only when the central build folder does not exist.
+ final File centralBuildParentDirPath = new File(projectPath, FileUtil.join("central"));
+ delete(centralBuildParentDirPath);
+
+ IdeFrameFixture ideFrame = importProject(projectDirName);
+ final Module app = ideFrame.getModule("app");
+
+ // Now we have to make sure that if project import was successful, the build folder (with custom path) is excluded in the IDE (to
+ // prevent unnecessary file indexing, which decreases performance.)
+ VirtualFile[] excludeFolders = GuiActionRunner.execute(new GuiQuery<VirtualFile[]>() {
+ @Override
+ protected VirtualFile[] executeInEDT() throws Throwable {
+ File centralBuildDirPath = new File(centralBuildParentDirPath, "build");
+ ModuleRootManager moduleRootManager = ModuleRootManager.getInstance(app);
+ ModifiableRootModel rootModel = moduleRootManager.getModifiableModel();
+ try {
+ ContentEntry[] contentEntries = rootModel.getContentEntries();
+ ContentEntry parent = FilePaths.findParentContentEntry(centralBuildDirPath, contentEntries);
+ assertNotNull(parent);
+ return parent.getExcludeFolderFiles();
+ }
+ finally {
+ rootModel.dispose();
+ }
+ }
+ });
+
+ assertThat(excludeFolders).isNotEmpty();
+
+ VirtualFile centralBuildDir = VfsUtil.findFileByIoFile(centralBuildParentDirPath, true);
+ assertNotNull(centralBuildDir);
+ boolean isExcluded = false;
+ for (VirtualFile folder : excludeFolders) {
+ if (isAncestor(centralBuildDir, folder, true)) {
+ isExcluded = true;
+ break;
+ }
+ }
+
+ assertTrue(isExcluded);
+ }
+}
diff --git a/android/src/com/android/tools/idea/gradle/compiler/PostProjectBuildTasksExecutor.java b/android/src/com/android/tools/idea/gradle/compiler/PostProjectBuildTasksExecutor.java
index 00757ead4e5..206852ce477 100644
--- a/android/src/com/android/tools/idea/gradle/compiler/PostProjectBuildTasksExecutor.java
+++ b/android/src/com/android/tools/idea/gradle/compiler/PostProjectBuildTasksExecutor.java
@@ -243,7 +243,7 @@ public class PostProjectBuildTasksExecutor {
try {
ContentEntry[] contentEntries = rootModel.getContentEntries();
- ContentEntry parent = findParentContentEntry(buildFolderPath, contentEntries);
+ ContentEntry parent = FilePaths.findParentContentEntry(buildFolderPath, contentEntries);
if (parent == null) {
rootModel.dispose();
return;
@@ -278,16 +278,6 @@ public class PostProjectBuildTasksExecutor {
}
}
- @Nullable
- private static ContentEntry findParentContentEntry(@NotNull File path, @NotNull ContentEntry[] contentEntries) {
- for (ContentEntry contentEntry : contentEntries) {
- if (FilePaths.isPathInContentEntry(path, contentEntry)) {
- return contentEntry;
- }
- }
- return null;
- }
-
private static boolean unresolvedDependenciesFound(@NotNull String errorMessage) {
return errorMessage.contains("Could not resolve all dependencies");
}
diff --git a/android/src/com/android/tools/idea/gradle/customizer/AbstractContentRootModuleCustomizer.java b/android/src/com/android/tools/idea/gradle/customizer/AbstractContentRootModuleCustomizer.java
index 06d9b0978ce..d850add9eea 100644
--- a/android/src/com/android/tools/idea/gradle/customizer/AbstractContentRootModuleCustomizer.java
+++ b/android/src/com/android/tools/idea/gradle/customizer/AbstractContentRootModuleCustomizer.java
@@ -17,7 +17,6 @@ package com.android.tools.idea.gradle.customizer;
import com.android.tools.idea.gradle.util.FilePaths;
import com.google.common.collect.Lists;
-import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.module.Module;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.roots.ContentEntry;
@@ -36,8 +35,6 @@ import java.util.Collection;
import java.util.List;
public abstract class AbstractContentRootModuleCustomizer<T> implements ModuleCustomizer<T> {
- private static final Logger LOG = Logger.getInstance(AbstractContentRootModuleCustomizer.class);
-
@Override
public void customizeModule(@NotNull Module module, @NotNull Project project, @Nullable T model) {
if (model == null) {
@@ -79,7 +76,7 @@ public abstract class AbstractContentRootModuleCustomizer<T> implements ModuleCu
@NotNull JpsModuleSourceRootType type,
boolean generated,
@NotNull List<RootSourceFolder> orphans) {
- ContentEntry parent = findParentContentEntry(contentEntries, folderPath);
+ ContentEntry parent = FilePaths.findParentContentEntry(folderPath, contentEntries);
if (parent == null) {
orphans.add(new RootSourceFolder(folderPath, type, generated));
return;
@@ -113,17 +110,6 @@ public abstract class AbstractContentRootModuleCustomizer<T> implements ModuleCu
return true;
}
- @Nullable
- protected ContentEntry findParentContentEntry(@NotNull Collection<ContentEntry> contentEntries, @NotNull File dirPath) {
- for (ContentEntry contentEntry : contentEntries) {
- if (FilePaths.isPathInContentEntry(dirPath, contentEntry)) {
- return contentEntry;
- }
- }
- LOG.info(String.format("Failed to find content entry for file '%1$s'", dirPath.getPath()));
- return null;
- }
-
protected static class RootSourceFolder {
@NotNull private final File myPath;
@NotNull private final JpsModuleSourceRootType myType;
diff --git a/android/src/com/android/tools/idea/gradle/customizer/android/ContentRootModuleCustomizer.java b/android/src/com/android/tools/idea/gradle/customizer/android/ContentRootModuleCustomizer.java
index d2fde2ef6ee..e8a37f6322c 100644
--- a/android/src/com/android/tools/idea/gradle/customizer/android/ContentRootModuleCustomizer.java
+++ b/android/src/com/android/tools/idea/gradle/customizer/android/ContentRootModuleCustomizer.java
@@ -202,8 +202,10 @@ public class ContentRootModuleCustomizer extends AbstractContentRootModuleCustom
private void addExcludedOutputFolders(@NotNull Collection<ContentEntry> contentEntries, @NotNull IdeaAndroidProject androidProject) {
File buildFolderPath = androidProject.getDelegate().getBuildFolder();
- ContentEntry parentContentEntry = findParentContentEntry(contentEntries, buildFolderPath);
- assert parentContentEntry != null;
+ ContentEntry parentContentEntry = FilePaths.findParentContentEntry(buildFolderPath, contentEntries);
+ if (parentContentEntry == null) {
+ return;
+ }
// Explicitly exclude the output folders created by the Android Gradle plug-in
for (String folderName : EXCLUDED_OUTPUT_FOLDER_NAMES) {
diff --git a/android/src/com/android/tools/idea/gradle/customizer/java/ContentRootModuleCustomizer.java b/android/src/com/android/tools/idea/gradle/customizer/java/ContentRootModuleCustomizer.java
index 866a5d53c28..72d38244344 100644
--- a/android/src/com/android/tools/idea/gradle/customizer/java/ContentRootModuleCustomizer.java
+++ b/android/src/com/android/tools/idea/gradle/customizer/java/ContentRootModuleCustomizer.java
@@ -76,7 +76,7 @@ public class ContentRootModuleCustomizer extends AbstractContentRootModuleCustom
for (File excluded : contentRoot.getExcludeDirectories()) {
if (excluded != null) {
- ContentEntry contentEntry = findParentContentEntry(contentEntries, excluded);
+ ContentEntry contentEntry = FilePaths.findParentContentEntry(excluded, contentEntries);
if (contentEntry != null) {
if (isTopLevelJavaModule && !buildFolderUnexcluded) {
// We need to "undo" the implicit exclusion of "build" folder for top-level module.
diff --git a/android/src/com/android/tools/idea/gradle/util/FilePaths.java b/android/src/com/android/tools/idea/gradle/util/FilePaths.java
index 26e77a2cd07..c96d9dd62c9 100644
--- a/android/src/com/android/tools/idea/gradle/util/FilePaths.java
+++ b/android/src/com/android/tools/idea/gradle/util/FilePaths.java
@@ -20,19 +20,45 @@ import com.intellij.openapi.util.io.FileUtil;
import com.intellij.openapi.vfs.VfsUtilCore;
import com.intellij.openapi.vfs.VirtualFile;
import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
import java.io.File;
+import java.util.Collection;
public final class FilePaths {
private FilePaths() {
}
+ @Nullable
+ public static ContentEntry findParentContentEntry(@NotNull File path, @NotNull ContentEntry[] contentEntries) {
+ for (ContentEntry contentEntry : contentEntries) {
+ if (isPathInContentEntry(path, contentEntry)) {
+ return contentEntry;
+ }
+ }
+ return null;
+ }
+
+ @Nullable
+ public static ContentEntry findParentContentEntry(@NotNull File path, @NotNull Collection<ContentEntry> contentEntries) {
+ for (ContentEntry contentEntry : contentEntries) {
+ if (isPathInContentEntry(path, contentEntry)) {
+ return contentEntry;
+ }
+ }
+ return null;
+ }
+
public static boolean isPathInContentEntry(@NotNull File path, @NotNull ContentEntry contentEntry) {
VirtualFile rootFile = contentEntry.getFile();
+ File rootFilePath;
if (rootFile == null) {
- return false;
+ String s = VfsUtilCore.urlToPath(contentEntry.getUrl());
+ rootFilePath = new File(s);
+ }
+ else {
+ rootFilePath = VfsUtilCore.virtualToIoFile(rootFile);
}
- File rootFilePath = VfsUtilCore.virtualToIoFile(rootFile);
return FileUtil.isAncestor(rootFilePath, path, false);
}
diff --git a/android/testData/guiTests/CentralBuildDirectory/.gitignore b/android/testData/guiTests/CentralBuildDirectory/.gitignore
new file mode 100644
index 00000000000..46326953812
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/.gitignore
@@ -0,0 +1,10 @@
+.gradle
+/gradle
+/local.properties
+/.idea
+.DS_Store
+/build
+gradlew
+gradlew.bat
+*.iml
+/central
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/.gitignore b/android/testData/guiTests/CentralBuildDirectory/app/.gitignore
new file mode 100644
index 00000000000..796b96d1c40
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/.gitignore
@@ -0,0 +1 @@
+/build
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/build.gradle b/android/testData/guiTests/CentralBuildDirectory/app/build.gradle
new file mode 100644
index 00000000000..41f3fad7012
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/build.gradle
@@ -0,0 +1,26 @@
+apply plugin: 'com.android.application'
+
+buildDir = new File(rootProject.getBuildDir().getParentFile(), "central" + File.separator + "build");
+
+android {
+ compileSdkVersion 20
+ buildToolsVersion "19.1.0"
+
+ defaultConfig {
+ applicationId "com.android.central.build.directory"
+ minSdkVersion 19
+ targetSdkVersion 20
+ versionCode 1
+ versionName "1.0"
+ }
+ buildTypes {
+ release {
+ runProguard false
+ proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
+ }
+ }
+}
+
+dependencies {
+ compile fileTree(dir: 'libs', include: ['*.jar'])
+}
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/proguard-rules.pro b/android/testData/guiTests/CentralBuildDirectory/app/proguard-rules.pro
new file mode 100644
index 00000000000..e2f6a3ded07
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/proguard-rules.pro
@@ -0,0 +1,17 @@
+# Add project specific ProGuard rules here.
+# By default, the flags in this file are appended to flags specified
+# in /Applications/adt-bundle-mac-x86_64-20131030/sdk/tools/proguard/proguard-android.txt
+# You can edit the include path and order by changing the proguardFiles
+# directive in build.gradle.
+#
+# For more details, see
+# http://developer.android.com/guide/developing/tools/proguard.html
+
+# Add any project specific keep options here:
+
+# If your project uses WebView with JS, uncomment the following
+# and specify the fully qualified class name to the JavaScript interface
+# class:
+#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
+# public *;
+#}
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/androidTest/java/com/android/centralizebuilddirectory/ApplicationTest.java b/android/testData/guiTests/CentralBuildDirectory/app/src/androidTest/java/com/android/centralizebuilddirectory/ApplicationTest.java
new file mode 100644
index 00000000000..2a32f82353c
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/androidTest/java/com/android/centralizebuilddirectory/ApplicationTest.java
@@ -0,0 +1,13 @@
+package com.android.centralizebuilddirectory;
+
+import android.app.Application;
+import android.test.ApplicationTestCase;
+
+/**
+ * <a href="http://d.android.com/tools/testing/testing_android.html">Testing Fundamentals</a>
+ */
+public class ApplicationTest extends ApplicationTestCase<Application> {
+ public ApplicationTest() {
+ super(Application.class);
+ }
+} \ No newline at end of file
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/AndroidManifest.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/AndroidManifest.xml
new file mode 100644
index 00000000000..2a05b7c3956
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/AndroidManifest.xml
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="utf-8"?>
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="com.android.centralizebuilddirectory" >
+
+ <application
+ android:allowBackup="true"
+ android:icon="@drawable/ic_launcher"
+ android:label="@string/app_name"
+ android:theme="@style/AppTheme" >
+ <activity
+ android:name=".MyActivity"
+ android:label="@string/app_name" >
+ <intent-filter>
+ <action android:name="android.intent.action.MAIN" />
+
+ <category android:name="android.intent.category.LAUNCHER" />
+ </intent-filter>
+ </activity>
+ </application>
+
+</manifest>
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/java/com/android/centralizebuilddirectory/MyActivity.java b/android/testData/guiTests/CentralBuildDirectory/app/src/main/java/com/android/centralizebuilddirectory/MyActivity.java
new file mode 100644
index 00000000000..1ae12be648e
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/java/com/android/centralizebuilddirectory/MyActivity.java
@@ -0,0 +1,36 @@
+package com.android.centralizebuilddirectory;
+
+import android.app.Activity;
+import android.os.Bundle;
+import android.view.Menu;
+import android.view.MenuItem;
+
+
+public class MyActivity extends Activity {
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ setContentView(R.layout.activity_my);
+ }
+
+
+ @Override
+ public boolean onCreateOptionsMenu(Menu menu) {
+ // Inflate the menu; this adds items to the action bar if it is present.
+ getMenuInflater().inflate(R.menu.my, menu);
+ return true;
+ }
+
+ @Override
+ public boolean onOptionsItemSelected(MenuItem item) {
+ // Handle action bar item clicks here. The action bar will
+ // automatically handle clicks on the Home/Up button, so long
+ // as you specify a parent activity in AndroidManifest.xml.
+ int id = item.getItemId();
+ if (id == R.id.action_settings) {
+ return true;
+ }
+ return super.onOptionsItemSelected(item);
+ }
+}
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/drawable/ic_launcher.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/drawable/ic_launcher.xml
new file mode 100644
index 00000000000..bebd9834a0e
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/drawable/ic_launcher.xml
@@ -0,0 +1,2 @@
+<?xml version="1.0" encoding="utf-8"?>
+<color xmlns:android="http://schemas.android.com/apk/res/android" android:color="#ff0000" />
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/layout/activity_my.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/layout/activity_my.xml
new file mode 100644
index 00000000000..c17166f4d34
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/layout/activity_my.xml
@@ -0,0 +1,16 @@
+<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:tools="http://schemas.android.com/tools"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:paddingLeft="@dimen/activity_horizontal_margin"
+ android:paddingRight="@dimen/activity_horizontal_margin"
+ android:paddingTop="@dimen/activity_vertical_margin"
+ android:paddingBottom="@dimen/activity_vertical_margin"
+ tools:context=".MyActivity">
+
+ <TextView
+ android:text="@string/hello_world"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" />
+
+</RelativeLayout>
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/menu/my.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/menu/my.xml
new file mode 100644
index 00000000000..bea58cc00be
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/menu/my.xml
@@ -0,0 +1,8 @@
+<menu xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:tools="http://schemas.android.com/tools"
+ tools:context=".MyActivity" >
+ <item android:id="@+id/action_settings"
+ android:title="@string/action_settings"
+ android:orderInCategory="100"
+ android:showAsAction="never" />
+</menu>
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values-w820dp/dimens.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values-w820dp/dimens.xml
new file mode 100644
index 00000000000..63fc8164446
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values-w820dp/dimens.xml
@@ -0,0 +1,6 @@
+<resources>
+ <!-- Example customization of dimensions originally defined in res/values/dimens.xml
+ (such as screen margins) for screens with more than 820dp of available width. This
+ would include 7" and 10" devices in landscape (~960dp and ~1280dp respectively). -->
+ <dimen name="activity_horizontal_margin">64dp</dimen>
+</resources>
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/dimens.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/dimens.xml
new file mode 100644
index 00000000000..47c82246738
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/dimens.xml
@@ -0,0 +1,5 @@
+<resources>
+ <!-- Default screen margins, per the Android Design guidelines. -->
+ <dimen name="activity_horizontal_margin">16dp</dimen>
+ <dimen name="activity_vertical_margin">16dp</dimen>
+</resources>
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/strings.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/strings.xml
new file mode 100644
index 00000000000..d9e014d6c7d
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/strings.xml
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="utf-8"?>
+<resources>
+
+ <string name="app_name">CentralizeBuildDirectory</string>
+ <string name="hello_world">Hello world!</string>
+ <string name="action_settings">Settings</string>
+
+</resources>
diff --git a/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/styles.xml b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/styles.xml
new file mode 100644
index 00000000000..ff6c9d2c0fb
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/app/src/main/res/values/styles.xml
@@ -0,0 +1,8 @@
+<resources>
+
+ <!-- Base application theme. -->
+ <style name="AppTheme" parent="android:Theme.Holo.Light.DarkActionBar">
+ <!-- Customize your theme here. -->
+ </style>
+
+</resources>
diff --git a/android/testData/guiTests/CentralBuildDirectory/build.gradle b/android/testData/guiTests/CentralBuildDirectory/build.gradle
new file mode 100644
index 00000000000..9b8abe4fe13
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/build.gradle
@@ -0,0 +1,19 @@
+// Top-level build file where you can add configuration options common to all sub-projects/modules.
+
+buildscript {
+ repositories {
+ jcenter()
+ }
+ dependencies {
+ classpath 'com.android.tools.build:gradle:0.12.2'
+
+ // NOTE: Do not place your application dependencies here; they belong
+ // in the individual module build.gradle files
+ }
+}
+
+allprojects {
+ repositories {
+ jcenter()
+ }
+}
diff --git a/android/testData/guiTests/CentralBuildDirectory/gradle.properties b/android/testData/guiTests/CentralBuildDirectory/gradle.properties
new file mode 100644
index 00000000000..5d08ba75bb9
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/gradle.properties
@@ -0,0 +1,18 @@
+# Project-wide Gradle settings.
+
+# IDE (e.g. Android Studio) users:
+# Settings specified in this file will override any Gradle settings
+# configured through the IDE.
+
+# For more details on how to configure your build environment visit
+# http://www.gradle.org/docs/current/userguide/build_environment.html
+
+# Specifies the JVM arguments used for the daemon process.
+# The setting is particularly useful for tweaking memory settings.
+# Default value: -Xmx10248m -XX:MaxPermSize=256m
+# org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
+
+# When configured, Gradle will run in incubating parallel mode.
+# This option should only be used with decoupled projects. More details, visit
+# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
+# org.gradle.parallel=true \ No newline at end of file
diff --git a/android/testData/guiTests/CentralBuildDirectory/settings.gradle b/android/testData/guiTests/CentralBuildDirectory/settings.gradle
new file mode 100644
index 00000000000..e7b4def49cb
--- /dev/null
+++ b/android/testData/guiTests/CentralBuildDirectory/settings.gradle
@@ -0,0 +1 @@
+include ':app'