編輯:關於Android編程
例子中用於解析Json的Gson請自己Google下載
主Activity:
package COM.Example.Main; import java.util.HashMap; import java.util.Iterator; import java.util.LinkedList; import java.util.List; import java.util.Map; import COM.Example.Main.R; import COM.Example.Main.stringGetJson.User; import android.app.Activity; import android.app.ListActivity; import android.os.AsyncTask; import android.os.Bundle; import android.view.Gravity; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.AbsListView; import android.widget.AbsListView.OnScrollListener; import android.widget.ArrayAdapter; import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.ListView; import android.widget.ProgressBar; import android.widget.TextView; public class stringListActivity extends ListActivity { private MyAdapter mMyAdapter; private LinkedList<User> users = null; // 當前Activity中的ListView ListView listView = null; int lastItem = 0; LinearLayout loadingLayout = null; @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.foodlistactivity); listView = getListView(); setLoadingLayout(); new readTask().execute(null); } private final class MyAdapter extends ArrayAdapter<User> { public MyAdapter(Activity activity, List<User> newsList) { super(activity, 0, newsList); } private Map<Integer, View> viewMap = new HashMap<Integer, View>(); @Override public View getView(int position, View convertView, ViewGroup parent) { ViewHolder holder; View rowView = this.viewMap.get(position); if (rowView == null) { User user = users.get(position); LayoutInflater inflater = ((Activity) this.getContext()) .getLayoutInflater(); holder = new ViewHolder(); rowView = inflater .inflate(R.layout.foodlistactivity_item, null); holder.mNameText = (TextView) rowView .findViewById(R.id.foodItemUsername); holder.mPhoto = (ImageView) rowView .findViewById(R.id.foodItemPic); rowView.setTag(holder); holder.mNameText.setText(user.Name); if (!holder.mPhoto.isDrawingCacheEnabled()) { holder.mPhoto.setTag(user.Pic); new downImageTask().execute(holder.mPhoto); holder.mPhoto.setDrawingCacheEnabled(true); } viewMap.put(position, rowView); } else { holder = (ViewHolder) rowView.getTag(); } return rowView; } public class ViewHolder { public TextView mNameText; public ImageView mPhoto; } } public void setLoadingLayout() { LinearLayout layout = new LinearLayout(this); layout.setOrientation(LinearLayout.HORIZONTAL); ProgressBar progressBar = new ProgressBar(this); progressBar.setPadding(0, 0, 15, 0); layout.addView(progressBar); TextView textView = new TextView(this); textView.setText("加載中..."); textView.setGravity(Gravity.CENTER_VERTICAL); layout.addView(textView); layout.setGravity(Gravity.CENTER); loadingLayout = new LinearLayout(this); loadingLayout.addView(layout); loadingLayout.setGravity(Gravity.CENTER); } private class scrollListener implements OnScrollListener { @Override public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) { // 當listView中沒有數據,或者數據超過100條,或者不是10的整數倍(即數據不足)時隱藏“更多”並取消onScroll事件的綁定 if (mMyAdapter.getCount() >= 100 || mMyAdapter.getCount() % 10 > 0 || mMyAdapter.getCount() == 0) { listView.removeFooterView(loadingLayout); listView.setOnScrollListener(null); } lastItem = firstVisibleItem + visibleItemCount - 1;// 這裡減一是因為有FootView } @Override public void onScrollStateChanged(AbsListView view, int scrollState) { if (lastItem == mMyAdapter.getCount() && scrollState == OnScrollListener.SCROLL_STATE_IDLE) { // 進行翻頁操作 new scrollTask().execute(null); } } } public class readTask extends AsyncTask<Object, Void, Void> { @Override protected Void doInBackground(Object... arg0) { users = new stringGetJson().getJson(); return null; } @Override protected void onPostExecute(Void result) { listView.addFooterView(loadingLayout); mMyAdapter = new MyAdapter(stringListActivity.this, users); setListAdapter(mMyAdapter); listView.setOnScrollListener(new scrollListener()); } } public class scrollTask extends AsyncTask<Object, Void, Void> { @Override protected Void doInBackground(Object... arg0) { for (Iterator iterator = new stringGetJson().getJson() .iterator(); iterator.hasNext();) { User user = (User) iterator.next(); users.add(user); } return null; } @Override protected void onPostExecute(Void result) { mMyAdapter.notifyDataSetChanged(); } } }
Json數據來源(這裡的例子中把json字符串直接寫在代碼中了,實際項目中需要改成從網絡讀取,例子中已經使用了多線程):
package COM.Example.Main; import java.lang.reflect.Type; import java.util.Iterator; import java.util.LinkedList; import android.database.MatrixCursor; import android.widget.ListView; import android.widget.TextView; import com.google.gson.Gson; import com.google.gson.reflect.TypeToken; public class stringGetJson { // 設置臨時ID,在項目中將被現實的id取代 private int id = 0; public stringGetJson() { super(); } //通過getJson方法從Json字符串獲取User的列表 public LinkedList<User> getJson() { String jsonData = "[{\"Name\":\"xinuxForJson1\",\"Pic\":\"http://www.qqjay.com/uploads/110414/1_234626_5.jpg\"},{\"Name\":\"xinuxForJson2\",\"Pic\":\"http://www.qqjay.com/uploads/110414/1_234626_3.jpg\"},{\"Name\":\"xinuxForJson3\",\"Pic\":\"http://www.qqjay.com/uploads/110414/1_234626_4.jpg\"},{\"Name\":\"xinuxForJson4\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian1/8.jpg\"},{\"Name\":\"xinuxForJson5\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian1/10.jpg\"},{\"Name\":\"xinuxForJson6\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian1/7.jpg\"},{\"Name\":\"xinuxForJson7\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian1/11.jpg\"},{\"Name\":\"xinuxForJson8\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian1/12.jpg\"},{\"Name\":\"xinuxForJson9\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian1/9.jpg\"},{\"Name\":\"xinuxForJson10\",\"Pic\":\"http://sucai.qqjay.com/fengmian/201104/tupian/7.jpg\"}]"; Type listType = new TypeToken<LinkedList<User>>() {}.getType(); Gson gson = new Gson(); LinkedList<User> users = gson.fromJson(jsonData, listType); return users; } //為getJson提供了數據實體類 final static class User { public String Name; public String Pic; } }
圖片下載AsyncTask
package COM.Example.Main; import COM.Example.FunctionUtility.Download; import android.graphics.Bitmap; import android.os.AsyncTask; import android.widget.ImageView; public class downImageTask extends AsyncTask<ImageView, Void, Bitmap> { ImageView gView = null; @Override protected Bitmap doInBackground(ImageView... arg0) { gView = (ImageView)arg0[0]; return Download.getBitmapFromUrl(gView.getTag().toString()); } @Override protected void onPostExecute(Bitmap result) { if(result != null){ this.gView.setImageBitmap(result); } this.gView = null; } }
網絡圖片下載類:
package COM.Example.FunctionUtility; import java.io.BufferedInputStream; import java.io.IOException; import java.io.InputStream; import java.net.MalformedURLException; import java.net.URL; import android.graphics.Bitmap; import android.graphics.BitmapFactory; public class Download { public static Bitmap getBitmapFromUrl(String imgUrl) { URL url; Bitmap bitmap = null; try { url = new URL(imgUrl); InputStream is = url.openConnection().getInputStream(); BufferedInputStream bis = new BufferedInputStream(is); bitmap = BitmapFactory.decodeStream(bis); bis.close(); } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } return bitmap; } }
以上所述是小編給大家分享的Android程序開發ListView+Json+異步網絡圖片加載+滾動翻頁的例子(圖片能緩存,圖片不錯亂)的相關知識,希望對大家有所幫助。
前沿:前面博文大多少總結的是Camera HAL1到HAL3的系統架構,但這些架構對於Camera APP開發來說依舊還是處於Camera API1.0的標准
在軟件開發過程中,程序代碼的復用,是非常重要的概念。我們總是需要使用一些現有的模塊、包、框架,或開發自己的模塊、包、框架,來實現對程序代碼的復用。比如在JavaWeb編程
Service(服務)是一個應用程序組件,可以在後台執行長時間運行的操作,不提供用戶界面。其他應用程序組件可以啟動一個Serivce,它將繼續在後台運行,即使用戶切換到另
Android動畫的一個實戰內容,從屏幕底部滑動彈出PopupWindow。 相信這種效果大家在很多APP上都遇到過,比如需要拍照或者從SD卡選擇圖片,再比如需要分享某些