AI 143304: am: CL 143157 am: CL 142852 ADT fix #1682502: New XML File Wizard root combo is sometimes empty.
  Two issues in fact:
  1- On some selections the resource type is determined before the
  root values are computed.
  2- Added an sdk target change listener to refresh the project's roots
  if the SDK was still loading or if the project changed targets.
  The New Project Wizard has been updated with a similar sdk change
  listener to refresh the target selector. This is useful when the NPW
  is used before the targets have finished loading, e.g. upon lauching
  Eclipse.
  Note: this requires CL 142690 to compile.
  Original author: raphael
  Merged from: //branches/cupcake/...
  Original author: android-build
  Merged from: //branches/donutburger/...

Automated import of CL 143304
diff --git a/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/wizards/newproject/NewProjectCreationPage.java b/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/wizards/newproject/NewProjectCreationPage.java
index 7d3cad3..e26b31c 100644
--- a/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/wizards/newproject/NewProjectCreationPage.java
+++ b/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/wizards/newproject/NewProjectCreationPage.java
@@ -22,7 +22,9 @@
 
 package com.android.ide.eclipse.adt.wizards.newproject;
 
+import com.android.ide.eclipse.adt.AdtPlugin;
 import com.android.ide.eclipse.adt.sdk.Sdk;
+import com.android.ide.eclipse.adt.sdk.Sdk.ITargetChangeListener;
 import com.android.ide.eclipse.common.AndroidConstants;
 import com.android.ide.eclipse.common.project.AndroidManifestParser;
 import com.android.sdklib.IAndroidTarget;
@@ -122,6 +124,7 @@
     private Button mCreateActivityCheck;
     private Text mMinSdkVersionField;
     private SdkTargetSelector mSdkTargetSelector;
+    private ITargetChangeListener mSdkTargetChangeListener;
 
     private boolean mInternalLocationPathUpdate;
     protected boolean mInternalProjectNameUpdate;
@@ -263,6 +266,17 @@
         // Validate. This will complain about the first empty field.
         setPageComplete(validatePage());
     }
+    
+    @Override
+    public void dispose() {
+        
+        if (mSdkTargetChangeListener != null) {
+            AdtPlugin.getDefault().removeTargetListener(mSdkTargetChangeListener);
+            mSdkTargetChangeListener = null;
+        }
+        
+        super.dispose();
+    }
 
     /**
      * Creates the group for the project name:
@@ -389,18 +403,35 @@
         group.setFont(parent.getFont());
         group.setText("Target");
         
-        // get the targets from the sdk
-        IAndroidTarget[] targets = null;
-        if (Sdk.getCurrent() != null) {
-            targets = Sdk.getCurrent().getTargets();
-        }
+        // The selector is created without targets. They are added below in the change listener.
+        mSdkTargetSelector = new SdkTargetSelector(group, null, false /*multi-selection*/);
 
