aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--assetstudio/src/com/android/assetstudiolib/ActionBarIconGenerator.java9
-rw-r--r--eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/assetstudio/ConfigureAssetSetPage.java1
-rw-r--r--eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/editors/layout/configuration/ConfigurationComposite.java25
-rw-r--r--files/devices.xml807
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Camera.java2
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Device.java13
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/DeviceManager.java61
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Hardware.java51
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Meta.java18
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Screen.java12
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Software.java15
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/devices/State.java15
-rwxr-xr-xsdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdInfo.java14
-rw-r--r--sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdManager.java36
-rwxr-xr-xsdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman1/AvdManagerPage.java23
-rwxr-xr-xsdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman2/AvdManagerWindowImpl1.java15
-rw-r--r--sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdCreationDialog.java3
-rw-r--r--sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdSelector.java59
-rw-r--r--sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdStartDialog.java25
19 files changed, 697 insertions, 507 deletions
diff --git a/assetstudio/src/com/android/assetstudiolib/ActionBarIconGenerator.java b/assetstudio/src/com/android/assetstudiolib/ActionBarIconGenerator.java
index 9ed88e9..3cd6f11 100644
--- a/assetstudio/src/com/android/assetstudiolib/ActionBarIconGenerator.java
+++ b/assetstudio/src/com/android/assetstudiolib/ActionBarIconGenerator.java
@@ -34,8 +34,11 @@ public class ActionBarIconGenerator extends GraphicGenerator {
@Override
public BufferedImage generate(GraphicGeneratorContext context, Options options) {
+ ActionBarOptions actionBarOptions = (ActionBarOptions) options;
Rectangle iconSizeMdpi = new Rectangle(0, 0, 32, 32);
- Rectangle targetRectMdpi = new Rectangle(4, 4, 24, 24);
+ Rectangle targetRectMdpi = actionBarOptions.sourceIsClipart
+ ? new Rectangle(0, 0, 32, 32)
+ : new Rectangle(4, 4, 24, 24);
final float scaleFactor = GraphicGenerator.getMdpiScaleFactor(options.density);
Rectangle imageRect = Util.scaleRectangle(iconSizeMdpi, scaleFactor);
Rectangle targetRect = Util.scaleRectangle(targetRectMdpi, scaleFactor);
@@ -47,7 +50,6 @@ public class ActionBarIconGenerator extends GraphicGenerator {
Graphics2D g2 = (Graphics2D) tempImage.getGraphics();
Util.drawCenterInside(g2, options.sourceImage, targetRect);
- ActionBarOptions actionBarOptions = (ActionBarOptions) options;
if (actionBarOptions.theme == Theme.HOLO_LIGHT) {
Util.drawEffects(g, tempImage, 0, 0, new Effect[] {
new FillEffect(new Color(0x333333), 0.6),
@@ -69,6 +71,9 @@ public class ActionBarIconGenerator extends GraphicGenerator {
public static class ActionBarOptions extends GraphicGenerator.Options {
/** The theme to generate icons for */
public Theme theme = Theme.HOLO_LIGHT;
+
+ /** Whether or not the source image is a clipart source */
+ public boolean sourceIsClipart = false;
}
/** The themes to generate action bar icons for */
diff --git a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/assetstudio/ConfigureAssetSetPage.java b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/assetstudio/ConfigureAssetSetPage.java
index 567ffab..426dbae 100644
--- a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/assetstudio/ConfigureAssetSetPage.java
+++ b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/assetstudio/ConfigureAssetSetPage.java
@@ -1142,6 +1142,7 @@ public class ConfigureAssetSetPage extends WizardPage implements SelectionListen
actionBarOptions.theme = mValues.holoDark
? ActionBarIconGenerator.Theme.HOLO_DARK
: ActionBarIconGenerator.Theme.HOLO_LIGHT;
+ actionBarOptions.sourceIsClipart = (mValues.sourceType == SourceType.CLIPART);
options = actionBarOptions;
break;
diff --git a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/editors/layout/configuration/ConfigurationComposite.java b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/editors/layout/configuration/ConfigurationComposite.java
index 899e31e..b5869ce 100644
--- a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/editors/layout/configuration/ConfigurationComposite.java
+++ b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/editors/layout/configuration/ConfigurationComposite.java
@@ -69,6 +69,7 @@ import com.android.sdklib.IAndroidTarget;
import com.android.sdklib.devices.Device;
import com.android.sdklib.devices.DeviceManager;
import com.android.sdklib.devices.State;
+import com.android.sdklib.devices.DeviceManager.DevicesChangeListener;
import com.android.sdklib.internal.avd.AvdInfo;
import com.android.sdklib.internal.avd.AvdManager;
import com.android.sdklib.repository.PkgProps;
@@ -97,6 +98,7 @@ import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Menu;
@@ -145,7 +147,8 @@ import java.util.TreeMap;
* - Target reload. This is when the target used by the project is the edited file has finished<br>
* loading.<br>
*/
-public class ConfigurationComposite extends Composite implements SelectionListener {
+public class ConfigurationComposite extends Composite
+ implements SelectionListener, DevicesChangeListener {
public static final String ATTR_CONTEXT = "context"; //$NON-NLS-1$
private static final String ICON_SQUARE = "square"; //$NON-NLS-1$
private static final String ICON_LANDSCAPE = "landscape"; //$NON-NLS-1$
@@ -2669,13 +2672,7 @@ public class ConfigurationComposite extends Composite implements SelectionListen
if (sdk != null) {
mDeviceList = sdk.getDevices();
DeviceManager manager = sdk.getDeviceManager();
- manager.registerListener(new DeviceManager.DevicesChangeListener() {
- @Override
- public void onDevicesChange() {
- mDeviceList = sdk.getDevices();
- addDeviceMenuListener(mDeviceCombo);
- }
- });
+ manager.registerListener(this);
} else {
mDeviceList = new ArrayList<Device>();
}
@@ -2690,6 +2687,18 @@ public class ConfigurationComposite extends Composite implements SelectionListen
selectDevice(null);
}
}
+
+ @Override
+ public void onDevicesChange() {
+ final Sdk sdk = Sdk.getCurrent();
+ mDeviceList = sdk.getDevices();
+ Display.getDefault().asyncExec(new Runnable() {
+ @Override
+ public void run() {
+ addDeviceMenuListener(mDeviceCombo);
+ }
+ });
+ }
Image getOrientationIcon(ScreenOrientation orientation, boolean flip) {
IconFactory icons = IconFactory.getInstance();
diff --git a/files/devices.xml b/files/devices.xml
index c9eb890..ec8d936 100644
--- a/files/devices.xml
+++ b/files/devices.xml
@@ -1,452 +1,407 @@
-<?xml version="1.0"?>
-<d:layout-devices
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xmlns:d="http://schemas.android.com/sdk/android/layout-devices/1">
+<?xml version="1.0" encoding="UTF-8"?>
- <d:device name="2.7in QVGA">
- <d:default>
- <d:screen-size>small</d:screen-size>
- <d:screen-ratio>notlong</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>ldpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>240</d:size>
- <d:size>320</d:size>
- </d:screen-dimension>
- <d:xdpi>145</d:xdpi>
- <d:ydpi>145</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
+<d:devices xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns:d="http://schemas.android.com/sdk/devices/1">
- <d:device name="2.7in QVGA slider">
- <d:default>
- <d:screen-size>small</d:screen-size>
- <d:screen-ratio>notlong</d:screen-ratio>
+ <d:device>
+ <d:name>Nexus One</d:name>
+ <d:manufacturer>HTC</d:manufacturer>
+ <d:hardware>
+ <d:screen>
+ <d:screen-size>normal</d:screen-size>
+ <d:diagonal-length>3.7</d:diagonal-length>
+ <d:pixel-density>hdpi</d:pixel-density>
+ <d:screen-ratio>long</d:screen-ratio>
+ <d:dimensions>
+ <d:x-dimension>480</d:x-dimension>
+ <d:y-dimension>720</d:y-dimension>
+ </d:dimensions>
+ <d:xdpi>254</d:xdpi>
+ <d:ydpi>254</d:ydpi>
+ <d:touch>
+ <d:multitouch>basic</d:multitouch>
+ <d:mechanism>finger</d:mechanism>
+ <d:screen-type>capacitive</d:screen-type>
+ </d:touch>
+ </d:screen>
+ <d:networking>
+ Wifi
+ Bluetooth
+ </d:networking>
+ <d:sensors>
+ Accelerometer
+ Compass
+ GPS
+ LightSensor
+ ProximitySensor
+ </d:sensors>
+ <d:mic>true</d:mic>
+ <d:camera>
+ <d:location>back</d:location>
+ <d:autofocus>true</d:autofocus>
+ <d:flash>true</d:flash>
+ </d:camera>
+ <d:keyboard>nokeys</d:keyboard>
+ <d:nav>trackball</d:nav>
+ <d:ram unit="MiB">512</d:ram>
+ <d:buttons>hard</d:buttons>
+ <d:internal-storage unit="MiB">503</d:internal-storage>
+ <d:removable-storage unit="MiB">0</d:removable-storage>
+ <d:cpu>Qualcomm Scorpion</d:cpu>
+ <d:gpu>Qualcomm Adreno 200</d:gpu>
+ <d:abi>
+ armeabi-v7a
+ armeabi
+ </d:abi>
+ <d:dock> </d:dock>
+ <d:power-type>plugged-in</d:power-type>
+ </d:hardware>
+ <d:software>
+ <d:api-level>7-10</d:api-level>
+ <d:live-wallpaper-support>true</d:live-wallpaper-support>
+ <d:bluetooth-profiles> </d:bluetooth-profiles>
+ <d:gl-version>2.0</d:gl-version>
+ <d:gl-extensions>
+ </d:gl-extensions>
+ <d:status-bar>true</d:status-bar>
+ </d:software>
+ <d:state name="Portrait" default="true">
+ <d:description>The phone in portrait view</d:description>
<d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>ldpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:text-input-method>qwerty</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>240</d:size>
- <d:size>320</d:size>
- </d:screen-dimension>
- <d:xdpi>145</d:xdpi>
- <d:ydpi>145</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape, closed">
<d:keyboard-state>keyssoft</d:keyboard-state>
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
+ <d:state name="Landscape">
+ <d:description>The phone in landscape view</d:description>
<d:screen-orientation>land</d:screen-orientation>
- </d:config>
- <d:config name="Landscape, open">
- <d:keyboard-state>keysexposed</d:keyboard-state>
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="3.2in HVGA slider (ADP1)">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>notlong</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>mdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:text-input-method>qwerty</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>trackball</d:nav-method>
- <d:screen-dimension>
- <d:size>320</d:size>
- <d:size>480</d:size>
- </d:screen-dimension>
- <d:xdpi>180.6</d:xdpi>
- <d:ydpi>182</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape, closed">
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- <d:config name="Landscape, open">
- <d:keyboard-state>keysexposed</d:keyboard-state>
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="3.2in HVGA (ADP2)">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>notlong</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>mdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>trackball</d:nav-method>
- <d:screen-dimension>
- <d:size>320</d:size>
- <d:size>480</d:size>
- </d:screen-dimension>
- <d:xdpi>180.6</d:xdpi>
- <d:ydpi>182</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
</d:device>
-
- <d:device name="3.3in WQVGA">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
+ <d:device>
+ <d:name>Nexus S</d:name>
+ <d:manufacturer>Samsung</d:manufacturer>
+ <d:hardware>
+ <d:screen>
+ <d:screen-size>normal</d:screen-size>
+ <d:diagonal-length>4</d:diagonal-length>
+ <d:pixel-density>hdpi</d:pixel-density>
+ <d:screen-ratio>long</d:screen-ratio>
+ <d:dimensions>
+ <d:x-dimension>480</d:x-dimension>
+ <d:y-dimension>800</d:y-dimension>
+ </d:dimensions>
+ <d:xdpi>235</d:xdpi>
+ <d:ydpi>235</d:ydpi>
+ <d:touch>
+ <d:multitouch>jazz-hands</d:multitouch>
+ <d:mechanism>finger</d:mechanism>
+ <d:screen-type>capacitive</d:screen-type>
+ </d:touch>
+ </d:screen>
+ <d:networking>
+ Wifi
+ Bluetooth
+ NFC
+ </d:networking>
+ <d:sensors>
+ Accelerometer
+ Compass
+ GPS
+ Gyroscope
+ LightSensor
+ ProximitySensor
+ </d:sensors>
+ <d:mic>true</d:mic>
+ <d:camera>
+ <d:location>back</d:location>
+ <d:autofocus>true</d:autofocus>
+ <d:flash>true</d:flash>
+ </d:camera>
+ <d:camera>
+ <d:location>front</d:location>
+ <d:autofocus>false</d:autofocus>
+ <d:flash>false</d:flash>
+ </d:camera>
+ <d:keyboard>nokeys</d:keyboard>
+ <d:nav>nonav</d:nav>
+ <d:ram unit="KiB">351428</d:ram>
+ <d:buttons>hard</d:buttons>
+ <d:internal-storage unit="MiB">503</d:internal-storage>
+ <d:removable-storage unit="MiB">0</d:removable-storage>
+ <d:cpu>Samsung Exynos 3110</d:cpu>
+ <d:gpu>PowerVR SGX 540</d:gpu>
+ <d:abi>
+ armeabi-v7a
+ armeabi
+ </d:abi>
+ <d:dock> </d:dock>
+ <d:power-type>plugged-in</d:power-type>
+ </d:hardware>
+ <d:software>
+ <d:api-level>9-16</d:api-level>
+ <d:live-wallpaper-support>true</d:live-wallpaper-support>
+ <d:bluetooth-profiles> </d:bluetooth-profiles>
+ <d:gl-version>2.0</d:gl-version>
+ <d:gl-extensions>
+ GL_EXT_debug_marker
+ GL_OES_rgb8_rgba8
+ GL_OES_depth24
+ GL_OES_vertex_half_float
+ GL_OES_texture_float
+ GL_OES_texture_half_float
+ GL_OES_element_index_uint
+ GL_OES_mapbuffer
+ GL_OES_fragment_precision_high
+ GL_OES_compressed_ETC1_RGB8_texture
+ GL_OES_EGL_image
+ GL_OES_EGL_image_external
+ GL_OES_required_internalformat
+ GL_OES_depth_texture
+ GL_OES_get_program_binary
+ GL_OES_packed_depth_stencil
+ GL_OES_standard_derivatives
+ GL_OES_vertex_array_object
+ GL_OES_egl_sync
+ GL_EXT_multi_draw_arrays
+ GL_EXT_texture_format_BGRA8888
+ GL_EXT_discard_framebuffer
+ GL_EXT_shader_texture_lod
+ GL_IMG_shader_binary
+ GL_IMG_texture_compression_pvrtc
+ GL_IMG_texture_npot
+ GL_IMG_texture_format_BGRA8888
+ GL_IMG_read_format
+ GL_IMG_program_binary
+ GL_IMG_multisampled_render_to_texture
+ </d:gl-extensions>
+ <d:status-bar>true</d:status-bar>
+ </d:software>
+ <d:state name="Portrait" default="true">
+ <d:description>The phone in portrait view</d:description>
<d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>ldpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>240</d:size>
- <d:size>400</d:size>
- </d:screen-dimension>
- <d:xdpi>141</d:xdpi>
- <d:ydpi>141</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
+ <d:state name="Landscape">
+ <d:description>The phone in landscape view</d:description>
<d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
- <d:device name="3.4in FWQVGA">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>ldpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>240</d:size>
- <d:size>432</d:size>
- </d:screen-dimension>
- <d:xdpi>145</d:xdpi>
- <d:ydpi>145</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
</d:device>
- <d:device name="3.7in WVGA (Nexus One)">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
+ <d:device>
+ <d:name>
+ Galaxy Nexus
+ </d:name>
+ <d:manufacturer>
+ Samsung
+ </d:manufacturer>
+ <d:hardware>
+ <d:screen>
+ <d:screen-size>normal</d:screen-size>
+ <d:diagonal-length>4.65</d:diagonal-length> <!-- In inches -->
+ <d:pixel-density>xhdpi</d:pixel-density>
+ <d:screen-ratio>long</d:screen-ratio>
+ <d:dimensions>
+ <d:x-dimension>720</d:x-dimension>
+ <d:y-dimension>1280</d:y-dimension>
+ </d:dimensions>
+ <d:xdpi>316</d:xdpi>
+ <d:ydpi>316</d:ydpi>
+ <d:touch>
+ <d:multitouch>jazz-hands</d:multitouch>
+ <d:mechanism>finger</d:mechanism>
+ <d:screen-type>capacitive</d:screen-type>
+ </d:touch>
+ </d:screen>
+ <d:networking>
+ Bluetooth
+ Wifi
+ NFC
+ </d:networking>
+ <d:sensors>
+ Accelerometer
+ Barometer
+ Gyroscope
+ Compass
+ GPS
+ ProximitySensor
+ </d:sensors>
+ <d:mic>true</d:mic>
+ <d:camera>
+ <d:location>front</d:location>
+ <d:autofocus>true</d:autofocus>
+ <d:flash>false</d:flash>
+ </d:camera>
+ <d:camera>
+ <d:location>back</d:location>
+ <d:autofocus>true</d:autofocus>
+ <d:flash>true</d:flash>
+ </d:camera>
+ <d:keyboard>nokeys</d:keyboard>
+ <d:nav>nonav</d:nav>
+ <d:ram unit="GiB">1</d:ram>
+ <d:buttons>soft</d:buttons>
+ <d:internal-storage unit="GiB">16</d:internal-storage>
+ <d:removable-storage unit="KiB"></d:removable-storage>
+ <d:cpu>OMAP 4460</d:cpu> <!-- cpu type (Tegra3) freeform -->
+ <d:gpu>PowerVR SGX540</d:gpu>
+ <d:abi>
+ armeabi
+ armeabi-v7a
+ </d:abi>
+ <!--dock (car, desk, tv, none)-->
+ <d:dock>
+ </d:dock>
+ <!-- plugged in (never, charge, always) -->
+ <d:power-type>battery</d:power-type>
+ </d:hardware>
+ <d:software>
+ <d:api-level>14-</d:api-level>
+ <d:live-wallpaper-support>true</d:live-wallpaper-support>
+ <d:bluetooth-profiles>
+ HSP
+ HFP
+ SPP
+ A2DP
+ AVRCP
+ OPP
+ PBAP
+ GAVDP
+ AVDTP
+ HID
+ HDP
+ PAN
+ </d:bluetooth-profiles>
+ <d:gl-version>2.0</d:gl-version>
+ <!--
+ These can be gotten via
+ javax.microedition.khronos.opengles.GL10.glGetString(GL10.GL_EXTENSIONS);
+ -->
+ <d:gl-extensions>
+ GL_EXT_discard_framebuffer
+ GL_EXT_multi_draw_arrays
+ GL_EXT_shader_texture_lod
+ GL_EXT_texture_format_BGRA8888
+ GL_IMG_multisampled_render_to_texture
+ GL_IMG_program_binary
+ GL_IMG_read_format
+ GL_IMG_shader_binary
+ GL_IMG_texture_compression_pvrtc
+ GL_IMG_texture_format_BGRA8888
+ GL_IMG_texture_npot
+ GL_OES_compressed_ETC1_RGB8_texture
+ GL_OES_depth_texture
+ GL_OES_depth24
+ GL_OES_EGL_image
+ GL_OES_EGL_image_external
+ GL_OES_egl_sync
+ GL_OES_element_index_uint
+ GL_OES_fragment_precision_high
+ GL_OES_get_program_binary
+ GL_OES_mapbuffer
+ GL_OES_packed_depth_stencil
+ GL_OES_required_internalformat
+ GL_OES_rgb8_rgba8
+ GL_OES_standard_derivatives
+ GL_OES_texture_float
+ GL_OES_texture_half_float
+ GL_OES_vertex_array_object
+ GL_OES_vertex_half_float
+ </d:gl-extensions>
+ <d:status-bar>true</d:status-bar>
+ </d:software>
+ <d:state name="Portrait" default="true">
+ <d:description>The phone in portrait view</d:description>
<d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>hdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>trackball</d:nav-method>
- <d:screen-dimension>
- <d:size>480</d:size>
- <d:size>800</d:size>
- </d:screen-dimension>
- <d:xdpi>254</d:xdpi>
- <d:ydpi>254</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
+ <d:state name="Landscape">
+ <d:description>The phone in landscape view</d:description>
<d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="3.7in FWVGA slider">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>hdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:text-input-method>qwerty</d:text-input-method>
- <d:nav-state>navhidden</d:nav-state>
- <d:nav-method>dpad</d:nav-method>
- <d:screen-dimension>
- <d:size>480</d:size>
- <d:size>854</d:size>
- </d:screen-dimension>
- <d:xdpi>265</d:xdpi>
- <d:ydpi>265</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape, closed">
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- <d:config name="Landscape, open">
- <d:keyboard-state>keysexposed</d:keyboard-state>
- <d:screen-orientation>land</d:screen-orientation>
- <d:nav-state>navexposed</d:nav-state>
- </d:config>
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
</d:device>
+ <d:device>
+ <d:name>Nexus 7</d:name>
+ <d:manufacturer>Asus</d:manufacturer>
+ <d:hardware>
+ <d:screen>
+ <d:screen-size>large</d:screen-size>
+ <d:diagonal-length>7.27</d:diagonal-length>
+ <d:pixel-density>tvdpi</d:pixel-density>
+ <d:screen-ratio>notlong</d:screen-ratio>
+ <d:dimensions>
+ <d:x-dimension>800</d:x-dimension>
+ <d:y-dimension>1280</d:y-dimension>
+ </d:dimensions>
+ <d:xdpi>195</d:xdpi>
+ <d:ydpi>200</d:ydpi>
+ <d:touch>
+ <d:multitouch>jazz-hands</d:multitouch>
+ <d:mechanism>finger</d:mechanism>
+ <d:screen-type>capacitive</d:screen-type>
+ </d:touch>
+ </d:screen>
+ <d:networking>
+ Wifi
+ Bluetooth
+ NFC
+ </d:networking>
+ <d:sensors>
+ Accelerometer
+ Compass
+ GPS
+ Gyroscope
+ LightSensor
+ </d:sensors>
+ <d:mic>true</d:mic>
+ <d:camera>
+ <d:location>front</d:location>
+ <d:autofocus>false</d:autofocus>
+ <d:flash>false</d:flash>
+ </d:camera>
+ <d:keyboard>nokeys</d:keyboard>
+ <d:nav>nonav</d:nav>
+ <d:ram unit="GiB">1</d:ram>
+ <d:buttons>soft</d:buttons>
+ <d:internal-storage unit="GiB">8</d:internal-storage>
+ <d:removable-storage unit="MiB"> </d:removable-storage>
+ <d:cpu> Tegra3 </d:cpu>
+ <d:gpu> Tegra3 </d:gpu>
+ <d:abi>
+ armeabi-v7a
+ armeabi
+ </d:abi>
+ <d:dock> </d:dock>
+ <d:power-type>battery</d:power-type>
+ </d:hardware>
- <d:device name="4in WVGA (Nexus S)">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>hdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>480</d:size>
- <d:size>800</d:size>
- </d:screen-dimension>
- <d:xdpi>235</d:xdpi>
- <d:ydpi>235</d:ydpi>
- </d:default>
+ <d:software>
+ <d:api-level>16</d:api-level>
+ <d:live-wallpaper-support>true</d:live-wallpaper-support>
+ <d:bluetooth-profiles> </d:bluetooth-profiles>
+ <d:gl-version>2.0</d:gl-version>
+ <d:gl-extensions> </d:gl-extensions>
+ <d:status-bar>true</d:status-bar>
+ </d:software>
- <d:config name="Portrait">
+ <d:state name="Portrait" default="true">
+ <d:description>The phone in portrait view</d:description>
<d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="4.65in 720p (Galaxy Nexus)">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>xhdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>720</d:size>
- <d:size>1280</d:size>
- </d:screen-dimension>
- <d:xdpi>316</d:xdpi>
- <d:ydpi>316</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
+ <d:state name="Landscape">
+ <d:description>The phone in landscape view</d:description>
<d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="4.7in WXGA">
- <d:default>
- <d:screen-size>normal</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>xhdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
<d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>1280</d:size>
- <d:size>720</d:size>
- </d:screen-dimension>
- <d:xdpi>320</d:xdpi>
- <d:ydpi>320</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
+ <d:nav-state>nonav</d:nav-state>
+ </d:state>
- <d:device name="5.1in WVGA">
- <d:default>
- <d:screen-size>large</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>mdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>480</d:size>
- <d:size>800</d:size>
- </d:screen-dimension>
- <d:xdpi>183</d:xdpi>
- <d:ydpi>183</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="5.4in FWVGA">
- <d:default>
- <d:screen-size>large</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>port</d:screen-orientation>
- <d:pixel-density>mdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>480</d:size>
- <d:size>854</d:size>
- </d:screen-dimension>
- <d:xdpi>181</d:xdpi>
- <d:ydpi>181</d:ydpi>
- </d:default>
-
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="7in WSVGA (Tablet)">
- <d:default>
- <d:screen-size>large</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>land</d:screen-orientation>
- <d:pixel-density>mdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>1024</d:size>
- <d:size>600</d:size>
- </d:screen-dimension>
- <d:xdpi>169</d:xdpi>
- <d:ydpi>169</d:ydpi>
- </d:default>
-
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="7in WXGA (Nexus 7)">
- <d:default>
- <d:screen-size>large</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>land</d:screen-orientation>
- <d:pixel-density>tvdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>1280</d:size>
- <d:size>800</d:size>
- </d:screen-dimension>
- <d:xdpi>195</d:xdpi>
- <d:ydpi>200</d:ydpi>
- </d:default>
-
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
- </d:device>
-
- <d:device name="10.1in WXGA (Tablet)">
- <d:default>
- <d:screen-size>xlarge</d:screen-size>
- <d:screen-ratio>long</d:screen-ratio>
- <d:screen-orientation>land</d:screen-orientation>
- <d:pixel-density>mdpi</d:pixel-density>
- <d:touch-type>finger</d:touch-type>
- <d:keyboard-state>keyssoft</d:keyboard-state>
- <d:text-input-method>nokeys</d:text-input-method>
- <d:nav-state>navexposed</d:nav-state>
- <d:nav-method>nonav</d:nav-method>
- <d:screen-dimension>
- <d:size>1280</d:size>
- <d:size>800</d:size>
- </d:screen-dimension>
- <d:xdpi>149</d:xdpi>
- <d:ydpi>149</d:ydpi>
- </d:default>
-
- <d:config name="Landscape">
- <d:screen-orientation>land</d:screen-orientation>
- </d:config>
- <d:config name="Portrait">
- <d:screen-orientation>port</d:screen-orientation>
- </d:config>
</d:device>
-</d:layout-devices>
+</d:devices>
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Camera.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Camera.java
index 4f26994..d7d33fe 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Camera.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Camera.java
@@ -99,7 +99,7 @@ public class Camera {
@Override
public int hashCode() {
int hash = 17;
- hash = 31 * hash + mLocation.hashCode();
+ hash = 31 * hash + mLocation.ordinal();
hash = 31 * hash + (mAutofocus ? 1 : 0);
hash = 31 * hash + (mFlash ? 1 : 0);
return hash;
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Device.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Device.java
index e4da52e..dcd82a2 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Device.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Device.java
@@ -16,13 +16,13 @@
package com.android.sdklib.devices;
+import com.android.dvlib.DeviceSchema;
+
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
-import com.android.dvlib.DeviceSchema;
-
/**
* Instances of this class contain the specifications for a device. Use the
* {@link Builder} class to construct a Device object, or the
@@ -272,10 +272,15 @@ public final class Device {
}
@Override
+ /** A hash that's stable across JVM instances */
public int hashCode() {
int hash = 17;
- hash = 31 * hash + mName.hashCode();
- hash = 31 * hash + mManufacturer.hashCode();
+ for (Character c : mName.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+ for (Character c : mManufacturer.toCharArray()) {
+ hash = 31 * hash + c;
+ }
hash = 31 * hash + mSoftware.hashCode();
hash = 31 * hash + mState.hashCode();
hash = 31 * hash + mMeta.hashCode();
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/DeviceManager.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/DeviceManager.java
index 9cf0378..8bf45fc 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/DeviceManager.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/DeviceManager.java
@@ -16,6 +16,7 @@
package com.android.sdklib.devices;
+import com.android.annotations.Nullable;
import com.android.prefs.AndroidLocation;
import com.android.prefs.AndroidLocation.AndroidLocationException;
import com.android.resources.Keyboard;
@@ -23,7 +24,6 @@ import com.android.resources.KeyboardState;
import com.android.resources.Navigation;
import com.android.sdklib.ISdkLog;
import com.android.sdklib.SdkConstants;
-import com.android.sdklib.devices.Storage.Unit;
import com.android.sdklib.internal.avd.AvdManager;
import com.android.sdklib.internal.avd.HardwareProperties;
import com.android.sdklib.repository.PkgProps;
@@ -71,6 +71,21 @@ public class DeviceManager {
private static final List<DevicesChangeListener> listeners =
Collections.synchronizedList(new ArrayList<DevicesChangeListener>());
+ public static enum DeviceStatus {
+ /**
+ * The device exists unchanged from the given configuration
+ */
+ EXISTS,
+ /**
+ * A device exists with the given name and manufacturer, but has a different configuration
+ */
+ CHANGED,
+ /**
+ * There is no device with the given name and manufacturer
+ */
+ MISSING;
+ }
+
// TODO: Refactor this to look more like AvdManager so that we don't have
// multiple instances
// in the same application, which forces us to parse the XML multiple times
@@ -104,8 +119,34 @@ public class DeviceManager {
* notifications when modifications to the {@link Device} list occur.
* @param listener The listener to remove.
*/
- public void unregisterListener(DevicesChangeListener listener) {
- listeners.remove(listener);
+ public boolean unregisterListener(DevicesChangeListener listener) {
+ return listeners.remove(listener);
+ }
+
+ public DeviceStatus getDeviceStatus(
+ @Nullable String sdkLocation, String name, String manufacturer, int hashCode) {
+ Device d = getDevice(sdkLocation, name, manufacturer);
+ if (d == null) {
+ return DeviceStatus.MISSING;
+ } else {
+ return d.hashCode() == hashCode ? DeviceStatus.EXISTS : DeviceStatus.CHANGED;
+ }
+ }
+
+ public Device getDevice(@Nullable String sdkLocation, String name, String manufacturer) {
+ List<Device> devices;
+ if (sdkLocation != null) {
+ devices = getDevices(sdkLocation);
+ } else {
+ devices = new ArrayList<Device>(getDefaultDevices());
+ devices.addAll(getUserDevices());
+ }
+ for (Device d : devices) {
+ if (d.getName().equals(name) && d.getManufacturer().equals(manufacturer)) {
+ return d;
+ }
+ }
+ return null;
}
/**
@@ -158,6 +199,15 @@ public class DeviceManager {
if (mVendorDevices == null || !mVendorDevicesLocation.equals(sdkLocation)) {
mVendorDevicesLocation = sdkLocation;
List<Device> devices = new ArrayList<Device>();
+
+ // Load devices from tools folder
+ File toolsDevices = new File(sdkLocation, SdkConstants.OS_SDK_TOOLS_LIB_FOLDER +
+ File.separator + SdkConstants.FN_DEVICES_XML);
+ if (toolsDevices.isFile()) {
+ devices.addAll(loadDevices(toolsDevices));
+ }
+
+ // Load devices from vendor extras
File extrasFolder = new File(sdkLocation, SdkConstants.FD_EXTRAS);
List<File> deviceDirs = getExtraDirs(extrasFolder);
for (File deviceDir : deviceDirs) {
@@ -290,7 +340,6 @@ public class DeviceManager {
public static Map<String, String> getHardwareProperties(State s) {
Hardware hw = s.getHardware();
Map<String, String> props = new HashMap<String, String>();
- props.put("hw.ramSize", Long.toString(hw.getRam().getSizeAsUnit(Unit.MiB)));
props.put("hw.mainKeys", getBooleanVal(hw.getButtonType().equals(ButtonType.HARD)));
props.put("hw.trackBall", getBooleanVal(hw.getNav().equals(Navigation.TRACKBALL)));
props.put("hw.keyboard", getBooleanVal(hw.getKeyboard().equals(Keyboard.QWERTY)));
@@ -302,7 +351,6 @@ public class DeviceManager {
props.put("hw.sensors.orientation", getBooleanVal(sensors.contains(Sensor.GYROSCOPE)));
props.put("hw.audioInput", getBooleanVal(hw.hasMic()));
props.put("hw.sdCard", getBooleanVal(hw.getRemovableStorage().size() > 0));
- props.put("hw.sdCard", getBooleanVal(hw.getRemovableStorage().size() > 0));
props.put("hw.lcd.density",
Integer.toString(hw.getScreen().getPixelDensity().getDpiValue()));
props.put("hw.sensors.proximity",
@@ -324,6 +372,9 @@ public class DeviceManager {
props.put("hw.keyboard.lid", getBooleanVal(true));
}
}
+ props.put(AvdManager.AVD_INI_DEVICE_HASH, Integer.toString(d.hashCode()));
+ props.put(AvdManager.AVD_INI_DEVICE_NAME, d.getName());
+ props.put(AvdManager.AVD_INI_DEVICE_MANUFACTURER, d.getManufacturer());
return props;
}
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Hardware.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Hardware.java
index 8993cd6..b12f11d 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Hardware.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Hardware.java
@@ -282,21 +282,50 @@ public class Hardware {
public int hashCode() {
int hash = 17;
hash = 31 * hash + mScreen.hashCode();
- hash = 31 * hash + mNetworking.hashCode();
- hash = 31 * hash + mSensors.hashCode();
+
+ // Since sets have no defined order, we need to hash them in such a way that order doesn't
+ // matter.
+ int temp = 0;
+ for (Network n : mNetworking) {
+ temp |= 1 << n.ordinal();
+ }
+ hash = 31 * hash + temp;
+
+ temp = 0;
+ for (Sensor s : mSensors) {
+ temp |= 1 << s.ordinal();
+ }
+
+ hash = 31 * hash + temp;
hash = 31 * hash + (mMic ? 1 : 0);
- hash = 31 * hash + mCameras.hashCode();
- hash = 31 * hash + mKeyboard.hashCode();
- hash = 31 * hash + mNav.hashCode();
+ hash = mCameras.hashCode();
+ hash = 31 * hash + mKeyboard.ordinal();
+ hash = 31 * hash + mNav.ordinal();
hash = 31 * hash + mRam.hashCode();
- hash = 31 * hash + mButtons.hashCode();
+ hash = 31 * hash + mButtons.ordinal();
hash = 31 * hash + mInternalStorage.hashCode();
hash = 31 * hash + mRemovableStorage.hashCode();
- hash = 31 * hash + mCpu.hashCode();
- hash = 31 * hash + mGpu.hashCode();
- hash = 31 * hash + mAbis.hashCode();
- hash = 31 * hash + mUiModes.hashCode();
- hash = 31 * hash + mPluggedIn.hashCode();
+
+ for (Character c : mCpu.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+
+ for (Character c : mGpu.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+
+ temp = 0;
+ for (Abi a : mAbis) {
+ temp |= 1 << a.ordinal();
+ }
+ hash = 31 * hash + temp;
+
+ temp = 0;
+ for (UiMode ui : mUiModes) {
+ temp |= 1 << ui.ordinal();
+ }
+ hash = 31 * hash + temp;
+
return hash;
}
}
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Meta.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Meta.java
index 911c286..4c19f3f 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Meta.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Meta.java
@@ -143,19 +143,27 @@ public class Meta {
public int hashCode() {
int hash = 17;
if(mIconSixteen != null){
- hash = 31 * hash + mIconSixteen.hashCode();
+ for (Character c : mIconSixteen.getAbsolutePath().toCharArray()) {
+ hash = 31 * hash + c;
+ }
}
if(mIconSixtyFour != null){
- hash = 31 * hash + mIconSixtyFour.hashCode();
+ for (Character c : mIconSixtyFour.getAbsolutePath().toCharArray()) {
+ hash = 31 * hash + c;
+ }
}
if(mFrame != null){
- hash = 31 * hash + mFrame.hashCode();
+ for (Character c : mFrame.getAbsolutePath().toCharArray()) {
+ hash = 31 * hash + c;
+ }
}
if(mFrameOffsetLandscape != null){
- hash = 31 * hash + mFrameOffsetLandscape.hashCode();
+ hash = 31 * hash + mFrameOffsetLandscape.x;
+ hash = 31 * hash + mFrameOffsetLandscape.y;
}
if(mFrameOffsetPortrait != null){
- hash = 31 * hash + mFrameOffsetPortrait.hashCode();
+ hash = 31 * hash + mFrameOffsetPortrait.x;
+ hash = 31 * hash + mFrameOffsetPortrait.y;
}
return hash;
}
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Screen.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Screen.java
index 958219d..a7f4334 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Screen.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Screen.java
@@ -170,20 +170,20 @@ public class Screen {
@Override
public int hashCode() {
int hash = 17;
- hash = 31 * hash + mScreenSize.hashCode();
+ hash = 31 * hash + mScreenSize.ordinal();
long f = Double.doubleToLongBits(mDiagonalLength);
hash = 31 * hash + (int) (f ^ (f >>> 32));
- hash = 31 * hash + mPixelDensity.hashCode();
- hash = 31 * hash + mScreenRatio.hashCode();
+ hash = 31 * hash + mPixelDensity.ordinal();
+ hash = 31 * hash + mScreenRatio.ordinal();
hash = 31 * hash + mXDimension;
hash = 31 * hash + mYDimension;
f = Double.doubleToLongBits(mXdpi);
hash = 31 * hash + (int) (f ^ (f >>> 32));
f = Double.doubleToLongBits(mYdpi);
hash = 31 * hash + (int) (f ^ (f >>> 32));
- hash = 31 * hash + mMultitouch.hashCode();
- hash = 31 * hash + mMechanism.hashCode();
- hash = 31 * hash + mScreenType.hashCode();
+ hash = 31 * hash + mMultitouch.ordinal();
+ hash = 31 * hash + mMechanism.ordinal();
+ hash = 31 * hash + mScreenType.ordinal();
return hash;
}
}
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Software.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Software.java
index a452b6e..58f13b0 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Software.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/Software.java
@@ -125,14 +125,23 @@ public class Software {
}
@Override
+ /** A stable hash across JVM instances */
public int hashCode() {
int hash = 17;
hash = 31 * hash + mMinSdkLevel;
hash = 31 * hash + mMaxSdkLevel;
hash = 31 * hash + (mLiveWallpaperSupport ? 1 : 0);
- hash = 31 * hash + mBluetoothProfiles.hashCode();
- hash = 31 * hash + mGlVersion.hashCode();
- hash = 31 * hash + mGlExtensions.hashCode();
+ for (BluetoothProfile bp : mBluetoothProfiles) {
+ hash = 31 * hash + bp.ordinal();
+ }
+ for (Character c : mGlVersion.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+ for (String glExtension : mGlExtensions) {
+ for (Character c : glExtension.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+ }
hash = 31 * hash + (mStatusBar ? 1 : 0);
return hash;
}
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/State.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/State.java
index eb75605..1dc6961 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/State.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/devices/State.java
@@ -125,12 +125,17 @@ public class State {
public int hashCode() {
int hash = 17;
hash = 31 * hash + (mDefaultState ? 1 : 0);
- hash = 31 * hash + mName.hashCode();
- hash = 31 * hash + mDescription.hashCode();
- hash = 31 * hash + mOrientation.hashCode();
- hash = 31 * hash + mKeyState.hashCode();
- hash = 31 * hash + mNavState.hashCode();
+ for (Character c : mName.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+ for (Character c : mDescription.toCharArray()) {
+ hash = 31 * hash + c;
+ }
+ hash = 31 * hash + mOrientation.ordinal();
+ hash = 31 * hash + mKeyState.ordinal();
+ hash = 31 * hash + mNavState.ordinal();
hash = 31 * hash + mHardwareOverride.hashCode();
return hash;
}
+
}
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdInfo.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdInfo.java
index 54e2fa7..d2ec9db 100755
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdInfo.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdInfo.java
@@ -46,7 +46,11 @@ public final class AvdInfo implements Comparable<AvdInfo> {
/** Unable to parse config.ini */
ERROR_PROPERTIES,
/** System Image folder in config.ini doesn't exist */
- ERROR_IMAGE_DIR;
+ ERROR_IMAGE_DIR,
+ /** The {@link Device} this AVD is based on has changed from its original configuration*/
+ ERROR_DEVICE_CHANGED,
+ /** The {@link Device} this AVD is based on is no longer available */
+ ERROR_DEVICE_MISSING;
}
private final String mName;
@@ -284,6 +288,14 @@ public final class AvdInfo implements Comparable<AvdInfo> {
return String.format(
"Invalid value in image.sysdir. Run 'android update avd -n %1$s'",
mName);
+ case ERROR_DEVICE_CHANGED:
+ return String.format("%1$s %2$s configuration has changed since AVD creation",
+ mProperties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER),
+ mProperties.get(AvdManager.AVD_INI_DEVICE_NAME));
+ case ERROR_DEVICE_MISSING:
+ return String.format("%1$s %2$s no longer exists as a device",
+ mProperties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER),
+ mProperties.get(AvdManager.AVD_INI_DEVICE_NAME));
case OK:
assert false;
return null;
diff --git a/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdManager.java b/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdManager.java
index 1a13a5e..52ce5d6 100644
--- a/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdManager.java
+++ b/sdkmanager/libs/sdklib/src/com/android/sdklib/internal/avd/AvdManager.java
@@ -25,6 +25,8 @@ import com.android.sdklib.ISdkLog;
import com.android.sdklib.ISystemImage;
import com.android.sdklib.SdkConstants;
import com.android.sdklib.SdkManager;
+import com.android.sdklib.devices.DeviceManager;
+import com.android.sdklib.devices.DeviceManager.DeviceStatus;
import com.android.sdklib.internal.avd.AvdInfo.AvdStatus;
import com.android.sdklib.internal.project.ProjectProperties;
import com.android.sdklib.util.GrabProcessOutput;
@@ -182,6 +184,11 @@ public class AvdManager {
public final static String AVD_INI_DATA_PARTITION_SIZE = "disk.dataPartition.size";
/**
+ * AVD/config.ini key name representing the hash of the device this AVD is based on
+ */
+ public final static String AVD_INI_DEVICE_HASH = "hw.device.hash";
+
+ /**
* Pattern to match pixel-sized skin "names", e.g. "320x480".
*/
public final static Pattern NUMERIC_SKIN_SIZE = Pattern.compile("([0-9]{2,})x([0-9]{2,})"); //$NON-NLS-1$
@@ -1389,6 +1396,20 @@ public class AvdManager {
}
}
+ // Get the device status if this AVD is associated with a device
+ DeviceStatus deviceStatus = null;
+ if (properties != null) {
+ String deviceName = properties.get(AVD_INI_DEVICE_NAME);
+ String deviceMfctr = properties.get(AVD_INI_DEVICE_MANUFACTURER);
+ String hash = properties.get(AVD_INI_DEVICE_HASH);
+ if (deviceName != null && deviceMfctr != null && hash != null) {
+ int deviceHash = Integer.parseInt(hash);
+ deviceStatus = (new DeviceManager(log)).getDeviceStatus(
+ mSdkManager.getLocation(), deviceName, deviceMfctr, deviceHash);
+ }
+ }
+
+
// TODO: What about missing sdcard, skins, etc?
AvdStatus status;
@@ -1405,6 +1426,10 @@ public class AvdManager {
status = AvdStatus.ERROR_PROPERTIES;
} else if (validImageSysdir == false) {
status = AvdStatus.ERROR_IMAGE_DIR;
+ } else if (deviceStatus == DeviceStatus.CHANGED) {
+ status = AvdStatus.ERROR_DEVICE_CHANGED;
+ } else if (deviceStatus == DeviceStatus.MISSING) {
+ status = AvdStatus.ERROR_DEVICE_MISSING;
} else {
status = AvdStatus.OK;
}
@@ -1579,10 +1604,16 @@ public class AvdManager {
//FIXME: display paths to empty image folders?
status = AvdStatus.ERROR_IMAGE_DIR;
}
+ updateAvd(avd, properties, status, log);
+ }
+ public void updateAvd(AvdInfo avd,
+ Map<String, String> newProperties,
+ AvdStatus status,
+ ISdkLog log) throws IOException {
// now write the config file
File configIniFile = new File(avd.getDataFolderPath(), CONFIG_INI);
- writeIniFile(configIniFile, properties);
+ writeIniFile(configIniFile, newProperties);
// finally create a new AvdInfo for this unbroken avd and add it to the list.
// instead of creating the AvdInfo object directly we reparse it, to detect other possible
@@ -1595,8 +1626,7 @@ public class AvdManager {
avd.getTargetHash(),
avd.getTarget(),
avd.getAbiType(),
- properties,
- status);
+ newProperties);
replaceAvd(avd, newAvd);
}
diff --git a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman1/AvdManagerPage.java b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman1/AvdManagerPage.java
index 63c53e0..6408a27 100755
--- a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman1/AvdManagerPage.java
+++ b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman1/AvdManagerPage.java
@@ -17,6 +17,8 @@
package com.android.sdkuilib.internal.repository.sdkman1;
import com.android.prefs.AndroidLocation.AndroidLocationException;
+import com.android.sdklib.devices.DeviceManager;
+import com.android.sdklib.devices.DeviceManager.DevicesChangeListener;
import com.android.sdkuilib.internal.repository.UpdaterData;
import com.android.sdkuilib.internal.repository.UpdaterPage;
import com.android.sdkuilib.internal.widgets.AvdSelector;
@@ -29,23 +31,29 @@ import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Label;
-public class AvdManagerPage extends UpdaterPage implements ISdkChangeListener {
+public class AvdManagerPage extends UpdaterPage implements ISdkChangeListener, DevicesChangeListener {
private AvdSelector mAvdSelector;
private final UpdaterData mUpdaterData;
-
+ private final DeviceManager mDeviceManager;
/**
* Create the composite.
* @param parent The parent of the composite.
* @param updaterData An instance of {@link UpdaterData}.
*/
- public AvdManagerPage(Composite parent, int swtStyle, UpdaterData updaterData) {
+ public AvdManagerPage(Composite parent,
+ int swtStyle,
+ UpdaterData updaterData,
+ DeviceManager deviceManager) {
super(parent, swtStyle);
mUpdaterData = updaterData;
mUpdaterData.addListeners(this);
+ mDeviceManager = deviceManager;
+ mDeviceManager.registerListener(this);
+
createContents(this);
postCreate(); //$hide$
}
@@ -79,6 +87,7 @@ public class AvdManagerPage extends UpdaterPage implements ISdkChangeListener {
@Override
public void dispose() {
mUpdaterData.removeListener(this);
+ mDeviceManager.unregisterListener(this);
super.dispose();
}
@@ -120,6 +129,14 @@ public class AvdManagerPage extends UpdaterPage implements ISdkChangeListener {
// nothing to be done for now.
}
+ // --- Implementation of DevicesChangeListener
+
+ @Override
+ public void onDevicesChange() {
+ mAvdSelector.refresh(false /*reload*/);
+ }
+
+
// End of hiding from SWT Designer
//$hide<<$
}
diff --git a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman2/AvdManagerWindowImpl1.java b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman2/AvdManagerWindowImpl1.java
index 06cdc74..8a04b51 100755
--- a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman2/AvdManagerWindowImpl1.java
+++ b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/repository/sdkman2/AvdManagerWindowImpl1.java
@@ -69,6 +69,8 @@ public class AvdManagerWindowImpl1 {
private final UpdaterData mUpdaterData;
/** True if this window created the UpdaterData, in which case it needs to dispose it. */
private final boolean mOwnUpdaterData;
+ private final DeviceManager mDeviceManager;
+
// --- UI members ---
@@ -94,6 +96,7 @@ public class AvdManagerWindowImpl1 {
mContext = context;
mUpdaterData = new UpdaterData(osSdkRoot, sdkLog);
mOwnUpdaterData = true;
+ mDeviceManager = new DeviceManager(sdkLog);
}
/**
@@ -115,6 +118,7 @@ public class AvdManagerWindowImpl1 {
mContext = context;
mUpdaterData = updaterData;
mOwnUpdaterData = false;
+ mDeviceManager = new DeviceManager(mUpdaterData.getSdkLog());
}
/**
@@ -161,6 +165,7 @@ public class AvdManagerWindowImpl1 {
public void widgetDisposed(DisposeEvent e) {
ShellSizeAndPos.saveSizeAndPos(mShell, SIZE_POS_PREFIX); //$hide$
onAndroidSdkUpdaterDispose(); //$hide$
+ mAvdPage.dispose(); //$hide$
}
});
@@ -180,7 +185,7 @@ public class AvdManagerWindowImpl1 {
private void createContents() {
- mAvdPage = new AvdManagerPage(mShell, SWT.NONE, mUpdaterData);
+ mAvdPage = new AvdManagerPage(mShell, SWT.NONE, mUpdaterData, mDeviceManager);
mAvdPage.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true, 2, 1));
}
@@ -353,15 +358,13 @@ public class AvdManagerWindowImpl1 {
Menu menuDevices = new Menu(menuBarDevices);
menuBarDevices.setMenu(menuDevices);
- final DeviceManager manager = new DeviceManager(mUpdaterData.getSdkLog());
-
MenuItem createDevice = new MenuItem(menuDevices, SWT.NONE);
createDevice.setText("Create New Device");
createDevice.addSelectionListener(new SelectionAdapter() {
@Override
public void widgetSelected(SelectionEvent e) {
DeviceCreationDialog dlg = new DeviceCreationDialog(
- mShell, manager, mUpdaterData.getImageFactory(), null);
+ mShell, mDeviceManager, mUpdaterData.getImageFactory(), null);
if (dlg.open() == Window.OK) {
setupDevices(menuBarDevices);
}
@@ -370,7 +373,7 @@ public class AvdManagerWindowImpl1 {
new MenuItem(menuDevices, SWT.SEPARATOR);
Map<String, List<Device>> devices = new HashMap<String, List<Device>>();
- for (Device d : manager.getDevices(mUpdaterData.getOsSdkRoot())) {
+ for (Device d : mDeviceManager.getDevices(mUpdaterData.getOsSdkRoot())) {
List<Device> l;
if (devices.containsKey(d.getManufacturer())) {
l = devices.get(d.getManufacturer());
@@ -393,7 +396,7 @@ public class AvdManagerWindowImpl1 {
@Override
public void widgetSelected(SelectionEvent e) {
DeviceCreationDialog dlg = new DeviceCreationDialog(
- mShell, manager, mUpdaterData.getImageFactory(), d);
+ mShell, mDeviceManager, mUpdaterData.getImageFactory(), d);
if(dlg.open() == Window.OK) {
setupDevices(menuBarDevices);
}
diff --git a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdCreationDialog.java b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdCreationDialog.java
index baf8a26..24e3209 100644
--- a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdCreationDialog.java
+++ b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdCreationDialog.java
@@ -878,9 +878,6 @@ public class AvdCreationDialog extends GridDialog {
return false;
}
- hwProps.put(AvdManager.AVD_INI_DEVICE_MANUFACTURER, mDeviceManufacturer.getText());
- hwProps.put(AvdManager.AVD_INI_DEVICE_NAME, mDeviceName.getText());
-
// Although the device has this information, some devices have more RAM than we'd want to
// allocate to an emulator.
hwProps.put(AvdManager.AVD_INI_RAM_SIZE, mRam.getText());
diff --git a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdSelector.java b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdSelector.java
index 58bacec..c447c89 100644
--- a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdSelector.java
+++ b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdSelector.java
@@ -22,6 +22,8 @@ import com.android.sdklib.IAndroidTarget;
import com.android.sdklib.ISdkLog;
import com.android.sdklib.NullSdkLog;
import com.android.sdklib.SdkConstants;
+import com.android.sdklib.devices.Device;
+import com.android.sdklib.devices.DeviceManager;
import com.android.sdklib.internal.avd.AvdInfo;
import com.android.sdklib.internal.avd.AvdInfo.AvdStatus;
import com.android.sdklib.internal.avd.AvdManager;
@@ -66,7 +68,10 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.Formatter;
+import java.util.HashMap;
+import java.util.List;
import java.util.Locale;
+import java.util.Map;
/**
@@ -1000,21 +1005,49 @@ public final class AvdSelector {
false /*logErrorsOnly*/);
}
- // delete the AVD
- try {
- mAvdManager.updateAvd(avdInfo, log);
+ boolean success = true;
- // display the result
- if (log instanceof MessageBoxLog) {
- ((MessageBoxLog) log).displayResult(true /* success */);
+ if (avdInfo.getStatus() == AvdStatus.ERROR_IMAGE_DIR) {
+ // delete the AVD
+ try {
+ mAvdManager.updateAvd(avdInfo, log);
+ refresh(false /*reload*/);
+ } catch (IOException e) {
+ log.error(e, null);
+ success = false;
+ }
+ } else if (avdInfo.getStatus() == AvdStatus.ERROR_DEVICE_CHANGED) {
+ // Overwrite the properties derived from the device and nothing else
+ Map<String, String> properties = new HashMap<String, String>(avdInfo.getProperties());
+
+ List<Device> devices = (new DeviceManager(mSdkLog)).getDevices(mOsSdkPath);
+ String name = properties.get(AvdManager.AVD_INI_DEVICE_NAME);
+ String manufacturer = properties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER);
+
+ if (properties != null && devices != null && name != null && manufacturer != null) {
+ for (Device d : devices) {
+ if (d.getName().equals(name) && d.getManufacturer().equals(manufacturer)) {
+ properties.putAll(DeviceManager.getHardwareProperties(d));
+ try {
+ mAvdManager.updateAvd(avdInfo, properties, AvdStatus.OK, log);
+ } catch (IOException e) {
+ log.error(e,null);
+ success = false;
+ }
+ }
+ }
+ } else {
+ log.error(null, "Base device information incomplete or missing.");
+ success = false;
}
- refresh(false /*reload*/);
- } catch (IOException e) {
- log.error(e, null);
+ // display the result
if (log instanceof MessageBoxLog) {
- ((MessageBoxLog) log).displayResult(false /* success */);
+ ((MessageBoxLog) log).displayResult(success);
}
+ refresh(false /*reload*/);
+ } else if (avdInfo.getStatus() == AvdStatus.ERROR_DEVICE_MISSING) {
+ onEdit();
}
}
@@ -1056,7 +1089,7 @@ public final class AvdSelector {
}
AvdStartDialog dialog = new AvdStartDialog(mTable.getShell(), avdInfo, mOsSdkPath,
- mController);
+ mController, mSdkLog);
if (dialog.open() == Window.OK) {
String path = mOsSdkPath + File.separator
+ SdkConstants.OS_SDK_TOOLS_FOLDER
@@ -1200,6 +1233,8 @@ public final class AvdSelector {
}
private boolean isAvdRepairable(AvdStatus avdStatus) {
- return avdStatus == AvdStatus.ERROR_IMAGE_DIR;
+ return avdStatus == AvdStatus.ERROR_IMAGE_DIR
+ || avdStatus == AvdStatus.ERROR_DEVICE_CHANGED
+ || avdStatus == AvdStatus.ERROR_DEVICE_MISSING;
}
}
diff --git a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdStartDialog.java b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdStartDialog.java
index 63787f9..9649f95 100644
--- a/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdStartDialog.java
+++ b/sdkmanager/libs/sdkuilib/src/com/android/sdkuilib/internal/widgets/AvdStartDialog.java
@@ -16,6 +16,9 @@
package com.android.sdkuilib.internal.widgets;
+import com.android.sdklib.ISdkLog;
+import com.android.sdklib.devices.Device;
+import com.android.sdklib.devices.DeviceManager;
import com.android.sdklib.internal.avd.AvdInfo;
import com.android.sdklib.internal.avd.AvdManager;
import com.android.sdkuilib.internal.repository.SettingsController;
@@ -72,6 +75,7 @@ final class AvdStartDialog extends GridDialog {
private final AvdInfo mAvd;
private final String mSdkLocation;
private final SettingsController mSettingsController;
+ private final DeviceManager mDeviceManager;
private Text mScreenSize;
private Text mMonitorDpi;
@@ -91,11 +95,12 @@ final class AvdStartDialog extends GridDialog {
private Button mSnapshotLaunchCheckbox;
AvdStartDialog(Shell parentShell, AvdInfo avd, String sdkLocation,
- SettingsController settingsController) {
+ SettingsController settingsController, ISdkLog sdkLog) {
super(parentShell, 2, false);
mAvd = avd;
mSdkLocation = sdkLocation;
mSettingsController = settingsController;
+ mDeviceManager = new DeviceManager(sdkLog);
if (mAvd == null) {
throw new IllegalArgumentException("avd cannot be null");
}
@@ -430,7 +435,8 @@ final class AvdStartDialog extends GridDialog {
/**
* Returns the screen size to start with.
* <p/>If an emulator with the same skin was already launched, scaled, the size used is reused.
- * <p/>Otherwise the default is returned (3)
+ * <p/>If one hasn't been launched and the AVD is based on a device, use the device's screen
+ * size. Otherwise, use the default (3).
*/
private String getScreenSize() {
String size = sSkinScaling.get(mAvd.getName());
@@ -438,6 +444,20 @@ final class AvdStartDialog extends GridDialog {
return size;
}
+ Map<String, String> properties = mAvd.getProperties();
+ if (properties != null) {
+ String name = properties.get(AvdManager.AVD_INI_DEVICE_NAME);
+ String mfctr = properties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER);
+ if (name != null && mfctr != null) {
+ Device d = mDeviceManager.getDevice(mSdkLocation, name, mfctr);
+ if (d != null) {
+ double screenSize =
+ d.getDefaultHardware().getScreen().getDiagonalLength();
+ return String.format("%.1f", screenSize);
+ }
+ }
+ }
+
return "3";
}
@@ -607,5 +627,4 @@ final class AvdStartDialog extends GridDialog {
mSnapshotLaunch = enabled && sSnapshotLaunch;
mSnapshotLaunchCheckbox.setSelection(mSnapshotLaunch);
}
-
}