1. 程式人生 > >百度地圖4.1_1開發教程(6)點收藏(1)

百度地圖4.1_1開發教程(6)點收藏(1)

在本章教程中,將一起學習長按地圖收藏該點,這本章中,將設計到的內容有
1.長按時間
2.生成marker
3.地理編碼搜尋(用地址檢索座標)、反地理編碼搜尋(用座標檢索地址)
4.收藏點
5.刪除點等操作

先上效果圖

長按地圖,生成地圖的點,地理編碼搜尋得到地標名,點選底部的收藏,將對應的點收藏。

做好了,我們開車咯!
首先看一下佈局
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" android:id="@+id/activity_main" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="com.kowalski.MainActivity">
<com.baidu.mapapi.map.MapView android:id="@+id/activity_main_mv_map" android:layout_width
="match_parent" android:layout_height="match_parent" android:clickable="true"/>
<!-- 收藏介面 --> <LinearLayout android:id="@+id/activity_main_favo_ll_favo" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentBottom
="true" android:animateLayoutChanges="true" android:clickable="true" android:focusable="true" android:background="@android:color/white" android:focusableInTouchMode="true" android:orientation="vertical" android:padding="10dp" android:visibility="gone">
<LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal"> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:gravity="center_vertical" android:text="地標名:" android:textSize="18sp"/> <EditText android:id="@+id/activity_main_favo_et_address" android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:gravity="center_vertical" android:textColor="@android:color/secondary_text_dark_nodisable" android:textSize="18sp"/> </LinearLayout> <TextView android:id="@+id/activity_main_favo_tv_latlng" android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center_vertical" android:lineSpacingMultiplier="1.3" android:text="經度:\n緯度:" android:textSize="18sp"/> <TextView android:id="@+id/activity_main_favo_tv_favorite" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:layout_marginLeft="20dp" android:gravity="center" android:padding="10dp" android:text="收藏"/> </LinearLayout> <Button android:id="@+id/activity_main_favo_bt_favoList" android:layout_width="match_parent" android:layout_height="wrap_content" android:text="收藏列表"/> </RelativeLayout>
收藏介面是隱藏的,僅當點選收藏點的時候才會顯示出來。下面重點看類:

宣告,都加了註釋,後面程式碼看不懂可以翻到這裡檢視

    private MapView mv_map;
    private BaiduMap mBaiduMap;

    private LinearLayout ll_favo; // 收藏Layout
    GeoCoder mSearch = null; // 搜尋模組,也可去掉地圖模組獨立使用
    private Marker mFavoMarker; // 收藏的點
    private LatLng mFavoLatlng; // 收藏點的經緯度
    private InfoWindow mInfoWindow;

    private EditText et_address; // 收藏點的做表明
    private TextView tv_latlng, tv_favorite; // 收藏點的經緯度
    private Button bt_favoList; // 跳轉收藏列表的按鈕

    private BitmapDescriptor mFavoIcon; // 生成marker的點的圖片

    private Activity activity = MainActivity.this;

別忘了SDKInitializer.initialize(getApplicationContext());

 @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        SDKInitializer.initialize(getApplicationContext());
        setContentView(R.layout.activity_main);

        initWidget();
    }

    /**
     * 初始化控制元件
     */
    private void initWidget()
    {
        mv_map = (MapView) findViewById(R.id.activity_main_mv_map);
        ll_favo = (LinearLayout)findViewById(R.id.activity_main_favo_ll_favo);
        et_address = (EditText)findViewById(R.id.activity_main_favo_et_address);
        tv_latlng = (TextView)findViewById(R.id.activity_main_favo_tv_latlng);
        tv_favorite = (TextView)findViewById(R.id.activity_main_favo_tv_favorite);
        tv_favorite.setOnClickListener(this);
        bt_favoList = (Button)findViewById(R.id.activity_main_favo_bt_favoList);
        bt_favoList.setOnClickListener(this);
        mBaiduMap = mv_map.getMap(); // 通過控制元件獲取地圖物件
        mv_map.setLogoPosition(LogoPosition.logoPostionRightTop); // 設定Logo方位
        mBaiduMap.setViewPadding(0, 20, 20, 0); // LOGO邊距

        mSearch = GeoCoder.newInstance();// 初始化搜尋模組,註冊事件監聽
        mSearch.setOnGetGeoCodeResultListener(this);

        mBaiduMap.setOnMapLongClickListener(this);
        mBaiduMap.setOnMarkerClickListener(this);
        FavoriteManager.getInstance().init(); // 初始化收藏夾
    }
