Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android 百度地圖 SDK v3.0.0 (四) 引入離線地圖功能

Android 百度地圖 SDK v3.0.0 (四) 引入離線地圖功能

編輯:關於Android編程

 

一直覺得地圖應用支持離線地圖很重要啊,我等移動2G屌絲,流量不易,且用且珍惜。

 

對於官方開發指南對於離線地圖的教程,提供了兩種方案:

第一,手動導入,先將從官網下載的離線包解壓,把vmp文件夾拷入SD卡根目錄下的BaiduMapSDK文件夾內。好吧,我表示不能接受,無視了。

第二,接口下載方法如下:mOffline.start(cityid);還比較靠譜,就是沒詳細介紹。

今天,我們主要對第二種方式進行詳細介紹,然後集成到我們的已經集成了定位方向傳感器的地圖中,如果你還不了解:Android百度地圖 SDK v3.0.0 (三) 添加覆蓋物Marker與InfoWindow的使用

效果圖:\ 為了方便,我又添加了個菜單按鈕~可以看到能夠對下載位置的保存,支持多個等待下載,已經取消下載等。最主要當然是,下載過後,只需要定位的流量(甚至不用)就能很好的使用咱們的地圖拉~ 順便提一下:本來想搞個線程池,支持多個同時下載,這塊可能很多不注意會有一些問題,但是百度地圖公開出來的start(cityCode)不管我怎麼嘗試(嘗試了多個離線地圖實例都不行),每次同時都只能下載一個。
1、百度地圖離線相關API介紹
a 、類 MKOfflineMap 提供地圖的下載,離線地圖列表的獲取,已下載地圖的查詢等 java.util.ArrayList getAllUpdateInfo() 返回各城市離線地圖更新信息
java.util.ArrayList getHotCityList() 返回熱門城市列表
java.util.ArrayList getOfflineCityList() 返回支持離線地圖城市列表
MKOLUpdateElement getUpdateInfo(int cityID) 返回指定城市ID離線地圖更新信息 java.util.ArrayList searchCity(java.lang.String cityName) 根據城市名搜索該城市離線地圖記錄
boolean init(MKOfflineMapListener listener) 初使化
boolean pause(int cityID) 暫停下載指定城市ID的離線地圖
boolean remove(int cityID) 刪除指定城市ID的離線地圖
boolean start(int cityID) 啟動下載指定城市ID的離線地圖 void destroy() 銷毀離線地圖管理模塊,不用時調用

接口 MKOfflineMapListener 離線地圖事件通知接口。 void onGetOfflineMapState(int type, int state)
類 MKOLUpdateElement 和 類 MKOLSearchRecord 基本就是包含一些cityName , cityId, size 等等
API在百度的幫助文檔中也很詳細,下面會在代碼中使用這些API。
2、離線地圖城市信息的實體Bean
package com.zhy.zhy_baidu_ditu_demo00;

public class OfflineMapCityBean
{
	private String cityName;
	private int cityCode;
	/**
	 * 下載的進度
	 */
	private int progress;
	
	private Flag flag = Flag.NO_STATUS;
	/**
	 * 下載的狀態:無狀態,暫停,正在下載
	 * @author zhy
	 *
	 */
	public enum Flag
	{
		NO_STATUS,PAUSE,DOWNLOADING
	}

	public Flag getFlag()
	{
		return flag;
	}

	public void setFlag(Flag flag)
	{
		this.flag = flag;
	}

	public OfflineMapCityBean()
	{
	}

	public OfflineMapCityBean(String cityName, int cityCode, int progress)
	{
		this.cityName = cityName;
		this.cityCode = cityCode;
		this.progress = progress;
	}

	public String getCityName()
	{
		return cityName;
	}

	public void setCityName(String cityName)
	{
		this.cityName = cityName;
	}

	public int getCityCode()
	{
		return cityCode;
	}

	public void setCityCode(int cityCode)
	{
		this.cityCode = cityCode;
	}

	public int getProgress()
	{
		return progress;
	}

	public void setProgress(int progress)
	{
		this.progress = progress;
	}

}

包含了,城市名稱:用於listview上的顯示,城市id:用於查詢下載情況,進度:更新listview下載時的顯示,標志:用戶開啟或者取消下載時的標志。
3、離線地圖的使用
在Actvity啟動時,首先初始化離線地圖
/**
	 * 初始化離線地圖
	 */
	private void initOfflineMap()
	{
		mOfflineMap = new MKOfflineMap();
		// 設置監聽
		mOfflineMap.init(new MKOfflineMapListener()
		{
			@Override
			public void onGetOfflineMapState(int type, int state)
			{
				switch (type)
				{
				case MKOfflineMap.TYPE_DOWNLOAD_UPDATE:
					// 離線地圖下載更新事件類型
					MKOLUpdateElement update = mOfflineMap.getUpdateInfo(state);
					Log.e(TAG, update.cityName +  , + update.ratio);
					for (OfflineMapCityBean bean : mDatas)
					{
						if (bean.getCityCode() == state)
						{
							bean.setProgress(update.ratio);
							bean.setFlag(Flag.DOWNLOADING);
							break;
						}
					}
					mAdapter.notifyDataSetChanged();
					Log.e(TAG, TYPE_DOWNLOAD_UPDATE);
					break;
				case MKOfflineMap.TYPE_NEW_OFFLINE:
					// 有新離線地圖安裝
					Log.e(TAG, TYPE_NEW_OFFLINE);
					break;
				case MKOfflineMap.TYPE_VER_UPDATE:
					// 版本更新提示
					break;
				}

			}
		});
	}