-        mSdkTargetSelector = new SdkTargetSelector(group, targets, false /*multi-selection*/);
+        mSdkTargetChangeListener = new ITargetChangeListener() {
+            public void onProjectTargetChange(IProject changedProject) {
+                // Ignore
+            }
 
-        // If there's only one target, select it
-        if (targets != null && targets.length == 1) {
-            mSdkTargetSelector.setSelection(targets[0]);
-        }
+            public void onTargetsLoaded() {
+                // Update the sdk target selector with the new targets
+
+                // get the targets from the sdk
+                IAndroidTarget[] targets = null;
+                if (Sdk.getCurrent() != null) {
+                    targets = Sdk.getCurrent().getTargets();
+                }
+                mSdkTargetSelector.setTargets(targets);
+
+                // If there's only one target, select it
+                if (targets != null && targets.length == 1) {
+                    mSdkTargetSelector.setSelection(targets[0]);
+                }
+            }
+        };
+        
+        AdtPlugin.getDefault().addTargetListener(mSdkTargetChangeListener);
+        
+        // Invoke it once to initialize the targets
+        mSdkTargetChangeListener.onTargetsLoaded();
         
         mSdkTargetSelector.setSelectionListener(new SelectionAdapter() {
             @Override
diff --git a/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/editors/wizards/NewXmlFileCreationPage.java b/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/editors/wizards/NewXmlFileCreationPage.java
index 7a91150..83ab59b 100644
--- a/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/editors/wizards/NewXmlFileCreationPage.java
+++ b/tools/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/editors/wizards/NewXmlFileCreationPage.java
@@ -20,6 +20,7 @@
 import com.android.ide.eclipse.adt.AdtPlugin;
 import com.android.ide.eclipse.adt.sdk.AndroidTargetData;
 import com.android.ide.eclipse.adt.sdk.Sdk;
+import com.android.ide.eclipse.adt.sdk.Sdk.ITargetChangeListener;
 import com.android.ide.eclipse.common.AndroidConstants;
 import com.android.ide.eclipse.common.project.ProjectChooserHelper;
 import com.android.ide.eclipse.editors.descriptors.DocumentDescriptor;
@@ -237,7 +238,7 @@
                 "An XML file that describes preferences.",          // tooltip
                 ResourceFolderType.XML,                             // folder type
                 AndroidTargetData.DESCRIPTOR_PREFERENCES,           // root seed
-                AndroidConstants.CLASS_PREFERENCE_SCREEN,           // default root
+                AndroidConstants.CLASS_NAME_PREFERENCE_SCREEN,      // default root
                 SdkConstants.NS_RESOURCES,                          // xmlns
                 null,                                               // default attributes
                 1                                                   // target API level
@@ -290,7 +291,9 @@
     private boolean mInternalTypeUpdate;
     private boolean mInternalConfigSelectorUpdate;
     private ProjectChooserHelper mProjectChooserHelper;
+    private ITargetChangeListener mSdkTargetChangeListener;
 
+    private TypeInfo mCurrentTypeInfo;
 
     // --- UI creation ---
     
@@ -337,8 +340,43 @@
         initializeFromSelection(mInitialSelection);
         initializeRootValues();
         enableTypesBasedOnApi();
+        if (mCurrentTypeInfo != null) {
+            updateRootCombo(mCurrentTypeInfo);
+        }
+        installTargetChangeListener();
         validatePage();
     }
+    
+    private void installTargetChangeListener() {
+        mSdkTargetChangeListener = new ITargetChangeListener() {
+            public void onProjectTargetChange(IProject changedProject) {
+                // If this is the current project, force it to reload its data
+                if (changedProject != null && changedProject == mProject) {
+                    changeProject(mProject);
+                }
+            }
+
+            public void onTargetsLoaded() {
+                // Reload the current project, if any, in case its target has changed.
+                if (mProject != null) {
+                    changeProject(mProject);
+                }
+            }
+        };
+        
+        AdtPlugin.getDefault().addTargetListener(mSdkTargetChangeListener);
+    }
+
+    @Override
+    public void dispose() {
+        
+        if (mSdkTargetChangeListener != null) {
+            AdtPlugin.getDefault().removeTargetListener(mSdkTargetChangeListener);
+            mSdkTargetChangeListener = null;
+        }
+        
+        super.dispose();
+    }
 
     /**
      * Returns the target project or null.
@@ -652,7 +690,6 @@
             return;
         }
 
-        
         // Find the best match in the element list. In case there are multiple selected elements
         // select the one that provides the most information and assign them a score,
         // e.g. project=1 + folder=2 + file=4.
@@ -848,6 +885,10 @@
 
     /**
      * Changes mProject to the given new project and update the UI accordingly.
+     * <p/>
+     * Note that this does not check if the new project is the same as the current one
+     * on purpose, which allows a project to be updated when its target has changed or
+     * when targets are loaded in the background.
      */
     private void changeProject(IProject newProject) {
         mProject = newProject;
@@ -1067,6 +1108,7 @@
     private void selectType(TypeInfo type) {
         if (type == null || !type.getWidget().getSelection()) {
             mInternalTypeUpdate = true;
+            mCurrentTypeInfo = type;
             for (TypeInfo type2 : sTypes) {
                 type2.getWidget().setSelection(type2 == type);
             }