首先初始化控制元件,在Activity中,實現了
  implements View.OnClickListener, BaiduMap.OnMarkerClickListener, BaiduMap.OnMapLongClickListener,OnGetGeoCoderResultListener
  這些方法。 
    /**
     * 地圖長按事件
     */
    @Override
    public void onMapLongClick(LatLng latLng)
    {
        if (mFavoMarker != null)
        {
            mFavoMarker.remove();
        }
        mFavoIcon = BitmapDescriptorFactory
                .fromResource(R.mipmap.ic_pin);

        MarkerOptions mFavoOptions = new MarkerOptions()
                .position(latLng)  //設定marker的位置
                .icon(mFavoIcon) //設定marker圖示
                .zIndex(1)  //設定marker所在層級
                .draggable(true);  //設定手勢拖拽
        Bundle b = new Bundle();
        b.putString("favo", "favo");
        mFavoOptions.extraInfo(b);
        // 將marker新增到地圖上
        mFavoMarker = (Marker) (mBaiduMap.addOverlay(mFavoOptions));
    }
在地圖長按事件中,我們先判斷marker點是否存在,如果存在,則刪掉它,以我們當前長按的點為新的收藏點.
    /**
     * marker點選事件
     */
    @Override
    public boolean onMarkerClick(Marker marker)
    {
        TextView tv = new TextView(getApplicationContext());
        tv.setBackgroundResource(R.mipmap.location_tips);
        tv.setPadding(80, 30, 80, 80);
        tv.setTextColor(getResources().getColor(android.R.color.white));
        InfoWindow.OnInfoWindowClickListener listener = null;
        if (marker == null)
        {
            return false;
        } else if (marker.getExtraInfo().get("favo") != null)
        {
            tv.setText("移除");
            tv.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View v)
                {
                    mFavoMarker.remove();
                    mFavoMarker = null;
                    mBaiduMap.hideInfoWindow();
                    ll_favo.setVisibility(View.GONE);
                }
            });
            // 反Geo搜尋,根據經緯度獲取地標名
            mFavoLatlng = new LatLng(marker.getPosition().latitude, marker.getPosition().longitude);
            mSearch.reverseGeoCode(new ReverseGeoCodeOption().location(mFavoLatlng));

            mInfoWindow = new InfoWindow(tv, marker.getPosition(), -50);
            tv_latlng.setText("經度:" + marker.getPosition().longitude + "\n" + "緯度:" + marker.getPosition().latitude);
            // 設定詳細資訊到佈局
            ll_favo.setVisibility(View.VISIBLE); // 顯示詳情佈局
            mBaiduMap.showInfoWindow(mInfoWindow); // 顯示彈窗
            return true;
        }
        return false;
    }
在這段程式碼中,用到了我部落格之前的一些知識點,marker的彈窗事件,這裡就不復述了,這些是很基礎的東西,一定要會用。在點選marker以後,我們使用反Geo搜尋,並根據當前的marker對應的經緯度,獲取當前地標名。在完成獲取以後,將經緯度顯示到佈局上並將佈局顯示出來。具體獲取地標名的實現請看以下程式碼。
 /**
     * 根據經緯度獲取地名
     */
    @Override
    public void onGetGeoCodeResult(GeoCodeResult geoCodeResult)
    {}
    @Override
    public void onGetReverseGeoCodeResult(ReverseGeoCodeResult result)
    {
        if (result == null || result.error != SearchResult.ERRORNO.NO_ERROR)
        {
            Toast.makeText(activity, "抱歉,未能找到地標名,請手動輸入", Toast.LENGTH_SHORT);
            return;
        }
        et_address.setText(result.getAddress());
    }