設置離線地圖的下載監聽接口,目前我們只關注type為MKOfflineMap.TYPE_DOWNLOAD_UPDATE , 此時傳入的state為cityId, 然後我們通過mOfflineMap.getUpdateInfo(state);可以獲得該城市的下載數據,接下來更新我們listview的數據集,最後刷新界面。
初始化數據:
	private void initData()
	{

		// 獲得所有熱門城市
		ArrayList offlineCityList = mOfflineMap
				.getHotCityList();
		// 手動添加了西安
		MKOLSearchRecord xian = new MKOLSearchRecord();
		xian.cityID = 233;
		xian.cityName = 西安市;
		offlineCityList.add(xian);
		// 獲得所有已經下載的城市列表
		ArrayList allUpdateInfo = mOfflineMap
				.getAllUpdateInfo();
		// 設置所有數據的狀態
		for (MKOLSearchRecord record : offlineCityList)
		{
			OfflineMapCityBean cityBean = new OfflineMapCityBean();
			cityBean.setCityName(record.cityName);
			cityBean.setCityCode(record.cityID);

			if (allUpdateInfo != null)//沒有任何下載記錄,返回null,為啥不返回空列表~~
			{
				for (MKOLUpdateElement ele : allUpdateInfo)
				{
					if (ele.cityID == record.cityID)
					{
						cityBean.setProgress(ele.ratio);
					}
				}

			}
			mDatas.add(cityBean);
		}

	}

進入Activity先通過mOfflineMap.getHotCityList();獲得熱門城市列表,不過熱門裡面竟然沒有西安,我手動增加了一個西安。(這裡我是為了方便,有興趣的可以列出全國支持的城市);接下來mOfflineMap.getAllUpdateInfo();獲得已經下載城市的數據信息;然後就行交叉對比,設置數據源數據。
初始化listview
private void initListView()
	{
		mListView = (ListView) findViewById(R.id.id_offline_map_lv);
		mAdapter = new MyOfflineCityBeanAdapter();
		mListView.setAdapter(mAdapter);

		mListView.setOnItemClickListener(new OnItemClickListener()
		{
			@Override
			public void onItemClick(AdapterView parent, View view,
					int position, long id)
			{
				int cityId = mDatas.get(position).getCityCode();
				if (mCityCodes.contains(cityId))
				{
					removeTaskFromQueue(position, cityId);
				} else
				{
					addToDownloadQueue(position, cityId);
				}

			}
		});
	}

為listview的item設置點擊事件,第一次點擊時加入下載隊列,第二次點擊時取消下載。 listview的適配器
/**
	 * 熱門城市地圖列表的Adapter
	 * 
	 * @author zhy
	 * 
	 */
	class MyOfflineCityBeanAdapter extends BaseAdapter
	{

		@Override
		public boolean isEnabled(int position)
		{
			if (mDatas.get(position).getProgress() == 100)
			{
				return false;
			}
			return super.isEnabled(position);
		}

		@Override
		public int getCount()
		{
			return mDatas.size();
		}

		@Override
		public Object getItem(int position)
		{
			return mDatas.get(position);
		}

		@Override
		public long getItemId(int position)
		{
			return position;
		}

		@Override
		public View getView(int position, View convertView, ViewGroup parent)
		{
			OfflineMapCityBean bean = mDatas.get(position);
			ViewHolder holder = null;
			if (convertView == null)
			{
				holder = new ViewHolder();
				convertView = mInflater.inflate(R.layout.offlinemap_item,
						parent, false);
				holder.cityName = (TextView) convertView
						.findViewById(R.id.id_cityname);
				holder.progress = (TextView) convertView
						.findViewById(R.id.id_progress);
				convertView.setTag(holder);
			} else
			{
				holder = (ViewHolder) convertView.getTag();
			}

			holder.cityName.setText(bean.getCityName());
			int progress = bean.getProgress();
			String progressMsg = ;
			// 根據進度情況,設置顯示
			if (progress == 0)
			{
				progressMsg = 未下載;
			} else if (progress == 100)
			{
				bean.setFlag(Flag.NO_STATUS);
				progressMsg = 已下載;
			} else
			{
				progressMsg = progress + %;
			}
			// 根據當前狀態,設置顯示
			switch (bean.getFlag())
			{
			case PAUSE:
				progressMsg += 【等待下載】;
				break;
			case DOWNLOADING:
				progressMsg += 【正在下載】;
				break;
			default:
				break;
			}
			holder.progress.setText(progressMsg);
			return convertView;
		}

		private class ViewHolder
		{
			TextView cityName;
			TextView progress;

		}
	}

適配器的代碼比較簡單,主要就是getView中根本bean的數據設置顯示。 最後在我們主Activity增加一個菜單項,打開此Activity就完工了:
@Override
public boolean onOptionsItemSelected(MenuItem item)
{

	switch (item.getItemId())
	{
	case R.id.id_menu_map_offline:
		Intent intent = new Intent(MainActivity.this,
					OfflineMapActivity.class);
		startActivity(intent);
		break;
	...
	}	
}	

好了,關於百度地圖,目前就用到這麼多~~如果後期有別的需求,還會繼續更新~

源碼點擊下載 注:開發者key需要換成自己申請的,不清楚申請的請看第一篇博客的。


  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved