1

我在 android 中开发了一个应用程序,它使用谷歌地图来显示用户位置附近的购物中心列表。

这是我实现它的代码。

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <org.fluturasymphony.recommendation.StoreMapView 
        android:id="@+id/mapView"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:enabled="true"
        android:clickable="true"
        android:apiKey="0aHtkSh4B8Ub3ELLFUMRWJD23wpEWJAsFxL-ilw"
        />



</RelativeLayout>

商店地图活动的代码。

public class StoreMapActivity extends MapActivity {
   List<GeoPoint> items = new ArrayList<GeoPoint>();   
   StoreMapView mapView;  

  @SuppressWarnings("deprecation")
@Override
  public void onCreate(Bundle savedInstanceState){
    super.onCreate(savedInstanceState);
    setContentView(R.layout.map);
    SharedPreferences myPrefs = this.getSharedPreferences("myPrefs", MODE_WORLD_READABLE);
    String outlet_details = myPrefs.getString("outlet_details", "null");
    String show_all = myPrefs.getString("show_all","null");

    this.mapView = init();

    //MapController mc = mapView.getController();
    @SuppressWarnings("unused")
    GeoPoint p = new GeoPoint(0,0);


       // String all_data = "[{\"outlet_latlng\":\"12.928569,77.58311\",\"outlet_id\":\"1\",\"outlet_desc\":\"BigBazaar\",\"outlet_loc\":\"Jayanagar4thBlock\",\"outlet_image\":\"bigbazaar.png\",\"recommended_products\":[{\"item_id\":\"3\",\"item_desc\":\"dettol\",\"item_image\":\"dettol.png\"}]},{\"outlet_latlng\":\"12.939235,77.578068\",\"outlet_id\":\"2\",\"outlet_desc\":\"FoodWorld\",\"outlet_loc\":\"Basavanagudi\",\"outlet_image\":\"foodworld.png\",\"recommended_products\":[{\"item_id\":\"3\",\"item_desc\":\"dettol\",\"item_image\":\"dettol.png\"},{\"item_id\":\"3\",\"item_desc\":\"colgate\",\"item_image\":\"colgate.png\"}]},{\"outlet_latlng\":\"12.958934,77.657161\",\"outlet_id\":\"5\",\"outlet_desc\":\"Total\",\"outlet_loc\":\"MurgeshPalaya\",\"outlet_image\":\"total.png\",\"recommended_products\":[{\"item_id\":\"3\",\"item_desc\":\"dettol\",\"item_image\":\"dettol.png\"},{\"item_id\":\"3\",\"item_desc\":\"colgate\",\"item_image\":\"colgate.png\"}]}]"; // temp data

                myPrefs = StoreMapActivity.this.getSharedPreferences("myPrefs", MODE_WORLD_READABLE);
                String client = myPrefs.getString("client", "godrej");
                String url = "http://10.0.2.2/Flutura/PHP/Core/Data/android.data.php?request=outlets";
                Log.v("url",url);
                AsyncHttpClient httpclient = new AsyncHttpClient();
                httpclient.get(url, new AsyncHttpResponseHandler() {
                    @Override
                    public void onSuccess(String response) {
                        try {
                            Log.v("response",response);
                            updateMap(response);

                        } catch (JSONException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        }
                    }
                });                


}

  protected void updateMap(String json) throws JSONException{
     Log.v("json",json);
    ArrayList<String> outlets = Utils.ToArrayList(new JSONArray(json));

    Iterator<String> i = outlets.iterator();
    while(i.hasNext()){
      String j = i.next();   
      displayOutlet(this.mapView,new JSONObject(j));
    }

 this.setMapBoundsToPois(this.mapView, items, 0.1, 0.2);
 mapView.invalidate();
  }


  @Override
  protected boolean isRouteDisplayed() {
    // TODO Auto-generated method stub
    return false;// Minimum & maximum latitude so we can span it   
  }

  protected StoreMapView init(){

    // Initialize Map Object
    StoreMapView mapView = (StoreMapView) findViewById(R.id.mapView);

    // Add zoom controls
    mapView.setBuiltInZoomControls(true);

    // Add listener    
    mapView.setOnChangeListener(new MapViewChangeListener());

    return mapView;
  }

  protected GeoPoint displayOutlet(StoreMapView mapView,JSONObject outlet) throws JSONException{    

    String coordinates[] =outlet.getString("outlet_latlng").split(",");
    double lat = Double.parseDouble(coordinates[0]);
    double lng = Double.parseDouble(coordinates[1]); 

    GeoPoint p = new GeoPoint(
        (int) (lat * 1E6), 
        (int) (lng * 1E6));

    this.items.add(p);

    List<Overlay> mapOverlays = mapView.getOverlays();
    Drawable drawable = this.getResources().getDrawable(R.drawable.marker);
    StoreOverlay itemizedoverlay = new StoreOverlay(drawable, this);


    ArrayList<String> recomm_products = Utils.ToArrayList(new JSONArray(outlet.getString("recommended_products")));
    Iterator<String> i = recomm_products.iterator();
    String recommended_products = "";
    int index = 0;
    while (i.hasNext()) {
       index++;
       String j = i.next();
       JSONObject item = new JSONObject(j);
       Log.v("j",j);
       itemizedoverlay.addItem(item.getString("item_name"));
    }
    OverlayItem overlayitem = new OverlayItem(p, outlet.getString("outlet_desc"), "Recommended Products");
    itemizedoverlay.addOverlay(overlayitem);

    mapOverlays.add(itemizedoverlay);   

    return p;
  }

  private class MapViewChangeListener implements StoreMapView.OnChangeListener
  {

      @Override
      public void onChange(MapView view, GeoPoint newCenter, GeoPoint oldCenter, int newZoom, int oldZoom)
      {
          // Check values
          if ((!newCenter.equals(oldCenter)) && (newZoom != oldZoom))
          {
              // Map Zoom and Pan Detected
              // TODO: Add special action here
          }
          else if (!newCenter.equals(oldCenter))
          {
              // Map Pan Detected
              // TODO: Add special action here
          }
          else if (newZoom != oldZoom)
          {
              // Map Zoom Detected
              // TODO: Add special action here
          }
      }
  }

  public void setMapBoundsToPois(StoreMapView mapView,List<GeoPoint> items, double hpadding, double vpadding) {

    MapController mapController = mapView.getController();
    // If there is only on one result
    // directly animate to that location

    if (items.size() == 1) { // animate to the location
      mapController.animateTo(items.get(0));
    } else {
        // find the lat, lon span
        int minLatitude = Integer.MAX_VALUE;
        int maxLatitude = Integer.MIN_VALUE;
        int minLongitude = Integer.MAX_VALUE;
        int maxLongitude = Integer.MIN_VALUE;

        // Find the boundaries of the item set
        for (GeoPoint item : items) {
            int lat = item.getLatitudeE6(); int lon = item.getLongitudeE6();

            maxLatitude = Math.max(lat, maxLatitude);
            minLatitude = Math.min(lat, minLatitude);
            maxLongitude = Math.max(lon, maxLongitude);
            minLongitude = Math.min(lon, minLongitude);
        }

        // leave some padding from corners
        // such as 0.1 for hpadding and 0.2 for vpadding
        maxLatitude = maxLatitude + (int)((maxLatitude-minLatitude)*hpadding);
        minLatitude = minLatitude - (int)((maxLatitude-minLatitude)*hpadding);

        maxLongitude = maxLongitude + (int)((maxLongitude-minLongitude)*vpadding);
        minLongitude = minLongitude - (int)((maxLongitude-minLongitude)*vpadding);

        // Calculate the lat, lon spans from the given pois and zoom
        mapController.zoomToSpan(Math.abs(maxLatitude - minLatitude), Math
.abs(maxLongitude - minLongitude));

        // Animate to the center of the cluster of points
        mapController.animateTo(new GeoPoint(
              (maxLatitude + minLatitude) / 2, (maxLongitude + minLongitude) / 2));
    }
} // end of the method
}

商店地图视图的代码。

public class StoreMapView extends MapView
{ 
  // ------------------------------------------------------------------------
  // LISTENER DEFINITIONS
  // ------------------------------------------------------------------------

  // Change listener
  public interface OnChangeListener
  {
    public void onChange(MapView view, GeoPoint newCenter, GeoPoint oldCenter, int newZoom, int oldZoom);
  }

  // ------------------------------------------------------------------------
  // MEMBERS
  // ------------------------------------------------------------------------

  private StoreMapView mThis;
  private long mEventsTimeout = 250L;   // Set this variable to your preferred timeout
  private boolean mIsTouched = false;
  private GeoPoint mLastCenterPosition;
  private int mLastZoomLevel;
  //private Timer mChangeDelayTimer = new Timer();
  private StoreMapView.OnChangeListener mChangeListener = null;

  // ------------------------------------------------------------------------
  // RUNNABLES
  // ------------------------------------------------------------------------

  private Runnable mOnChangeTask = new Runnable()
  {
    @Override
    public void run()
    {
      if (mChangeListener != null) mChangeListener.onChange(mThis, getMapCenter(), mLastCenterPosition, getZoomLevel(), mLastZoomLevel);
      mLastCenterPosition = getMapCenter();
      mLastZoomLevel = getZoomLevel();      
    }
  };