這裡實現了兩個方法,因為我專案沒用到第一個方法,沒實際用過也不敢誤人子弟,如果想了解更詳細請上官網文件檢視,這裡我們只看第二個方法。

在這個方法中,result就是回調回來的地標名,做一個簡單的判斷後,將獲取到的座標顯示在輸入框中。在實際開發中,這裡應該加入一個進度條等待獲取成功,否則會給使用者帶來很差的體驗。接下來,就應該將這個點收藏起來了。
    /**
     * 單擊事件
     */
    @Override
    public void onClick(View v)
    {
        switch (v.getId())
        {
            case R.id.activity_main_favo_tv_favorite:
                FavoritePoiInfo info = new FavoritePoiInfo();
                info.poiName(et_address.getText().toString().trim());// 獲取地標名
                LatLng pt = new LatLng(mFavoLatlng.latitude, mFavoLatlng.longitude);
                info.pt(pt);
                if (FavoriteManager.getInstance().add(info) == 1)
                {
                    Toast.makeText(activity,"收藏成功,您可開啟我的收藏檢視。", Toast.LENGTH_SHORT);
                    et_address.setText("");
                    tv_latlng.setText("");
                    mBaiduMap.hideInfoWindow();
                    if (mFavoMarker != null)
                    {
                        mFavoMarker.remove();
                    }
                } else
                {
                    Toast.makeText(activity,"新增失敗,請檢查做表明是否重複." , Toast.LENGTH_SHORT);
                }
                ll_favo.setVisibility(View.GONE);
                break;

            case R.id.activity_main_favo_bt_favoList:
                List<FavoritePoiInfo> list= FavoriteManager.getInstance().getAllFavPois();
                for (int i = 0; i < list.size(); i++)
                {
                    Log.w("ddd", list.get(i).getPoiName());
                }
                break;
        }

    }
FavoritePoiInfo這個類是API給我們用的,這裡我們將獲取到的地標名作為poiName,將經緯度傳入,
    再呼叫 FavoriteManager.getInstance().add(info)就可以添加了,注意看它返回的是int型別,根據文件判斷當前返回值為1,就是儲存成功了。這裡做一個判斷,就新增成功了。

注意一下,我在寫部落格的Demo的時候,儲存成功或失敗,Toast並不會彈出,由於時間緊迫,暫時忽略掉這些細節,如果能幫我找出問題,感激不盡,謝謝

    如何檢視添加了那些收藏的點呢。
    我們寫一個迴圈將點打印出來檢視一下就知道了。暫時將收藏列表的點選時間加入以下程式碼:
List<FavoritePoiInfo> list= FavoriteManager.getInstance().getAllFavPois();
                for (int i = 0; i < list.size(); i++)
                {
                    Log.w("ddd", list.get(i).getPoiName());
                }
如果沒有問題的話,打印出來的是以下格式:
11-27 12:11:57.411 4515-4515/com.kowalski W/ddd: 北京市海淀區大慧寺路2011-27 12:11:57.411 4515-4515/com.kowalski W/ddd: 北京市西城區老牆根街1411-27 12:11:57.411 4515-4515/com.kowalski W/ddd: 北京市通州區G4501(北京六環高速)
11-27 12:11:57.411 4515-4515/com.kowalski W/ddd: 北京市豐臺區馬家堡路
11-27 12:11:57.411 4515-4515/com.kowalski W/ddd: 北京市東城區馬家堡路1號-100111-27 12:11:57.411 4515-4515/com.kowalski W/ddd: 北京市西城區長椿街45
ok,得知收藏成功以後,我們就要實現對收藏點的刪除,跳轉地圖的操作了。
部落格寫太長,看著累,我自己也累,所以我將在下一篇部落格中繼續介紹使用,謝謝大家。

請支援我,掃描左側二維碼打賞,謝謝。