編輯:關於Android編程
在使用GridView、ListView的過程中遇到內容錯亂的問題,費了較長時間才找到問題的根源,特地總結一下。
1、在自定義adapter中沒有給每一項都設置內容導致內容錯亂:
@Override public View getView(final int position, View convertView, ViewGroup parent) { if( null == convertView ){ mGridHolder = new GridHolder( ); convertView = mLayoutInflater.inflate( R.layout.view_log_word_item_layout, null ); mGridHolder.mBackTopLayout = (LinearLayout)convertView.findViewById( R.id.logItemTopLayoutId); mGridHolder.mBackBottomLayout = ( RelativeLayout )convertView.findViewById( R.id.logItemBottomLayoutId ); mGridHolder.mRightWordTxt = ( TextView )convertView.findViewById( R.id.rightWordTxtId ); mGridHolder.mUserWriteImg = ( ImageView )convertView.findViewById( R.id.userWordImgId ); mGridHolder.mWriteResultImg = ( ImageView )convertView.findViewById( R.id.writeResultImgId ); mGridHolder.mReasonTxt = ( TextView )convertView.findViewById( R.id.reasonTxtId ); mGridHolder.mRightWordTxt.setTypeface( mTypeface ); convertView.setTag( mGridHolder ); }else{ mGridHolder = ( GridHolder )convertView.getTag( ); } showContent( mDictationInfoList.get( position ) ); return convertView; } @SuppressWarnings("deprecation") private void showContent( DictationInfo dictationInfo ){ mGridHolder.mRightWordTxt.setText( dictationInfo.getmWord( ) ); if( null != dictationInfo.getmDrawable( ) ){ mGridHolder.mUserWriteImg.setBackgroundDrawable( dictationInfo.getmDrawable( ) ); if( !TextUtils.isEmpty( dictationInfo.getDetailReason( ) ) ){ mGridHolder.mReasonTxt.setText( dictationInfo.getDetailReason( ) ); }else{ mGridHolder.mReasonTxt.setText( "" ); } setWriteResult( dictationInfo.getmWriteResult( ) ); }else{ // 沒有為內容項為空的項設置內容 } }
上面是一個自定義adapter中的一段代碼,在getView中為每一項設置內容時只處理了有內容的項,沒有內容的項沒有賦值,導致在滑動內容時內容錯亂,分析發現這是由於使用了adapter的緩存機制導致的,正確的處理方式是需要為內容為空的項也要賦值,修改後的代碼如下:
@Override public View getView(final int position, View convertView, ViewGroup parent) { if( null == convertView ){ mGridHolder = new GridHolder( ); convertView = mLayoutInflater.inflate( R.layout.view_log_word_item_layout, null ); mGridHolder.mBackTopLayout = (LinearLayout)convertView.findViewById( R.id.logItemTopLayoutId); mGridHolder.mBackBottomLayout = ( RelativeLayout )convertView.findViewById( R.id.logItemBottomLayoutId ); mGridHolder.mRightWordTxt = ( TextView )convertView.findViewById( R.id.rightWordTxtId ); mGridHolder.mUserWriteImg = ( ImageView )convertView.findViewById( R.id.userWordImgId ); mGridHolder.mWriteResultImg = ( ImageView )convertView.findViewById( R.id.writeResultImgId ); mGridHolder.mReasonTxt = ( TextView )convertView.findViewById( R.id.reasonTxtId ); mGridHolder.mRightWordTxt.setTypeface( mTypeface ); convertView.setTag( mGridHolder ); }else{ mGridHolder = ( GridHolder )convertView.getTag( ); } showContent( mDictationInfoList.get( position ) ); return convertView; } @SuppressWarnings("deprecation") private void showContent( DictationInfo dictationInfo ){ mGridHolder.mRightWordTxt.setText( dictationInfo.getmWord( ) ); if( null != dictationInfo.getmDrawable( ) ){ mGridHolder.mUserWriteImg.setBackgroundDrawable( dictationInfo.getmDrawable( ) ); if( !TextUtils.isEmpty( dictationInfo.getDetailReason( ) ) ){ mGridHolder.mReasonTxt.setText( dictationInfo.getDetailReason( ) ); }else{ mGridHolder.mReasonTxt.setText( "" ); } setWriteResult( dictationInfo.getmWriteResult( ) ); }else{ mGridHolder.mUserWriteImg.setBackgroundResource( Color.TRANSPARENT ); mGridHolder.mReasonTxt.setText( "" ); mGridHolder.mWriteResultImg.setBackgroundResource( R.drawable.log_unknown ); mGridHolder.mBackTopLayout.setBackgroundResource( R.drawable.log_item_wrong_top_background ); mGridHolder.mBackBottomLayout.setBackgroundResource( R.drawable.log_item_wrong_bottom_background ); } }
2、在自定義adapter的getview方法中,每一項的內容加載時間過長導致內容錯亂。
@Override public View getView(int position, View convertView, ViewGroup parent) { mViewHolder = new ViewHolder( ); convertView = mLayoutInflater.inflate( R.layout.adapter_score_list_layout, null ); mViewHolder.mScoreLayout = ( RelativeLayout )convertView.findViewById( R.id.scoreLayoutId ); mViewHolder.mScoreLayout.setClickable( false ); mViewHolder.mPositionTxt = ( TextView )convertView.findViewById( R.id.positionTxtId ); mViewHolder.mUserNameTxt = ( TextView )convertView.findViewById( R.id.userNameTxtId ); mViewHolder.mUserNameTxt.setTypeface( mTypeface ); mViewHolder.mUserIconImg = ( ImageView )convertView.findViewById( R.id.userIconImgId ); mViewHolder.mUserScoreTxt = ( TextView )convertView.findViewById( R.id.userScoreTxtId ); showContent( position, mUserInfoList.get( position ) ); return convertView; } private void showContent( int index, UserScoreInfo userInfo ){ // 從網絡獲取頭像 handleUserIcon( mImageLoader, userInfo, mUserId ); mViewHolder.mPositionTxt.setVisibility(TextView.VISIBLE); mViewHolder.mPositionTxt.setText( "第" + userInfo.getScoreRank( ) + "名" ); if( mUserId.equals( userInfo.getUserId( ) ) ){ mMyPosition = index; mViewHolder.mScoreLayout.setBackgroundResource( R.drawable.chinese_dictation_score_list_select ); }else{ mViewHolder.mScoreLayout.setBackgroundResource( R.drawable.chinese_dictation_score_list_normal ); } String userName = userInfo.getNickName( ); if( !TextUtils.isEmpty( userName ) ){ userName = ( userName.length( ) > 10 )?( userName.substring(0, 7) + "..." ):userName; }else{ userName = "佚名"; } if( mUserId.equals( userInfo.getUserId( ) ) ){ String localUserName = PersonalInfo.getCurrentUserName( mContext ); mMyPosition = index; mViewHolder.mScoreLayout.setBackgroundResource( R.drawable.chinese_dictation_score_list_select ); if( TextUtils.isEmpty( userName ) || ( !localUserName.equals( userName ) ) ){ mViewHolder.mUserNameTxt.setText( localUserName ); }else{ mViewHolder.mUserNameTxt.setText( userName ); } }else{ mViewHolder.mScoreLayout.setBackgroundResource( R.drawable.chinese_dictation_score_list_normal ); mViewHolder.mUserNameTxt.setText( userName ); } mViewHolder.mUserScoreTxt.setText( StringUtils.getSplitByComma( userInfo.getScore( ) + "" ) ); }上面是一個獲取用戶排名列表所自定義adapter中的一段代碼,handleUserIcon方法是從網絡獲取用戶頭像,在滑動排名列表的時候發現用戶頭像會錯亂,最後跟蹤找到具體的原因是由於從網絡獲取用戶頭像耗時,正確的做法應該是在獲取完成用戶頭像之後再通知adapter更新。
在使用gridview和listview的過程中,由於需要加載大量的內容,android建議我們采用viewholder的緩存機制,這樣能夠提高列表加載的效率,但是在使用的過程中一定要注意上面這兩個問題,否則可能會讓你很頭疼。
Android在4.4就已推出新運行時ART,准備替代用了有些時日的Dalvik。不過當時尚屬測試版,主角仍是Dalvik。 直到今年的Google I/O大會,ART才
在沒有google的時代,當在開發中遇到問題時,程序員唯一的方式就是去讀源代碼,雖然現在可以通過搜索引擎解決大部分開發問題,但是要想理解其內部運行原理,還是要去讀源代碼。
Java源文件通過Java編譯器生成CLASS文件,再通過dx工具轉換為classes.dex文件。DEX文件從整體上來看是一個索引的結構,類名、方法名、字段名等信息都存
一、為什麼需要自定義鎖屏頁鎖屏作為一種黑白屏時代就存在的手機功能,至今仍發揮著巨大作用,特別是觸屏時代的到來,鎖屏的功用被發揮到了極致。多少人曾經在無聊的時候每隔幾分鐘劃