aboutsummaryrefslogtreecommitdiffstats
path: root/apps
diff options
context:
space:
mode:
authorRaphael <raphael@google.com>2012-03-13 13:38:20 -0700
committerRaphael <raphael@google.com>2012-03-14 16:02:27 -0700
commit679f7f7a61413acbeff0f8012b5cb7838f390baf (patch)
tree26824af39663e68ed48ccb0fc77e7485f77b0740 /apps
parentc87a0a0ac401d121ddd282ca1dd03d505f7ab5af (diff)
downloadsdk-679f7f7a61413acbeff0f8012b5cb7838f390baf.zip
sdk-679f7f7a61413acbeff0f8012b5cb7838f390baf.tar.gz
sdk-679f7f7a61413acbeff0f8012b5cb7838f390baf.tar.bz2
Skeleton for a SdkController app with a sevice.
This is just a basic app that has a background service and an activity to start/stop the service. The service has a binder interface (so that the activities can control the service) and a listener (so that the service can report to activities.) The service automatically starts with the app and there's a toggle for the user to turn it off/on. The activity also reports errors from the service, if any. There's a notification when the service is running. which brings back to the control activity. Change-Id: I67d37e3d905eb328f4d1f7d13fb118f4c7077b74
Diffstat (limited to 'apps')
-rw-r--r--apps/SdkController/.gitignore9
-rwxr-xr-xapps/SdkController/SdkControllerApp/.classpath8
-rwxr-xr-xapps/SdkController/SdkControllerApp/.project33
-rwxr-xr-xapps/SdkController/SdkControllerApp/AndroidManifest.xml26
-rwxr-xr-xapps/SdkController/SdkControllerApp/proguard-project.txt20
-rwxr-xr-xapps/SdkController/SdkControllerApp/project.properties14
-rwxr-xr-xapps/SdkController/SdkControllerApp/res/drawable-hdpi/ic_launcher.pngbin0 -> 9397 bytes
-rwxr-xr-xapps/SdkController/SdkControllerApp/res/drawable-ldpi/ic_launcher.pngbin0 -> 2729 bytes
-rwxr-xr-xapps/SdkController/SdkControllerApp/res/drawable-mdpi/ic_launcher.pngbin0 -> 5237 bytes
-rwxr-xr-xapps/SdkController/SdkControllerApp/res/drawable-xhdpi/ic_launcher.pngbin0 -> 14383 bytes
-rwxr-xr-xapps/SdkController/SdkControllerApp/res/layout/main.xml108
-rwxr-xr-xapps/SdkController/SdkControllerApp/res/values/strings.xml38
-rwxr-xr-xapps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/ControllerService.java246
-rwxr-xr-xapps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MainActivity.java219
-rwxr-xr-xapps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MultitouchActivity.java34
-rwxr-xr-xapps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/SensorActivity.java34
-rwxr-xr-xapps/SdkController/SdkControllerLib/.classpath8
-rwxr-xr-xapps/SdkController/SdkControllerLib/.project33
-rwxr-xr-xapps/SdkController/SdkControllerLib/project.properties2
-rwxr-xr-xapps/SdkController/SdkControllerMultitouch/.classpath8
-rwxr-xr-xapps/SdkController/SdkControllerMultitouch/.project33
-rw-r--r--apps/SdkController/SdkControllerMultitouch/project.properties2
-rwxr-xr-xapps/SdkController/SdkControllerSensor/.classpath8
-rwxr-xr-xapps/SdkController/SdkControllerSensor/.project33
-rwxr-xr-xapps/SdkController/SdkControllerSensor/project.properties2
25 files changed, 906 insertions, 12 deletions
diff --git a/apps/SdkController/.gitignore b/apps/SdkController/.gitignore
deleted file mode 100644
index d3a6cac..0000000
--- a/apps/SdkController/.gitignore
+++ /dev/null
@@ -1,9 +0,0 @@
-bin
-gen
-.classpath
-.project
-SdkControllerLib/bin/
-SdkControllerSensor/bin/
-SdkControllerSensor/gen/
-SdkControllerMultitouch/bin/
-SdkControllerMultitouch/gen/
diff --git a/apps/SdkController/SdkControllerApp/.classpath b/apps/SdkController/SdkControllerApp/.classpath
new file mode 100755
index 0000000..a4f1e40
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/.classpath
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+ <classpathentry kind="src" path="src"/>
+ <classpathentry kind="src" path="gen"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.ANDROID_FRAMEWORK"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.LIBRARIES"/>
+ <classpathentry kind="output" path="bin/classes"/>
+</classpath>
diff --git a/apps/SdkController/SdkControllerApp/.project b/apps/SdkController/SdkControllerApp/.project
new file mode 100755
index 0000000..a2d5c18
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/.project
@@ -0,0 +1,33 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+ <name>SdkControllerApp</name>
+ <comment></comment>
+ <projects>
+ </projects>
+ <buildSpec>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ResourceManagerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.PreCompilerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.jdt.core.javabuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ApkBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ </buildSpec>
+ <natures>
+ <nature>com.android.ide.eclipse.adt.AndroidNature</nature>
+ <nature>org.eclipse.jdt.core.javanature</nature>
+ </natures>
+</projectDescription>
diff --git a/apps/SdkController/SdkControllerApp/AndroidManifest.xml b/apps/SdkController/SdkControllerApp/AndroidManifest.xml
new file mode 100755
index 0000000..62e498f
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/AndroidManifest.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="com.android.tools.sdkcontroller"
+ android:versionCode="1"
+ android:versionName="1.0" >
+
+ <uses-sdk android:minSdkVersion="7" android:targetSdkVersion="15"/>
+
+ <application
+ android:icon="@drawable/ic_launcher"
+ android:label="@string/app_name" >
+ <activity
+ android:name=".MainActivity"
+ android:label="@string/app_name" android:launchMode="singleInstance">
+ <intent-filter>
+ <action android:name="android.intent.action.MAIN" />
+
+ <category android:name="android.intent.category.LAUNCHER" />
+ </intent-filter>
+ </activity>
+ <activity android:name=".SensorActivity" android:launchMode="singleInstance"></activity>
+ <activity android:name=".MultitouchActivity" android:launchMode="singleInstance" android:configChanges="mcc|mnc|locale|touchscreen|keyboard|keyboardHidden|navigation|orientation|screenLayout|fontScale" android:screenOrientation="portrait"></activity>
+ <service android:icon="@drawable/ic_launcher" android:description="@string/service_description" android:name="ControllerService"></service>
+ </application>
+
+</manifest> \ No newline at end of file
diff --git a/apps/SdkController/SdkControllerApp/proguard-project.txt b/apps/SdkController/SdkControllerApp/proguard-project.txt
new file mode 100755
index 0000000..f2fe155
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/proguard-project.txt
@@ -0,0 +1,20 @@
+# To enable ProGuard in your project, edit project.properties
+# to define the proguard.config property as described in that file.
+#
+# Add project specific ProGuard rules here.
+# By default, the flags in this file are appended to flags specified
+# in ${sdk.dir}/tools/proguard/proguard-android.txt
+# You can edit the include path and order by changing the ProGuard
+# include property in project.properties.
+#
+# 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/apps/SdkController/SdkControllerApp/project.properties b/apps/SdkController/SdkControllerApp/project.properties
new file mode 100755
index 0000000..9c52cb1
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/project.properties
@@ -0,0 +1,14 @@
+# This file is automatically generated by Android Tools.
+# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
+#
+# This file must be checked in Version Control Systems.
+#
+# To customize properties used by the Ant build system edit
+# "ant.properties", and override values to adapt the script to your
+# project structure.
+#
+# To enable ProGuard to shrink and obfuscate your code, uncomment this (available properties: sdk.dir, user.home):
+#proguard.config=${sdk.dir}\tools\proguard\proguard-android.txt:proguard-project.txt
+
+# Project target.
+target=android-15
diff --git a/apps/SdkController/SdkControllerApp/res/drawable-hdpi/ic_launcher.png b/apps/SdkController/SdkControllerApp/res/drawable-hdpi/ic_launcher.png
new file mode 100755
index 0000000..96a442e
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/res/drawable-hdpi/ic_launcher.png
Binary files differ
diff --git a/apps/SdkController/SdkControllerApp/res/drawable-ldpi/ic_launcher.png b/apps/SdkController/SdkControllerApp/res/drawable-ldpi/ic_launcher.png
new file mode 100755
index 0000000..9923872
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/res/drawable-ldpi/ic_launcher.png
Binary files differ
diff --git a/apps/SdkController/SdkControllerApp/res/drawable-mdpi/ic_launcher.png b/apps/SdkController/SdkControllerApp/res/drawable-mdpi/ic_launcher.png
new file mode 100755
index 0000000..359047d
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/res/drawable-mdpi/ic_launcher.png
Binary files differ
diff --git a/apps/SdkController/SdkControllerApp/res/drawable-xhdpi/ic_launcher.png b/apps/SdkController/SdkControllerApp/res/drawable-xhdpi/ic_launcher.png
new file mode 100755
index 0000000..71c6d76
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/res/drawable-xhdpi/ic_launcher.png
Binary files differ
diff --git a/apps/SdkController/SdkControllerApp/res/layout/main.xml b/apps/SdkController/SdkControllerApp/res/layout/main.xml
new file mode 100755
index 0000000..612b9fc
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/res/layout/main.xml
@@ -0,0 +1,108 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+ * Copyright (C) 2012 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.
+ */
+-->
+
+<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:tools="http://schemas.android.com/tools"
+ android:id="@+id/RelativeLayout1"
+ android:layout_width="fill_parent"
+ android:layout_height="fill_parent"
+ android:orientation="vertical"
+ android:padding="8dp" >
+
+ <TextView
+ android:id="@+id/textIntro"
+ android:layout_width="fill_parent"
+ android:layout_height="wrap_content"
+ android:layout_alignParentLeft="true"
+ android:layout_alignParentTop="true"
+ android:text="@string/main_text_intro" />
+
+ <ToggleButton
+ android:id="@+id/toggleService"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_alignParentRight="true"
+ android:layout_below="@+id/textIntro" />
+
+ <TextView
+ android:id="@+id/labelService"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_alignBaseline="@+id/toggleService"
+ android:layout_alignParentLeft="true"
+ android:layout_marginTop="20dp"
+ android:text="@string/main_label_service"
+ android:textAppearance="?android:attr/textAppearanceLarge" />
+
+ <TextView
+ android:id="@+id/textStatus"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_alignBaseline="@+id/labelService"
+ android:layout_marginLeft="8dp"
+ android:layout_toRightOf="@+id/labelService"
+ android:text="[status]"
+ android:textAppearance="?android:attr/textAppearanceLarge"
+ tools:ignore="HardcodedText" />
+
+ <TextView
+ android:id="@+id/textError"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_alignParentLeft="true"
+ android:layout_alignParentRight="true"
+ android:layout_below="@+id/toggleService"
+ android:layout_marginBottom="8dp"
+ android:layout_marginTop="8dp"
+ android:background="#F00F"
+ android:gravity="center_horizontal"
+ android:padding="8dp"
+ android:text="[service errors]"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:textColor="#FFF0"
+ tools:ignore="HardcodedText" />
+
+ <TextView
+ android:id="@+id/labelButtons"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_below="@+id/textError"
+ android:layout_marginTop="16dp"
+ android:text="@string/main_label_buttons"
+ android:textAppearance="?android:attr/textAppearanceLarge" />
+
+ <Button
+ android:id="@+id/btnOpenMultitouch"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_below="@+id/labelButtons"
+ android:layout_centerHorizontal="true"
+ android:layout_marginTop="16dp"
+ android:text="@string/main_btn_open_multitouch" />
+
+ <Button
+ android:id="@+id/btnOpenSensors"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_below="@+id/btnOpenMultitouch"
+ android:layout_centerHorizontal="true"
+ android:layout_marginTop="16dp"
+ android:text="@string/main_btn_open_sensors" />
+
+</RelativeLayout> \ No newline at end of file
diff --git a/apps/SdkController/SdkControllerApp/res/values/strings.xml b/apps/SdkController/SdkControllerApp/res/values/strings.xml
new file mode 100755
index 0000000..e840166
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/res/values/strings.xml
@@ -0,0 +1,38 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+ * Copyright (C) 2012 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.
+ */
+-->
+
+<resources>
+
+ <!-- Strings for manifest. -->
+ <string name="app_name">SdkControllerApp</string>
+ <string name="service_description">Background service for SdkController</string>
+
+ <!-- Strings for service. -->
+ <string name="service_notif_title">SdkController is running</string>
+
+ <!-- Strings for layout/main -->
+ <string name="main_text_intro">(insert a description of the purpose of this app here)</string>
+ <string name="main_label_service">Service:</string>
+ <string name="main_label_buttons">What you can do:</string>
+ <string name="main_btn_open_multitouch">Control Multi-touch</string>
+ <string name="main_btn_open_sensors">Control Sensors</string>
+ <string name="main_service_status_running">Running</string>
+ <string name="main_service_status_stopped">Stopped</string>
+
+</resources> \ No newline at end of file
diff --git a/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/ControllerService.java b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/ControllerService.java
new file mode 100755
index 0000000..b67ac45
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/ControllerService.java
@@ -0,0 +1,246 @@
+/*
+ * Copyright (C) 2012 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.sdkcontroller;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import android.app.Activity;
+import android.app.Notification;
+import android.app.NotificationManager;
+import android.app.PendingIntent;
+import android.app.Service;
+import android.content.Intent;
+import android.os.Binder;
+import android.os.IBinder;
+import android.os.SystemClock;
+import android.util.Log;
+
+/**
+ * The background service of the SdkController.
+ * There can be only one instance of this.
+ */
+public class ControllerService extends Service {
+
+ /*
+ * Implementation reference:
+ * http://developer.android.com/reference/android/app/Service.html#LocalServiceSample
+ */
+
+ public static String TAG = ControllerService.class.getSimpleName();
+ private static boolean DEBUG = true;
+
+ private static int NOTIF_ID = 'S' << 24 + 'd' << 16 + 'k' << 8 + 'C' << 0;
+
+ private final IBinder mBinder = new ControllerBinder();
+
+ private List<ControllerListener> mListeners = new ArrayList<ControllerListener>();
+
+ /**
+ * Whether the service is running. Set to true in onCreate, false in onDestroy.
+ */
+ private static volatile boolean gServiceIsRunning = false;
+
+ /** Internal error reported by the service. */
+ private String mSensorError = "";
+
+ /**
+ * Interface that the service uses to notify binded activities.
+ * <p/>
+ * As a design rule, implementations of this listener should be aware that most calls
+ * will NOT happen on the UI thread. Any access to the UI should be properly protected
+ * by using {@link Activity#runOnUiThread(Runnable)}.
+ */
+ public interface ControllerListener {
+ /**
+ * The error string reported by the service has changed. <br/>
+ * Note this may be called from a thread different than the UI thread.
+ * @param error The new error string.
+ */
+ void onErrorChanged(String error);
+ }
+
+ /** Interface that callers can use to access the service. */
+ public class ControllerBinder extends Binder {
+
+ /**
+ * Adds a new listener that will be notified when the service state changes.
+ *
+ * @param listener A non-null listener. Ignored if already listed.
+ */
+ public void addListener(ControllerListener listener) {
+ if (listener != null) {
+ synchronized(mListeners) {
+ if (!mListeners.contains(listener)) {
+ mListeners.add(listener);
+ }
+ }
+ }
+ }
+
+ /**
+ * Removes a listener.
+ *
+ * @param listener A listener to remove. Can be null.
+ */
+ public void removeListener(ControllerListener listener) {
+ synchronized(mListeners) {
+ mListeners.remove(listener);
+ }
+ }
+
+ public String getSensorErrors() {
+ return mSensorError;
+ }
+ }
+
+ /**
+ * Whether the service is running. Set to true in onCreate, false in onDestroy.
+ */
+ public static boolean isServiceIsRunning() {
+ return gServiceIsRunning;
+ }
+
+ @Override
+ public void onCreate() {
+ super.onCreate();
+ if (DEBUG) Log.d(TAG, "Service onCreate");
+ gServiceIsRunning = true;
+ showNotification();
+ onServiceStarted();
+ }
+
+ @Override
+ public int onStartCommand(Intent intent, int flags, int startId) {
+ // We want this service to continue running until it is explicitly
+ // stopped, so return sticky.
+ if (DEBUG) Log.d(TAG, "Service onStartCommand");
+ return START_STICKY;
+ }
+
+ @Override
+ public IBinder onBind(Intent intent) {
+ if (DEBUG) Log.d(TAG, "Service onBind");
+ return mBinder;
+ }
+
+ @Override
+ public void onDestroy() {
+ if (DEBUG) Log.d(TAG, "Service onDestroy");
+ gServiceIsRunning = false;
+ removeNotification();
+ resetError();
+ onServiceStopped();
+ super.onDestroy();
+ }
+
+ // ------
+
+ /**
+ * Called when the service has been created.
+ */
+ private void onServiceStarted() {
+ // TODO: add stuff to do when the service starts (e.g. activate sensors?)
+
+ // Hack: just do see if this is working, change the error field for a little while.
+ Thread t = new Thread(new Runnable() {
+ @Override
+ public void run() {
+ for (int i = 1; i <= 5 && gServiceIsRunning; i++) {
+ SystemClock.sleep(1000); // 1s
+ resetError();
+ addError("Test msg from service thread " + i);
+ }
+ resetError();
+ }
+ });
+ t.start();
+ }
+
+ /**
+ * Called when the service is being destroyed.
+ */
+ private void onServiceStopped() {
+
+ // TODO: add stuff to do when the service stops (e.g. release sensors?)
+ }
+
+ /**
+ * Resets the error string and notify listeners.
+ */
+ private void resetError() {
+ mSensorError = "";
+
+ synchronized(mListeners) {
+ for (ControllerListener listener : mListeners) {
+ listener.onErrorChanged(mSensorError);
+ }
+ }
+ }
+
+ /**
+ * An internal utility method to add a line to the error string and notify listeners.
+ * @param error A non-null non-empty error line. \n will be added automatically.
+ */
+ private void addError(String error) {
+ Log.e(TAG, error);
+ if (mSensorError.length() > 0) {
+ mSensorError += "\n";
+ }
+ mSensorError += error;
+
+ synchronized(mListeners) {
+ for (ControllerListener listener : mListeners) {
+ listener.onErrorChanged(mSensorError);
+ }
+ }
+ }
+
+ /**
+ * Displays a notification showing that the service is running.
+ * When the user touches the notification, it opens the main activity
+ * which allows the user to stop this service.
+ */
+ @SuppressWarnings("deprecated")
+ private void showNotification() {
+ NotificationManager nm = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
+
+ String text = getString(R.string.service_notif_title);
+
+ // Note: Notification is marked as deprecated -- in API 11+ there's a new Builder class
+ // but we need to have API 7 compatibility so we ignore that warning.
+
+ Notification n = new Notification(R.drawable.ic_launcher, text, System.currentTimeMillis());
+ n.flags |= Notification.FLAG_ONGOING_EVENT | Notification.FLAG_NO_CLEAR;
+ Intent intent = new Intent(this, MainActivity.class);
+ intent.setFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP);
+ PendingIntent pi = PendingIntent.getActivity(
+ this, //context
+ 0, //requestCode
+ intent, //intent
+ 0 // pending intent flags
+ );
+ n.setLatestEventInfo(this, text, text, pi);
+
+ nm.notify(NOTIF_ID, n);
+ }
+
+ private void removeNotification() {
+ NotificationManager nm = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
+ nm.cancel(NOTIF_ID);
+ }
+}
diff --git a/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MainActivity.java b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MainActivity.java
new file mode 100755
index 0000000..fb3d223
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MainActivity.java
@@ -0,0 +1,219 @@
+/*
+ * Copyright (C) 2012 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.sdkcontroller;
+
+import android.app.Activity;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.content.ServiceConnection;
+import android.os.Bundle;
+import android.os.IBinder;
+import android.util.Log;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.widget.Button;
+import android.widget.CompoundButton;
+import android.widget.CompoundButton.OnCheckedChangeListener;
+import android.widget.TextView;
+import android.widget.ToggleButton;
+
+import com.android.tools.sdkcontroller.ControllerService.ControllerBinder;
+import com.android.tools.sdkcontroller.ControllerService.ControllerListener;
+
+public class MainActivity extends Activity {
+
+ public static String TAG = MainActivity.class.getSimpleName();
+ private static boolean DEBUG = true;
+ private Button mBtnOpenMultitouch;
+ private Button mBtnOpenSensors;
+ private ToggleButton mBtnToggleService;
+ private ServiceConnection mServiceConnection;
+ protected ControllerBinder mServiceBinder;
+ private TextView mTextError;
+ private TextView mTextStatus;
+
+ /** Called when the activity is first created. */
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ setContentView(R.layout.main);
+
+ mTextError = (TextView) findViewById(R.id.textError);
+ mTextStatus = (TextView) findViewById(R.id.textStatus);
+
+ setupButtons();
+ }
+
+ @Override
+ protected void onResume() {
+ if (DEBUG) Log.d(TAG, "onResume");
+ super.onResume();
+ bindToService();
+ updateError();
+ }
+
+ @Override
+ protected void onPause() {
+ if (DEBUG) Log.d(TAG, "onPause");
+ super.onPause();
+ // On pause we unbind but don't stop -- this is the case when the users goes home
+ // or invokes any other activity, including our owns.
+ boolean isRunning = mServiceBinder != null;
+ unbindFromService();
+ }
+
+ @Override
+ public void onBackPressed() {
+ if (DEBUG) Log.d(TAG, "onBackPressed");
+ // If back is pressed, we stop the service automatically. It seems more intuitive that way.
+ stopService();
+ super.onBackPressed();
+ }
+
+ // ----------
+
+ private void setupButtons() {
+
+ mBtnOpenMultitouch = (Button) findViewById(R.id.btnOpenMultitouch);
+ mBtnOpenSensors = (Button) findViewById(R.id.btnOpenSensors);
+
+ mBtnOpenMultitouch.setOnClickListener(new OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ // Open the multi-touch activity.
+ Intent i = new Intent(MainActivity.this, MultitouchActivity.class);
+ startActivity(i);
+ }
+ });
+
+ mBtnOpenSensors.setOnClickListener(new OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ // Open the sensor activity.
+ Intent i = new Intent(MainActivity.this, SensorActivity.class);
+ startActivity(i);
+ }
+ });
+
+ mBtnToggleService = (ToggleButton) findViewById(R.id.toggleService);
+
+ // set initial state
+ updateButtons();
+
+ mBtnToggleService.setOnCheckedChangeListener(new OnCheckedChangeListener() {
+ @Override
+ public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
+ if (isChecked) {
+ bindToService();
+ } else {
+ stopService();
+ }
+ }
+ });
+
+ }
+
+ private void updateButtons() {
+ boolean running = ControllerService.isServiceIsRunning();
+ mBtnOpenMultitouch.setEnabled(running);
+ mBtnOpenSensors.setEnabled(running);
+ mBtnToggleService.setChecked(running);
+
+ mTextStatus.setText(
+ getText(running ? R.string.main_service_status_running
+ : R.string.main_service_status_stopped));
+ }
+
+ /**
+ * Starts the service and binds to it.
+ */
+ private void bindToService() {
+ if (mServiceConnection == null) {
+ final ControllerListener listener = new OurControllerListener();
+
+ mServiceConnection = new ServiceConnection() {
+ @Override
+ public void onServiceConnected(ComponentName name, IBinder service) {
+ if (DEBUG) Log.d(TAG, "Activity connected to service");
+ mServiceBinder = (ControllerBinder) service;
+ mServiceBinder.addListener(listener);
+ updateButtons();
+ }
+
+ @Override
+ public void onServiceDisconnected(ComponentName name) {
+ if (DEBUG) Log.d(TAG, "Activity disconnected from service");
+ mServiceBinder = null;
+ updateButtons();
+ }
+ };
+ }
+
+ // Start service so that it doesn't stop when we unbind
+ if (DEBUG) Log.d(TAG, "start requested & bind service");
+ Intent service = new Intent(this, ControllerService.class);
+ startService(service);
+ bindService(service,
+ mServiceConnection,
+ Context.BIND_AUTO_CREATE);
+ }
+
+ /**
+ * Unbinds from the service but does not actually stop the service.
+ * This lets us have it run in the background even if this isn't the active app.
+ */
+ private void unbindFromService() {
+ if (mServiceConnection != null) {
+ if (DEBUG) Log.d(TAG, "unbind service");
+ unbindService(mServiceConnection);
+ mServiceConnection = null;
+ }
+ }
+
+ /**
+ * Unbind and then actually stops the service.
+ */
+ private void stopService() {
+ Intent service = new Intent(this, ControllerService.class);
+ unbindFromService();
+ if (DEBUG) Log.d(TAG, "stop service requested");
+ stopService(service);
+ }
+
+ private class OurControllerListener implements ControllerListener {
+ @Override
+ public void onErrorChanged(String error) {
+ runOnUiThread(new Runnable() {
+ @Override
+ public void run() {
+ updateError();
+ }
+ });
+ }
+ }
+
+ private void updateError() {
+ String error = mServiceBinder == null ? "" : mServiceBinder.getSensorErrors();
+ if (error == null) {
+ error = "";
+ }
+
+ mTextError.setVisibility(error.length() == 0 ? View.GONE : View.VISIBLE);
+ mTextError.setText(error);
+ }
+} \ No newline at end of file
diff --git a/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MultitouchActivity.java b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MultitouchActivity.java
new file mode 100755
index 0000000..fd9bf22
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/MultitouchActivity.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2012 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.sdkcontroller;
+
+import android.app.Activity;
+import android.os.Bundle;
+
+public class MultitouchActivity extends Activity {
+
+ public static String TAG = MultitouchActivity.class.getSimpleName();
+ @SuppressWarnings("unused")
+ private static boolean DEBUG = true;
+
+ /** Called when the activity is first created. */
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ //TODO setContentView(R.layout.multitouch);
+ }
+}
diff --git a/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/SensorActivity.java b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/SensorActivity.java
new file mode 100755
index 0000000..64edb01
--- /dev/null
+++ b/apps/SdkController/SdkControllerApp/src/com/android/tools/sdkcontroller/SensorActivity.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2012 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.sdkcontroller;
+
+import android.app.Activity;
+import android.os.Bundle;
+
+public class SensorActivity extends Activity {
+
+ public static String TAG = SensorActivity.class.getSimpleName();
+ @SuppressWarnings("unused")
+ private static boolean DEBUG = true;
+
+ /** Called when the activity is first created. */
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ //TODO setContentView(R.layout.sensors);
+ }
+}
diff --git a/apps/SdkController/SdkControllerLib/.classpath b/apps/SdkController/SdkControllerLib/.classpath
new file mode 100755
index 0000000..a4f1e40
--- /dev/null
+++ b/apps/SdkController/SdkControllerLib/.classpath
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+ <classpathentry kind="src" path="src"/>
+ <classpathentry kind="src" path="gen"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.ANDROID_FRAMEWORK"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.LIBRARIES"/>
+ <classpathentry kind="output" path="bin/classes"/>
+</classpath>
diff --git a/apps/SdkController/SdkControllerLib/.project b/apps/SdkController/SdkControllerLib/.project
new file mode 100755
index 0000000..efa52a5
--- /dev/null
+++ b/apps/SdkController/SdkControllerLib/.project
@@ -0,0 +1,33 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+ <name>SdkControllerLib</name>
+ <comment></comment>
+ <projects>
+ </projects>
+ <buildSpec>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ResourceManagerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.PreCompilerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.jdt.core.javabuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ApkBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ </buildSpec>
+ <natures>
+ <nature>com.android.ide.eclipse.adt.AndroidNature</nature>
+ <nature>org.eclipse.jdt.core.javanature</nature>
+ </natures>
+</projectDescription>
diff --git a/apps/SdkController/SdkControllerLib/project.properties b/apps/SdkController/SdkControllerLib/project.properties
index 337e8f3..5fa344c 100755
--- a/apps/SdkController/SdkControllerLib/project.properties
+++ b/apps/SdkController/SdkControllerLib/project.properties
@@ -8,5 +8,5 @@
# project structure.
# Project target.
-target=android-7
+target=android-15
android.library=true
diff --git a/apps/SdkController/SdkControllerMultitouch/.classpath b/apps/SdkController/SdkControllerMultitouch/.classpath
new file mode 100755
index 0000000..a4f1e40
--- /dev/null
+++ b/apps/SdkController/SdkControllerMultitouch/.classpath
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+ <classpathentry kind="src" path="src"/>
+ <classpathentry kind="src" path="gen"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.ANDROID_FRAMEWORK"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.LIBRARIES"/>
+ <classpathentry kind="output" path="bin/classes"/>
+</classpath>
diff --git a/apps/SdkController/SdkControllerMultitouch/.project b/apps/SdkController/SdkControllerMultitouch/.project
new file mode 100755
index 0000000..7498997
--- /dev/null
+++ b/apps/SdkController/SdkControllerMultitouch/.project
@@ -0,0 +1,33 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+ <name>SdkControllerMultitouch</name>
+ <comment></comment>
+ <projects>
+ </projects>
+ <buildSpec>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ResourceManagerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.PreCompilerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.jdt.core.javabuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ApkBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ </buildSpec>
+ <natures>
+ <nature>com.android.ide.eclipse.adt.AndroidNature</nature>
+ <nature>org.eclipse.jdt.core.javanature</nature>
+ </natures>
+</projectDescription>
diff --git a/apps/SdkController/SdkControllerMultitouch/project.properties b/apps/SdkController/SdkControllerMultitouch/project.properties
index d3d8dc4..1234e7b 100644
--- a/apps/SdkController/SdkControllerMultitouch/project.properties
+++ b/apps/SdkController/SdkControllerMultitouch/project.properties
@@ -8,5 +8,5 @@
# project structure.
# Project target.
-target=android-7
+target=android-15
android.library.reference.1=../SdkControllerLib
diff --git a/apps/SdkController/SdkControllerSensor/.classpath b/apps/SdkController/SdkControllerSensor/.classpath
new file mode 100755
index 0000000..a4f1e40
--- /dev/null
+++ b/apps/SdkController/SdkControllerSensor/.classpath
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<classpath>
+ <classpathentry kind="src" path="src"/>
+ <classpathentry kind="src" path="gen"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.ANDROID_FRAMEWORK"/>
+ <classpathentry kind="con" path="com.android.ide.eclipse.adt.LIBRARIES"/>
+ <classpathentry kind="output" path="bin/classes"/>
+</classpath>
diff --git a/apps/SdkController/SdkControllerSensor/.project b/apps/SdkController/SdkControllerSensor/.project
new file mode 100755
index 0000000..4a5bf31
--- /dev/null
+++ b/apps/SdkController/SdkControllerSensor/.project
@@ -0,0 +1,33 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+ <name>SdkControllerSensor</name>
+ <comment></comment>
+ <projects>
+ </projects>
+ <buildSpec>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ResourceManagerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.PreCompilerBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.jdt.core.javabuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>com.android.ide.eclipse.adt.ApkBuilder</name>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ </buildSpec>
+ <natures>
+ <nature>com.android.ide.eclipse.adt.AndroidNature</nature>
+ <nature>org.eclipse.jdt.core.javanature</nature>
+ </natures>
+</projectDescription>
diff --git a/apps/SdkController/SdkControllerSensor/project.properties b/apps/SdkController/SdkControllerSensor/project.properties
index d3d8dc4..1234e7b 100755
--- a/apps/SdkController/SdkControllerSensor/project.properties
+++ b/apps/SdkController/SdkControllerSensor/project.properties
@@ -8,5 +8,5 @@
# project structure.
# Project target.
-target=android-7
+target=android-15
android.library.reference.1=../SdkControllerLib