  // ------------------------------------------------------------------------
  // CONSTRUCTORS
  // ------------------------------------------------------------------------

  public StoreMapView(Context context, String apiKey)
  {
    super(context, apiKey);
    init();
  }

  public StoreMapView(Context context, AttributeSet attrs)
  {
    super(context, attrs);
    init();
  }

  public StoreMapView(Context context, AttributeSet attrs, int defStyle)
  {
    super(context, attrs, defStyle);
    init();
  }

  private void init()
  {
    mThis = this;
    mLastCenterPosition = this.getMapCenter();
    mLastZoomLevel = this.getZoomLevel();
  }

  // ------------------------------------------------------------------------
  // GETTERS / SETTERS
  // ------------------------------------------------------------------------

  public void setOnChangeListener(StoreMapView.OnChangeListener l)
  {
    mChangeListener = l;
  }

  // ------------------------------------------------------------------------
  // EVENT HANDLERS
  // ------------------------------------------------------------------------

  @Override
  public boolean onTouchEvent(MotionEvent ev)
  {   
    // Set touch internal
    mIsTouched = (ev.getAction() != MotionEvent.ACTION_UP);

    return super.onTouchEvent(ev);
  }

  @Override
  public void computeScroll()
  {
    super.computeScroll();

    // Check for change
    if (isSpanChange() || isZoomChange())
    {
      // If computeScroll called before timer counts down we should drop it and 
      // start counter over again
      resetMapChangeTimer();
    }
  }

  // ------------------------------------------------------------------------
  // TIMER RESETS
  // ------------------------------------------------------------------------

  private void resetMapChangeTimer()
  {
    StoreMapView.this.removeCallbacks(mOnChangeTask);
    StoreMapView.this.postDelayed(mOnChangeTask, mEventsTimeout);
  }

  // ------------------------------------------------------------------------
  // CHANGE FUNCTIONS
  // ------------------------------------------------------------------------

  private boolean isSpanChange()
  {
    return !mIsTouched && !getMapCenter().equals(mLastCenterPosition);
  }

  private boolean isZoomChange()
  {
    return (getZoomLevel() != mLastZoomLevel);
  }

}

但是当我运行模拟器时,我得到一个像这样的空白屏幕。我该如何解决?

在此处输入图像描述

告诉我我在这里做错了什么。

嗨,我现在遇到了 log cat 错误。

01-03 07:28:02.585: E/MapActivity(3823): 无法获取连接工厂客户端

01-03 07:30:26.165: E/MapActivity(12298): 无法获取连接工厂客户端

我的安卓清单文件。

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="org.fluturasymphony.recommendation"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk android:minSdkVersion="9"
              android:targetSdkVersion="11" />
    <uses-permission android:name="android.permission.INTERNET" />    
    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
    <application android:icon="@drawable/ic_launcher" android:label="@string/app_name">
        <activity android:label="@string/app_name" android:name=".LoginActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

        <activity android:name="org.achartengine.GraphicalActivity" />
        <activity android:name=".CategoryWiseSalesChartActivity" />
        <activity android:name=".ProductWiseSalesChartActivity" />
        <activity android:label="@string/home_screen" android:name=".HomeActivity" android:configChanges="orientation">            
        </activity>
        <activity android:label="@string/store_screen" android:name=".StoreActivity" android:configChanges="orientation">            
        </activity>
        <activity android:label="@string/store_list_screen" android:name=".StoreListActivity" android:configChanges="orientation">            
        </activity>
        <activity android:label="@string/location_screen" android:name=".StoreMapActivity" android:configChanges="orientation">            
        </activity>
        <activity android:label="@string/recommended_products_list_screen" android:name=".RecommendedProductsListActivity" android:configChanges="orientation">            
        </activity>
        <activity android:label="@string/category_wise_sales_screen" android:name=".CategoryWiseSalesActivity" android:configChanges="orientation">            
        </activity>
        <activity android:label="@string/product_wise_sales_screen" android:name=".ProductWiseSalesActivity" android:configChanges="orientation">            
        </activity>
                <uses-library android:name="com.google.android.maps" />


    </application>



</manifest>
4

2 回答 2

3

请生成新的 android 地图密钥,然后在 XML 中替换此密钥...可能是密钥未正确生成的问题...

于 2013-01-03T11:02:43.273 回答
2

我认为您的 android 地图 api 密钥无法正确生成,然后您只需点击此链接并获取 google 地图 api 密钥, https://developers.google.com/maps/documentation/android/v1/mapkey

于 2013-01-03T11:09:22.660 回答