實訓第五週(2)

李晨晨:

本次我主要實現了上次圖片選擇界面中的圖片預覽activity。

1.首先在上次的PhotoSelectActivity中加入帶result請求的頁面跳轉,以及相應的result處理:

[java]  view plain  copy
  1. /** 
  2.     * 單擊單張圖片時,調整到預覽頁面顯示該圖 
  3.     */  
  4.    private void previewByItem(){  
  5.        Intent intent = new Intent(this,ImagePreviewActivity.class);  
  6.        intent.putExtra("FLAG", ImagePreviewActivity.FLAG_SHOW_ITEM);  
  7.        intent.putExtra("IMAGE_ITEM",mShowItem);  
  8.        startActivityForResult(intent,REQUEST_SHOW_ITEM);  
  9.    }  
  10.   
  11.    /** 
  12.     * 單擊「預覽」按鈕時,跳轉到預覽頁面顯示所有已選中的圖片 
  13.     */  
  14.    private void previewByBtn(){  
  15.        Intent intent = new Intent(this,ImagePreviewActivity.class);  
  16.        intent.putExtra("FLAG", ImagePreviewActivity.FLAG_SHOW_LIST);  
  17.        intent.putExtra("IMAGE_LIST", (Serializable) mSelectedImages);  
  18.        startActivityForResult(intent,REQUEST_SHOW_LIST);  
  19.    }  
  20.   
  21.    @Override  
  22.    protected void onActivityResult(int requestCode, int resultCode, Intent data) {  
  23.        super.onActivityResult(requestCode, resultCode, data);  
  24.        // 預覽界面點擊了「發送」按鈕  
  25.        if (resultCode == RESULT_OK){  
  26.            if (requestCode == REQUEST_SHOW_ITEM){  
  27.                if (mShowItem != null){  
  28.                    mSelectedImages.clear();  
  29.                    mSelectedImages.add(mShowItem);  
  30.                    sendImage();  
  31.                }  
  32.            }else if (requestCode == REQUEST_SHOW_LIST){  
  33.                sendImage();  
  34.            }  
  35.        }  
  36.    }  

2.ImagePreviewActivity中,主要分爲控件id綁定,從上一個intent中獲得要顯示的圖片,顯示圖片,以及自定義的PagerAdapter和IndicatorView。

[java]  view plain  copy
  1. @Override  
  2.     protected void onCreate(@Nullable Bundle savedInstanceState) {  
  3.         super.onCreate(savedInstanceState);  
  4.         setContentView(R.layout.activity_image_preview);  
  5.         findView();  
  6.         getImageFromIntent();  
  7.         showImage();  
  8.     }  

相應的佈局:

activity_image_preview.xml

[java]  view plain  copy
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout  
  3.     xmlns:android="http://schemas.android.com/apk/res/android"  
  4.     android:layout_width="match_parent"  
  5.     android:layout_height="match_parent"  
  6.     android:orientation="vertical">  
  7.   
  8.     <include layout="@layout/layout_title"/>  
  9.   
  10.     <RelativeLayout  
  11.         android:layout_width="match_parent"  
  12.         android:layout_height="0dp"  
  13.         android:layout_weight="1">  
  14.   
  15.         <android.support.v4.view.ViewPager  
  16.             android:id="@+id/view_page"  
  17.             android:layout_width="match_parent"  
  18.             android:layout_height="match_parent"/>  
  19.   
  20.         <com.ezreal.ezchat.photoselector.IndicatorView  
  21.             android:id="@+id/indicator_view"  
  22.             android:layout_width="match_parent"  
  23.             android:layout_height="25dp"  
  24.             android:layout_alignParentBottom="true"  
  25.             android:layout_marginBottom="5dp"  
  26.             android:gravity="center"/>  
  27.     </RelativeLayout>  
  28.   
  29. </LinearLayout>  

item_image_pre.xml

[java]  view plain  copy
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <RelativeLayout  
  3.     xmlns:android="http://schemas.android.com/apk/res/android"  
  4.     android:id="@+id/layout_img"  
  5.     android:layout_width="match_parent"  
  6.     android:layout_height="match_parent">  
  7.   
  8.     <com.bm.library.PhotoView  
  9.         android:id="@+id/iv_img"  
  10.         android:layout_width="match_parent"  
  11.         android:layout_height="match_parent"  
  12.         android:background="@android:color/black"/>  
  13.   
  14. </RelativeLayout>  

2.findView方法:其中爲返回鍵和發送鍵設置了OnClickListener。

[java]  view plain  copy
  1. private void findView() {  
  2.         mTvTitle = (TextView) findViewById(R.id.tv_title);  
  3.         mTvTitle.setText("預覽");  
  4.   
  5.         mIvBack = (ImageView) findViewById(R.id.iv_back);  
  6.         mIvBack.setOnClickListener(new View.OnClickListener() {  
  7.             @Override  
  8.             public void onClick(View v) {  
  9.                 ImagePreviewActivity.this.setResult(RESULT_CANCELED);  
  10.                 finish();  
  11.             }  
  12.         });  
  13.   
  14.         mTvSend = (TextView) findViewById(R.id.tv_send);  
  15.         mTvSend.setText("發送");  
  16.         mTvSend.setTextColor(Color.WHITE);  
  17.         mTvSend.setOnClickListener(new View.OnClickListener() {  
  18.             @Override  
  19.             public void onClick(View v) {  
  20.                 ImagePreviewActivity.this.setResult(RESULT_OK);  
  21.                 finish();  
  22.             }  
  23.         });  
  24.   
  25.         mIndicatorView = (IndicatorView) findViewById(R.id.indicator_view);  
  26.         mViewPager = (ViewPager) findViewById(R.id.view_page);  
  27.     }  

3.getImageFromIntent方法:根據上一個activity不同的flag設置不同的響應。

[java]  view plain  copy
  1. private void getImageFromIntent() {  
  2.         mImageBeans = new ArrayList<>();  
  3.         int flag = getIntent().getIntExtra("FLAG", FLAG_SHOW_ITEM);  
  4.         if (flag == FLAG_SHOW_ITEM) {  
  5.             ImageBean image = (ImageBean) getIntent().getSerializableExtra("IMAGE_ITEM");  
  6.             if (image != null) {  
  7.                 mImageBeans.add(image);  
  8.             }  
  9.         } else if (flag == FLAG_SHOW_LIST) {  
  10.             List<ImageBean> list = (List<ImageBean>) getIntent().getSerializableExtra("IMAGE_LIST");  
  11.             if (list != null) {  
  12.                 mImageBeans.addAll(list);  
  13.             }  
  14.         }  
  15.         createViews();  
  16.     }  

其中用到的createViews方法:

[java]  view plain  copy
  1. private void createViews() {  
  2.        mViews = new ArrayList<>();  
  3.        for (int i = 0; i < mImageBeans.size(); i++) {  
  4.            View view = LayoutInflater.from(this).inflate(R.layout.item_image_pre,  
  5.                    nullfalse);  
  6.            PhotoView photoView = (PhotoView) view.findViewById(R.id.iv_img);  
  7.            photoView.setMaxScale(4);  
  8.            photoView.enable();  
  9.            Glide.with(ImagePreviewActivity.this)  
  10.                    .load(mImageBeans.get(i).getPath()).diskCacheStrategy(DiskCacheStrategy.ALL)  
  11.                    .error(R.drawable.bg_img_defalut)  
  12.                    .into(photoView);  
  13.            mViews.add(view);  
  14.        }  
  15.        mIndicatorView.init(mViews.size());  
  16.    }  

4.showImage方法:

[java]  view plain  copy
  1. private void showImage() {  
  2.         mPageAdapter = new ViewPageAdapter(mViews);  
  3.         mViewPager.setAdapter(mPageAdapter);  
  4.         mViewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {  
  5.   
  6.             private int mOldPosition = 0;  
  7.   
  8.             @Override  
  9.             public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {  
  10.   
  11.             }  
  12.   
  13.             @Override  
  14.             public void onPageSelected(int position) {  
  15.                 mIndicatorView.playBy(mOldPosition, position);  
  16.                 mOldPosition = position;  
  17.             }  
  18.   
  19.             @Override  
  20.             public void onPageScrollStateChanged(int state) {  
  21.   
  22.             }  
  23.         });  
  24.     }  

5.用到的自定義PagerAdapter-ViewPageAdapter

[java]  view plain  copy
  1. private class ViewPageAdapter extends PagerAdapter {  
  2.   
  3.         private List<View> mViews;  
  4.   
  5.         public ViewPageAdapter(List<View> views) {  
  6.             mViews = views;  
  7.         }  
  8.   
  9.         @Override  
  10.         public int getCount() {  
  11.             return mViews != null ? mViews.size() : 0;  
  12.         }  
  13.   
  14.         @Override  
  15.         public Object instantiateItem(ViewGroup container, int position) {  
  16.             container.addView(mViews.get(position));  
  17.             return mViews.get(position);  
  18.         }  
  19.   
  20.         @Override  
  21.         public void destroyItem(ViewGroup container, int position, Object object) {  
  22.             container.removeView(mViews.get(position));  
  23.         }  
  24.   
  25.         @Override  
  26.         public boolean isViewFromObject(View view, Object object) {  
  27.             return view == object;  
  28.         }  
  29.     }  

6.IndicatorView選擇指示器:主要是滑動圖片時,相應的下面的小圓點的動畫。

[java]  view plain  copy
  1. public class IndicatorView extends LinearLayout {  
  2.   
  3.     private Context mContext;  
  4.     private ArrayList<ImageView> mImageViews;  
  5.     private Bitmap mBtnSelect;  
  6.     private Bitmap mBtnNormal;  
  7.     private int mMaxHeight;  
  8.     private int mMaxWidth;  
  9.     private AnimatorSet mPlayToAnimatorSet;  
  10.     private AnimatorSet mPlayByInAnimatorSet;  
  11.     private AnimatorSet mPlayByOutAnimatorSet;  
  12.   
  13.     public IndicatorView(Context context) {  
  14.         this(context, null);  
  15.     }  
  16.   
  17.     public IndicatorView(Context context, AttributeSet attrs) {  
  18.         super(context, attrs);  
  19.         this.mContext = context;  
  20.         this.setOrientation(HORIZONTAL);  
  21.         mMaxWidth = mMaxHeight = dip2px(16);  
  22.         mBtnSelect = BitmapFactory.decodeResource(getResources(), R.drawable.indicator_point_select);  
  23.         mBtnNormal = BitmapFactory.decodeResource(getResources(), R.drawable.indicator_point_nomal);  
  24.     }  
  25.   
  26.     public void init(int count) {  
  27.   
  28.         mImageViews = new ArrayList<>();  
  29.         this.removeAllViews();  
  30.         for (int i = 0; i < count; i++) {  
  31.             RelativeLayout rl = new RelativeLayout(mContext);  
  32.             LayoutParams params = new LayoutParams(mMaxWidth, mMaxHeight);  
  33.             RelativeLayout.LayoutParams layoutParams = new RelativeLayout.LayoutParams(  
  34.                     LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);  
  35.             layoutParams.addRule(RelativeLayout.CENTER_IN_PARENT);  
  36.             ImageView imageView = new ImageView(mContext);  
  37.             if (i == 0) {  
  38.                 imageView.setImageBitmap(mBtnSelect);  
  39.                 rl.addView(imageView, layoutParams);  
  40.             } else {  
  41.                 imageView.setImageBitmap(mBtnNormal);  
  42.                 rl.addView(imageView, layoutParams);  
  43.             }  
  44.             this.addView(rl, params);  
  45.             mImageViews.add(imageView);  
  46.         }  
  47.     }  
  48.   
  49.     public void playBy(int startPosition, int nextPosition) {  
  50.   
  51.         boolean isShowInAnimOnly = false;  
  52.         if (startPosition < 0 || nextPosition < 0 || nextPosition == startPosition) {  
  53.             startPosition = nextPosition = 0;  
  54.         }  
  55.   
  56.         if (startPosition < 0) {  
  57.             isShowInAnimOnly = true;  
  58.             startPosition = nextPosition = 0;  
  59.         }  
  60.   
  61.         final ImageView imageViewStrat = mImageViews.get(startPosition);  
  62.         final ImageView imageViewNext = mImageViews.get(nextPosition);  
  63.   
  64.         ObjectAnimator anim1 = ObjectAnimator.ofFloat(imageViewStrat,  
  65.                 "scaleX"1.0f, 0.25f);  
  66.         ObjectAnimator anim2 = ObjectAnimator.ofFloat(imageViewStrat,  
  67.                 "scaleY"1.0f, 0.25f);  
  68.   
  69.         if (mPlayByOutAnimatorSet != null && mPlayByOutAnimatorSet.isRunning()) {  
  70.             mPlayByOutAnimatorSet.cancel();  
  71.             mPlayByOutAnimatorSet = null;  
  72.         }  
  73.         mPlayByOutAnimatorSet = new AnimatorSet();  
  74.         mPlayByOutAnimatorSet.play(anim1).with(anim2);  
  75.         mPlayByOutAnimatorSet.setDuration(100);  
  76.   
  77.         ObjectAnimator animIn1 = ObjectAnimator.ofFloat(imageViewNext,  
  78.                 "scaleX"0.25f, 1.0f);  
  79.         ObjectAnimator animIn2 = ObjectAnimator.ofFloat(imageViewNext,  
  80.                 "scaleY"0.25f, 1.0f);  
  81.   
  82.         if (mPlayByInAnimatorSet != null && mPlayByInAnimatorSet.isRunning()) {  
  83.             mPlayByInAnimatorSet.cancel();  
  84.             mPlayByInAnimatorSet = null;  
  85.         }  
  86.         mPlayByInAnimatorSet = new AnimatorSet();  
  87.         mPlayByInAnimatorSet.play(animIn1).with(animIn2);  
  88.         mPlayByInAnimatorSet.setDuration(100);  
  89.   
  90.         if (isShowInAnimOnly) {  
  91.             mPlayByInAnimatorSet.start();  
  92.             return;  
  93.         }  
  94.   
  95.         anim1.addListener(new Animator.AnimatorListener() {  
  96.             @Override  
  97.             public void onAnimationStart(Animator animation) {  
  98.             }  
  99.   
  100.             @Override  
  101.             public void onAnimationEnd(Animator animation) {  
  102.                 imageViewStrat.setImageBitmap(mBtnNormal);  
  103.                 ObjectAnimator animFil1l = ObjectAnimator.ofFloat(imageViewStrat,  
  104.                         "scaleX"1.0f);  
  105.                 ObjectAnimator animFill2 = ObjectAnimator.ofFloat(imageViewStrat,  
  106.                         "scaleY"1.0f);  
  107.                 AnimatorSet mFillAnimatorSet = new AnimatorSet();  
  108.                 mFillAnimatorSet.play(animFil1l).with(animFill2);  
  109.                 mFillAnimatorSet.start();  
  110.                 imageViewNext.setImageBitmap(mBtnSelect);  
  111.                 mPlayByInAnimatorSet.start();  
  112.             }  
  113.   
  114.             @Override  
  115.             public void onAnimationCancel(Animator animation) {  
  116.             }  
  117.   
  118.             @Override  
  119.             public void onAnimationRepeat(Animator animation) {  
  120.             }  
  121.         });  
  122.         mPlayByOutAnimatorSet.start();  
  123.     }  
  124.   
  125.     private int dip2px(float dipValue) {  
  126.         final float scale = getContext().getResources().getDisplayMetrics().density;  
  127.         return (int) (dipValue * scale + 0.5f);  
  128.     }  
  129. }  

最終效果:


下面的四個小點就是選擇指示器,代表預覽界面有幾張圖片。哪一個小點暗一點就代表顯示的是那一張。



仝心:

   這次的工作在上次的基礎上完成錄音發送功能。

    自定義AudioRecordButton類繼承自Button,用於實現聊天時的錄音和發送語音及其他一些相關功能。

    構造方法,設置按鈕樣式以及提示用戶可以按住按鈕說話

[java]  view plain  copy
  1. public AudioRecordButton(Context context, AttributeSet attrs, int defStyleAttr) {  
  2.         super(context, attrs, defStyleAttr);  
  3.         // 初始化按鈕樣式  
  4.         setBackgroundResource(R.drawable.record_button_normal);  
  5.         setText(getResources().getString(R.string.press_record));//按住 說話  
  6.     }  

     初始化按鈕,並設置長按按鈕的事件監聽器。

[java]  view plain  copy
  1. public void init(String audioSaveDir) {  
  2.         mAudioSaveDir = audioSaveDir;  
  3.         // 初始化 dialog 管理器  
  4.         mDialogManager = new RecordDialogManager(getContext());  
  5.         // 獲取音頻管理,以申請音頻焦點  
  6.         mAudioManager = (AudioManager) getContext().getSystemService(Context.AUDIO_SERVICE);  
  7.         // 初始化錄音管理器  
  8.         mAudioRecordManager = AudioRecordManager.getInstance(mAudioSaveDir);  
  9.   
  10.         mAudioRecordManager.setAudioStateListener(this);  
  11.   
  12.         // 設置按鈕長按事件監聽,只有觸發長按纔開始準備錄音  
  13.         setOnLongClickListener(new OnLongClickListener() {  
  14.             @Override  
  15.             public boolean onLongClick(View v) {  
  16.                 // 獲取焦點  
  17.                 int focus = mAudioManager.requestAudioFocus(null,  
  18.                         AudioManager.STREAM_MUSIC, AudioManager.AUDIOFOCUS_GAIN_TRANSIENT);  
  19.                 if (focus == AudioManager.AUDIOFOCUS_REQUEST_GRANTED){  
  20.                     isReady = true;  
  21.                     mAudioRecordManager.prepareAudio();  
  22.                 }else if (focus == AudioManager.AUDIOFOCUS_REQUEST_FAILED){  
  23.                     if (mRecordingListener != null) {  
  24.                         mRecordingListener.recordError("AUDIO_FOCUS_REQUEST_FAILED");  
  25.                     }  
  26.                 }  
  27.                 return true;  
  28.             }  
  29.         });  
  30.         hasInit = true;  
  31.     }  

    子線程runnable,每間隔0.1秒獲取音量大小,並記錄錄音時間

[java]  view plain  copy
  1. private Runnable mGetVoiceLevelRunnable = new Runnable() {  
  2.     @Override  
  3.     public void run() {  
  4.         while (isRecording) {  
  5.             try {  
  6.                 Thread.sleep(100);  
  7.                 mRecordTime += 100;  
  8.                 mHandler.sendEmptyMessage(MSG_VOICE_CHANGE);  
  9.             } catch (InterruptedException e) {  
  10.                 e.printStackTrace();  
  11.             }  
  12.         }  
  13.     }  
  14. };  

    通過Handler關聯子線程,通過Handler將Message和Runnable對象發送到該Handler所關聯線程的MessageQueue(消息隊列)中,然後該消息隊列一直在循環拿出一個Message,對其進行處理,處理完之後拿出下一個Message,繼續進行處理,周而復始。

[java]  view plain  copy
  1. @SuppressLint("HandlerLeak")  
  2.     private Handler mHandler = new Handler() {  
  3.         @Override  
  4.         public void handleMessage(Message msg) {  
  5.             super.handleMessage(msg);  
  6.             switch (msg.what) {  
  7.                 case MSG_AUDIO_PREPARED:  
  8.                     // 錄音管理器 prepare 成功,開始錄音並顯示dialog  
  9.                     // 啓動線程記錄時間並獲取音量變化  
  10.                     isRecording = true;  
  11.                     mDialogManager.showDialogRecord();  
  12.                     // 啓動線程,每隔0.1秒獲取音量大小  
  13.                     new Thread(mGetVoiceLevelRunnable).start();  
  14.                     break;  
  15.                 case MSG_VOICE_CHANGE:  
  16.                     mDialogManager.updateVoiceLevel(mAudioRecordManager.getVoiceLevel(7));  
  17.                     break;  
  18.                 case MSG_DIALOG_DISMISS:  
  19.                     mDialogManager.dismissDialog();  
  20.                     break;  
  21.             }  
  22.         }  
  23.     };  

    改變錄音提示狀態,包括「按住 說話」、「鬆開 發送」、「鬆開手指 取消發送」

[java]  view plain  copy
  1. private void changeState(int state) {  
  2.         if (mCurrentState != state) {  
  3.             mCurrentState = state;  
  4.             if (state == STATE_NORMAL) {  
  5.                 setText(getResources().getString(R.string.press_record));  
  6.                 setBackgroundResource(R.drawable.record_button_normal);  
  7.             } else if (state == STATE_RECORDING) {  
  8.                 setText(getResources().getString(R.string.release_end));  
  9.                 setBackgroundResource(R.drawable.record_button_recoding);  
  10.                 if (isRecording) {  
  11.                     mDialogManager.showRecording();  
  12.                 }  
  13.             } else if (state == STATE_WANT_CANCEL) {  
  14.                 setText(getResources().getString(R.string.release_cancel));  
  15.                 setBackgroundResource(R.drawable.record_button_recoding);  
  16.                 if (isRecording) {  
  17.                     mDialogManager.showDialogWantCancel();  
  18.                 }  
  19.             }  
  20.         }  
  21.     }  

    判斷是否要取消語音發送,通過判斷觸控點的x、y座標變化來判斷用戶行爲。

[java]  view plain  copy
  1. private boolean isWantToCancel(int x, int y) {  
  2.         return x < 0 || x > getWidth()  
  3.                 || y < -CANCEL_HEIGHT || y > getHeight() + CANCEL_HEIGHT;  
  4.     }  

    釋放資源,釋放音頻焦點

[java]  view plain  copy
  1. private void reset() {  
  2.         isReady = false;  
  3.         isRecording = false;  
  4.         mRecordTime = 0;  
  5.         changeState(STATE_NORMAL);  
  6.   
  7.         // 釋放焦點  
  8.         if (mAudioManager != null){  
  9.             mAudioManager.abandonAudioFocus(null);  
  10.         }  
  11.     }  

    然後在上週的文本輸入框中添加發送錄音的功能

[java]  view plain  copy
  1. // 錄音按鈕初始化和錄音監聽  
  2.         mBtnAudioRecord.init(Constant.APP_CACHE_AUDIO);  
  3.         mBtnAudioRecord.setRecordingListener(new AudioRecordButton.OnRecordingListener() {  
  4.             @Override  
  5.             public void recordFinish(String audioFilePath, long recordTime) {  
  6.                 if (mLayoutListener != null) {  
  7.                     mLayoutListener.audioRecordFinish(audioFilePath, recordTime);  
  8.                 }  
  9.             }  
  10.   
  11.             @Override  
  12.             public void recordError(String message) {  
  13.                 if (mLayoutListener != null) {  
  14.                     mLayoutListener.audioRecordError(message);  
  15.                 }  
  16.             }  
  17.         });  



張靜:

接下來完成「驗證提醒」後會跳轉進入的界面以及相關功能實現

一. activity_check_notify.xml  (進入驗證提醒後總體界面的佈局)

[java]  view plain  copy
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout  
  3.     xmlns:android="http://schemas.android.com/apk/res/android"  
  4.     android:orientation="vertical"  
  5.     android:layout_width="match_parent"  
  6.     android:layout_height="match_parent"  
  7.     android:fitsSystemWindows="true">  
  8.   
  9.     <include layout="@layout/title_layout"/>  
  10.   
  11.   
  12.     <android.support.v7.widget.RecyclerView  
  13.         android:background="@color/interval_color"  
  14.         android:id="@+id/rcv_notify_list"  
  15.         android:layout_width="match_parent"  
  16.         android:layout_height="match_parent"/>  
  17.   
  18. </LinearLayout>  


二. CheckNotifyListActivity(處理驗證消息)

1.初始化

(1)(2)爲適配器方法

(1)設置每一項的佈局

[java]  view plain  copy
  1. @Override  
  2.            public int setItemLayoutId(int position) {  
  3.                return R.layout.item_check_notify;  
  4.            }  

item_check_notify.xml

[java]  view plain  copy
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <RelativeLayout  
  3.     xmlns:android="http://schemas.android.com/apk/res/android"  
  4.     xmlns:app="http://schemas.android.com/apk/res-auto"  
  5.     android:layout_width="match_parent"  
  6.     android:background="@color/white_color"  
  7.     android:layout_height="wrap_content"  
  8.     android:gravity="center_vertical">  
  9.   
  10.     <LinearLayout  
  11.         android:id="@+id/layout_notify"  
  12.         android:layout_width="match_parent"  
  13.         android:layout_height="65dp"  
  14.         android:orientation="horizontal"  
  15.         android:gravity="center_vertical"  
  16.         android:paddingTop="5dp"  
  17.         android:layout_marginLeft="10dp"  
  18.         android:layout_marginRight="10dp">  
  19.   
  20.     <com.joooonho.SelectableRoundedImageView  
  21.         android:padding="5dp"  
  22.         android:id="@+id/iv_head_picture"  
  23.         android:layout_width="60dp"  
  24.         android:layout_height="match_parent"  
  25.         android:scaleType="fitXY"  
  26.         app:sriv_oval="true"/>  
  27.   
  28.     <LinearLayout  
  29.         android:id="@+id/msg_detail"  
  30.         android:layout_width="0dp"  
  31.         android:layout_height="match_parent"  
  32.         android:layout_marginLeft="5dp"  
  33.         android:layout_weight="1"  
  34.         android:gravity="center_vertical"  
  35.         android:orientation="vertical">  
  36.   
  37.         <TextView  
  38.             android:id="@+id/tv_name"  
  39.             android:layout_width="wrap_content"  
  40.             android:layout_height="wrap_content"  
  41.             android:maxLines="1"  
  42.             android:text="@string/app_name"  
  43.             android:textColor="@color/app_black_color"/>  
  44.   
  45.         <TextView  
  46.             android:id="@+id/tv_content"  
  47.             android:layout_width="wrap_content"  
  48.             android:layout_height="wrap_content"  
  49.             android:layout_marginTop="10dp"  
  50.             android:maxLines="1"  
  51.             android:text="@string/test_msg"  
  52.             android:textColor="@color/default_text_color"/>  
  53.     </LinearLayout>  
  54.   
  55.   
  56.     <TextView  
  57.         android:id="@+id/tv_do_agree"  
  58.         android:layout_marginLeft="5dp"  
  59.         android:layout_width="50dp"  
  60.         android:layout_height="30dp"  
  61.         android:gravity="center"  
  62.         android:background="@drawable/tv_btn_round_green"  
  63.         android:text="@string/do_agree"  
  64.         android:textColor="@color/app_green_color"  
  65.         android:visibility="visible"/>  
  66.   
  67.     <TextView  
  68.         android:id="@+id/tv_do_refuse"  
  69.         android:layout_marginLeft="10dp"  
  70.         android:layout_width="50dp"  
  71.         android:layout_height="30dp"  
  72.         android:background="@drawable/tv_btn_round_red"  
  73.         android:gravity="center"  
  74.         android:text="@string/do_refuse"  
  75.         android:textColor="@color/app_red_color"  
  76.         android:visibility="visible"/>  
  77.   
  78.     <TextView  
  79.         android:id="@+id/tv_status"  
  80.         android:layout_width="wrap_content"  
  81.         android:layout_height="wrap_content"  
  82.         android:layout_marginLeft="5dp"  
  83.         android:layout_marginRight="10dp"  
  84.         android:text="@string/have_agree"  
  85.         android:visibility="gone"  
  86.         android:textColor="@color/app_black_color"/>  
  87.     </LinearLayout>  
  88.   
  89.     <View  
  90.         android:layout_marginTop="5dp"  
  91.         android:layout_below="@+id/layout_notify"  
  92.         android:layout_width="match_parent"  
  93.         android:layout_height="0.8dp"  
  94.         android:background="@color/interval_color"/>  
  95. </RelativeLayout>  

(2)綁定控件

每一項會顯示該用戶頭像和用戶名

同時,設有兩個個TextView爲「同意」和「拒絕」以及一個表示信息處理狀態的TextView(會顯示「已拒絕」或「已同意」):

a. 若獲取的系統通知的處理狀態爲「declined」(已拒絕),兩個TextView「同意」「拒絕」均不顯示,顯示「已拒絕」

b. 若獲取的系統通知的處理狀態爲「passed」(已通過驗證),兩個TextView「同意」「拒絕」均不顯示,顯示「已同意」

c.否則,同時顯示「同意」,「拒絕」。(默認情況下)

爲兩個TextView「同意」和「拒絕」分別設置onClickListener

[java]  view plain  copy
  1. @Override  
  2. public void bindView(RViewHolder holder, final int position) {  
  3.     final AddFriendNotify item = mNotifyInfoList.get(position);  
  4.     SystemMessage message = item.getMessage();  
  5.     NimUserInfo userInfo = item.getUserInfo();  
  6.     if (userInfo != null) {  
  7.         holder.setImageByUrl(CheckNotifyListActivity.this, R.id.iv_head_picture,  
  8.                 userInfo.getAvatar(), R.mipmap.bg_img_defalut);  
  9.         holder.setText(R.id.tv_name, userInfo.getName());  
  10.     } else {  
  11.         holder.setImageResource(R.id.iv_head_picture, R.mipmap.bg_img_defalut);  
  12.         holder.setText(R.id.tv_name, message.getFromAccount());  
  13.     }  
  14.   
  15.     holder.setText(R.id.tv_content, message.getContent());  
  16.   
  17.     TextView tv_status = holder.getTextView(R.id.tv_status);  
  18.     TextView tv_agree = holder.getTextView(R.id.tv_do_agree);  
  19.     TextView tv_refuse = holder.getTextView(R.id.tv_do_refuse);  
  20.     if (message.getStatus() == SystemMessageStatus.declined) {  
  21.         tv_agree.setVisibility(View.GONE);  
  22.         tv_refuse.setVisibility(View.GONE);  
  23.         tv_status.setText("已拒絕");  
  24.         tv_status.setVisibility(View.VISIBLE);  
  25.     } else if (message.getStatus() == SystemMessageStatus.passed) {  
  26.         tv_agree.setVisibility(View.GONE);  
  27.         tv_refuse.setVisibility(View.GONE);  
  28.         tv_status.setText("已同意");  
  29.         tv_status.setVisibility(View.VISIBLE);  
  30.     } else if (message.getStatus() == SystemMessageStatus.init) {  
  31.         tv_status.setText("");  
  32.         tv_status.setVisibility(View.GONE);  
  33.         tv_agree.setVisibility(View.VISIBLE);  
  34.         tv_refuse.setVisibility(View.VISIBLE);  
  35.     }  
  36.     tv_agree.setOnClickListener(new View.OnClickListener() {  
  37.         @Override  
  38.         public void onClick(View v) {  
  39.             dealRequest(item.getMessage().getFromAccount(), position, true);  
  40.         }  
  41.     });  
  42.   
  43.     tv_refuse.setOnClickListener(new View.OnClickListener() {  
  44.         @Override  
  45.         public void onClick(View v) {  
  46.             dealRequest(item.getMessage().getFromAccount(), position, false);  
  47.         }  
  48.     });  
  49. }  

(3)對驗證提醒界面中的某一項,若長按,可選擇是否刪除該條信息

[java]  view plain  copy
  1. mAdapter.setItemLongClickListener(new OnItemLongClickListener() {  
  2.             @Override  
  3.             public void onItemLongClick(RViewHolder holder, int position) {  
  4.                 ignoreRequest(position);  
  5.             }  
  6.         });  

(4)對驗證提醒界面中的某一項,若點擊,可查看該用戶信息

[java]  view plain  copy
  1. mAdapter.setItemClickListener(new OnItemClickListener() {  
  2.            @Override  
  3.            public void onItemClick(RViewHolder holder, int position) {  
  4.                showAccountInfo(position);  
  5.            }  
  6.        });  

(5)初始化好友添加通知監聽,收到信息後刷新頁面

[java]  view plain  copy
  1. NimSysMsgHandler.getInstance().setMessageListener(new SystemMessageListener() {  
  2.             @Override  
  3.             public void addFriendNotify() {  
  4.                 loadAddFriendNotify();  
  5.             }  
  6.         });  

(6)完整初始化過程

[java]  view plain  copy
  1. private void init() {  
  2.         mNotifyInfoList = new ArrayList<>();  
  3.         mAdapter = new RecycleViewAdapter<AddFriendNotify>(this, mNotifyInfoList) {  
  4.             @Override  
  5.             public int setItemLayoutId(int position) {  
  6.                 return R.layout.item_check_notify;  
  7.             }  
  8.   
  9.             @Override  
  10.             public void bindView(RViewHolder holder, final int position) {  
  11.                 final AddFriendNotify item = mNotifyInfoList.get(position);  
  12.                 SystemMessage message = item.getMessage();  
  13.                 NimUserInfo userInfo = item.getUserInfo();  
  14.                 if (userInfo != null) {  
  15.                     holder.setImageByUrl(CheckNotifyListActivity.this, R.id.iv_head_picture,  
  16.                             userInfo.getAvatar(), R.mipmap.bg_img_defalut);  
  17.                     holder.setText(R.id.tv_name, userInfo.getName());  
  18.                 } else {  
  19.                     holder.setImageResource(R.id.iv_head_picture, R.mipmap.bg_img_defalut);  
  20.                     holder.setText(R.id.tv_name, message.getFromAccount());  
  21.                 }  
  22.   
  23.                 holder.setText(R.id.tv_content, message.getContent());  
  24.   
  25.                 TextView tv_status = holder.getTextView(R.id.tv_status);  
  26.                 TextView tv_agree = holder.getTextView(R.id.tv_do_agree);  
  27.                 TextView tv_refuse = holder.getTextView(R.id.tv_do_refuse);  
  28.                 if (message.getStatus() == SystemMessageStatus.declined) {  
  29.                     tv_agree.setVisibility(View.GONE);  
  30.                     tv_refuse.setVisibility(View.GONE);  
  31.                     tv_status.setText("已拒絕");  
  32.                     tv_status.setVisibility(View.VISIBLE);  
  33.                 } else if (message.getStatus() == SystemMessageStatus.passed) {  
  34.                     tv_agree.setVisibility(View.GONE);  
  35.                     tv_refuse.setVisibility(View.GONE);  
  36.                     tv_status.setText("已同意");  
  37.                     tv_status.setVisibility(View.VISIBLE);  
  38.                 } else if (message.getStatus() == SystemMessageStatus.init) {  
  39.                     tv_status.setText("");  
  40.                     tv_status.setVisibility(View.GONE);  
  41.                     tv_agree.setVisibility(View.VISIBLE);  
  42.                     tv_refuse.setVisibility(View.VISIBLE);  
  43.                 }  
  44.                 tv_agree.setOnClickListener(new View.OnClickListener() {  
  45.                     @Override  
  46.                     public void onClick(View v) {  
  47.                         dealRequest(item.getMessage().getFromAccount(), position, true);  
  48.                     }  
  49.                 });  
  50.   
  51.                 tv_refuse.setOnClickListener(new View.OnClickListener() {  
  52.                     @Override  
  53.                     public void onClick(View v) {  
  54.                         dealRequest(item.getMessage().getFromAccount(), position, false);  
  55.                     }  
  56.                 });  
  57.             }  
  58.         };  
  59.         //若長按,可選擇是否刪除該條信息  
  60.         mAdapter.setItemLongClickListener(new OnItemLongClickListener() {  
  61.             @Override  
  62.             public void onItemLongClick(RViewHolder holder, int position) {  
  63.                 ignoreRequest(position);  
  64.             }  
  65.         });  
  66.   
  67.         //若點擊,可查看該用戶信息  
  68.         mAdapter.setItemClickListener(new OnItemClickListener() {  
  69.             @Override  
  70.             public void onItemClick(RViewHolder holder, int position) {  
  71.                 showAccountInfo(position);  
  72.             }  
  73.         });  
  74.   
  75.         mRecyclerView.setLayoutManager(new LinearLayoutManager(this));  
  76.         mRecyclerView.setAdapter(mAdapter);  
  77.   
  78.         // Tool Bar  
  79.         mIvBack.setOnClickListener(new View.OnClickListener() {  
  80.             @Override  
  81.             public void onClick(View v) {  
  82.                 finish();  
  83.             }  
  84.         });  
  85.   
  86.         // 初始化好友添加通知監聽,收到信息後刷新頁面  
  87.         NimSysMsgHandler.getInstance().setMessageListener(new SystemMessageListener() {  
  88.             @Override  
  89.             public void addFriendNotify() {  
  90.                 loadAddFriendNotify();  
  91.             }  
  92.         });  
  93.   
  94.         loadAddFriendNotify();  
  95.     }  


2. 讀取好友添加通知數據(loadAddFriendNotify)

(1)獲取「添加朋友」消息列表

通過NimClient的getService接口獲取到SystemMessageService(系統通知消息接口)服務實例,調用querySystemMessageByTypeBlock方法根據類型查詢系統通知列表

(2)根據對方賬戶,獲取賬戶信息,構建顯示item數據

item數據在兩種情況下不顯示:

a. 若獲取到的系統通知的處理狀態爲ignored(已忽略)

b. 若獲取不到該條記錄的賬戶數據

其餘顯示的item設置信息,設置好友(通過NimFriendHandler的CheckIsMyFriend(檢查該賬戶是否爲我的好友)),設置信息,添加到通知列表

(3)刷新界面

(4)將「添加朋友」消息置爲已讀

[java]  view plain  copy
  1. private void loadAddFriendNotify() {  
  2.         List<SystemMessageType> types = new ArrayList<>();  
  3.         types.add(SystemMessageType.AddFriend);  
  4.   
  5.         // 獲取「添加朋友」消息列表  
  6.         List<SystemMessage> msgList = NIMClient.getService(SystemMessageService.class)  
  7.                 .querySystemMessageByTypeBlock(types, 0, LOAD_MESSAGE_COUNT);  
  8.   
  9.         // 根據對方賬戶,獲取賬戶信息,構建顯示 item 數據  
  10.         AddFriendNotify notify;  
  11.         List<AddFriendNotify> notifyInfoList = new ArrayList<>();  
  12.         for (SystemMessage message : msgList) {  
  13.             // 若用戶已選擇忽略這條消息,則跳過不顯示  
  14.             if (message.getStatus() == SystemMessageStatus.ignored) {  
  15.                 continue;  
  16.             }  
  17.             NimUserInfo userInfo = NimUserHandler.getInstance().getUserInfo();  
  18.             //若獲取不到該條記錄的賬戶數據,也跳過不顯示  
  19.             if (userInfo == null) {  
  20.                 return;  
  21.             }  
  22.   
  23.             notify = new AddFriendNotify();  
  24.             notify.setMessage(message);  
  25.             notify.setMyFriend(NimFriendHandler.getInstance().CheckIsMyFriend(message.getFromAccount()));  
  26.             notify.setUserInfo(userInfo);  
  27.             notifyInfoList.add(notify);  
  28.         }  
  29.   
  30.         // 刷新界面  
  31.         mNotifyInfoList.clear();  
  32.         mNotifyInfoList.addAll(notifyInfoList);  
  33.         mAdapter.notifyDataSetChanged();  
  34.   
  35.         // 將「添加朋友」消息至爲已讀  
  36.         NIMClient.getService(SystemMessageService.class)  
  37.                 .resetSystemMessageUnreadCountByType(types);  
  38.     }  


3. 處理好友請求(dealRequest)

通過NimClient的getService接口獲取到FriendService(好友管理/好友關係/黑名單關係/消息提醒相關操作)服務實例,調用ackAddFriendRequest方法進行同意/拒絕好友請求

設置回調,三種情況

(1)成功(onSuccess)

       a. 如果同意,則將系統消息狀態設置爲"passed"(已通過驗證)

       b. 否則,將系統消息狀態設置爲"declined"(已拒絕)

       通過NimClient的getService接口獲取到SystemMessageService(系統通知消息接口)服務實例調用setSystemMessageStatus

       方法設置系統通知狀態(根據前面同意與否所決定的狀態設置)

(2)失敗(onFailed):顯示消息「處理失敗,code:xxx」

(3)出錯(onException):顯示消息「處理出錯:xxx」

[java]  view plain  copy
  1. private void dealRequest(String account, int position, final boolean agree) {  
  2.         final SystemMessage message = mNotifyInfoList.get(position).getMessage();  
  3.         NIMClient.getService(FriendService.class)  
  4.                 .ackAddFriendRequest(account, agree).setCallback(new RequestCallback<Void>() {  
  5.             @Override  
  6.             public void onSuccess(Void param) {  
  7.                 SystemMessageStatus status;  
  8.                 if (agree) {  
  9.                     status = SystemMessageStatus.passed;  
  10.                 } else {  
  11.                     status = SystemMessageStatus.declined;  
  12.                 }  
  13.                 NIMClient.getService(SystemMessageService.class)  
  14.                         .setSystemMessageStatus(message.getMessageId(), status);  
  15.                 message.setStatus(status);  
  16.                 mAdapter.notifyDataSetChanged();  
  17.                 haveChange = true;  
  18.             }  
  19.   
  20.             @Override  
  21.             public void onFailed(int code) {  
  22.                 ToastUtils.showMessage(CheckNotifyListActivity.this"處理失敗,code:" + code);  
  23.             }  
  24.   
  25.             @Override  
  26.             public void onException(Throwable exception) {  
  27.                 ToastUtils.showMessage(CheckNotifyListActivity.this"處理出錯:" + exception.getMessage());  
  28.             }  
  29.         });  
  30.     }  

4. 刪除並忽略該條記錄——對應於初始化中若長按某一項所進行的操作

利用AlertDialog:

(1)setMessege:設置對話框中的內容爲「是否刪除該條記錄?」

(2)setCancelable(true):設置當點對話框以外的地方,退出對話框

(3)setPositiveButton:確定刪除,通過NimClient的getService接口獲取到SystemMessageService()服務實例,調用setSystemMessageStatus方法設置狀態爲ignored

    通知列表中刪除該條

    退出對話框

(4)setNegativeButton:取消,退出對話框

[java]  view plain  copy
  1. private void ignoreRequest(final int position) {  
  2.         new AlertDialog.Builder(this)  
  3.                 .setMessage("是否刪除該條記錄?")  
  4.                 .setCancelable(true)  
  5.                 .setPositiveButton("確定"new DialogInterface.OnClickListener() {  
  6.                     @Override  
  7.                     public void onClick(DialogInterface dialog, int which) {  
  8.                         SystemMessage message = mNotifyInfoList.get(position).getMessage();  
  9.                         NIMClient.getService(SystemMessageService.class)  
  10.                                 .setSystemMessageStatus(message.getMessageId(),  
  11.                                         SystemMessageStatus.ignored);  
  12.                         mNotifyInfoList.remove(position);  
  13.                         mAdapter.notifyDataSetChanged();  
  14.                         dialog.dismiss();  
  15.                     }  
  16.                 })  
  17.                 .setNegativeButton("取消"new DialogInterface.OnClickListener() {  
  18.                     @Override  
  19.                     public void onClick(DialogInterface dialog, int which) {  
  20.                         dialog.dismiss();  
  21.                     }  
  22.                 }).show();  
  23.   
  24.     }  

5. 顯示賬號信息(showAccountInfo)——對應於初始化中若點擊,可查看該用戶信息

跳轉到FriendInfoActivity(之前博客已寫)

a. 若已經是朋友(flag == FLAG_SHOW_FRIEND),則FriendInfoActivity中可選擇「發送信息」,「視頻聊天」

b. 否則(flag == FLAG_ADD_FRIEND), 則FriendInfoActivity中只可選擇「添加到通訊錄」

[java]  view plain  copy
  1. private void showAccountInfo(int position){  
  2.         AddFriendNotify notifyInfo = mNotifyInfoList.get(position);  
  3.         Intent intent = new Intent(this,FriendInfoActivity.class);  
  4.         intent.putExtra("NimUserInfo",notifyInfo.getUserInfo());  
  5.         if (notifyInfo.isMyFriend()){  
  6.             intent.putExtra("FLAG",FriendInfoActivity.FLAG_SHOW_FRIEND);  
  7.         }else {  
  8.             intent.putExtra("FLAG",FriendInfoActivity.FLAG_ADD_FRIEND);  
  9.         }  
  10.         startActivity(intent);  
  11.     }  



附上完整CheckNotifyListActivity.java

[java]  view plain  copy
  1. package com.ezreal.ezchat.activity;  
  2.   
  3. import android.content.DialogInterface;  
  4. import android.content.Intent;  
  5. import android.os.Bundle;  
  6. import android.support.annotation.Nullable;  
  7. import android.support.v7.app.AlertDialog;  
  8. import android.support.v7.widget.LinearLayoutManager;  
  9. import android.support.v7.widget.RecyclerView;  
  10. import android.view.View;  
  11. import android.widget.TextView;  
  12.   
  13. import com.ezreal.ezchat.R;  
  14. import com.ezreal.ezchat.bean.AddFriendNotify;  
  15. import com.ezreal.ezchat.handler.NimFriendHandler;  
  16. import com.ezreal.ezchat.handler.NimUserHandler;  
  17. import com.ezreal.ezchat.handler.NimSysMsgHandler;  
  18. import com.ezreal.ezchat.handler.NimSysMsgHandler.SystemMessageListener;  
  19. import com.netease.nimlib.sdk.NIMClient;  
  20. import com.netease.nimlib.sdk.RequestCallback;  
  21. import com.netease.nimlib.sdk.friend.FriendService;  
  22. import com.netease.nimlib.sdk.msg.SystemMessageService;  
  23. import com.netease.nimlib.sdk.msg.constant.SystemMessageStatus;  
  24. import com.netease.nimlib.sdk.msg.constant.SystemMessageType;  
  25. import com.netease.nimlib.sdk.msg.model.SystemMessage;  
  26. import com.netease.nimlib.sdk.uinfo.model.NimUserInfo;  
  27. import com.ezreal.ezchat.commonlibrary.adapter.OnItemClickListener;  
  28. import com.ezreal.ezchat.commonlibrary.adapter.OnItemLongClickListener;  
  29. import com.ezreal.ezchat.commonlibrary.adapter.RViewHolder;  
  30. import com.ezreal.ezchat.commonlibrary.adapter.RecycleViewAdapter;  
  31. import com.ezreal.ezchat.commonlibrary.utils.ToastUtils;  
  32.   
  33. import java.util.ArrayList;  
  34. import java.util.List;  
  35.   
  36. import butterknife.BindView;  
  37. import butterknife.ButterKnife;  
  38.   
  39. /** 
  40.  * Created by 張靜 
  41.  */  
  42.   
  43. public class CheckNotifyListActivity extends BaseActivity {  
  44.   
  45.     public static final int RESULT_HAVE_CHANGE = 0x4000;  
  46.     private static final int LOAD_MESSAGE_COUNT = 500;  
  47.     @BindView(R.id.rcv_notify_list)  
  48.     RecyclerView mRecyclerView;  
  49.     private List<AddFriendNotify> mNotifyInfoList;  
  50.     private RecycleViewAdapter<AddFriendNotify> mAdapter;  
  51.     private boolean haveChange = false;  
  52.   
  53.     @Override  
  54.     protected void onCreate(@Nullable Bundle savedInstanceState) {  
  55.         super.onCreate(savedInstanceState);  
  56.         setStatusBarColor(R.color.app_blue_color);  
  57.         setContentView(R.layout.activity_check_notify);  
  58.         setTitleBar("驗證提醒"truetrue);  
  59.         ButterKnife.bind(this);  
  60.         init();  
  61.     }  
  62.   
  63.     private void init() {  
  64.         mNotifyInfoList = new ArrayList<>();  
  65.         mAdapter = new RecycleViewAdapter<AddFriendNotify>(this, mNotifyInfoList) {  
  66.             @Override  
  67.             public int setItemLayoutId(int position) {  
  68.                 return R.layout.item_check_notify;  
  69.             }  
  70.   
  71.             @Override  
  72.             public void bindView(RViewHolder holder, final int position) {  
  73.                 final AddFriendNotify item = mNotifyInfoList.get(position);  
  74.                 SystemMessage message = item.getMessage();  
  75.                 NimUserInfo userInfo = item.getUserInfo();  
  76.                 if (userInfo != null) {  
  77.                     holder.setImageByUrl(CheckNotifyListActivity.this, R.id.iv_head_picture,  
  78.                             userInfo.getAvatar(), R.mipmap.bg_img_defalut);  
  79.                     holder.setText(R.id.tv_name, userInfo.getName());  
  80.                 } else {  
  81.                     holder.setImageResource(R.id.iv_head_picture, R.mipmap.bg_img_defalut);  
  82.                     holder.setText(R.id.tv_name, message.getFromAccount());  
  83.                 }  
  84.   
  85.                 holder.setText(R.id.tv_content, message.getContent());  
  86.   
  87.                 TextView tv_status = holder.getTextView(R.id.tv_status);  
  88.                 TextView tv_agree = holder.getTextView(R.id.tv_do_agree);  
  89.                 TextView tv_refuse = holder.getTextView(R.id.tv_do_refuse);  
  90.                 if (message.getStatus() == SystemMessageStatus.declined) {  
  91.                     tv_agree.setVisibility(View.GONE);  
  92.                     tv_refuse.setVisibility(View.GONE);  
  93.                     tv_status.setText("已拒絕");  
  94.                     tv_status.setVisibility(View.VISIBLE);  
  95.                 } else if (message.getStatus() == SystemMessageStatus.passed) {  
  96.                     tv_agree.setVisibility(View.GONE);  
  97.                     tv_refuse.setVisibility(View.GONE);  
  98.                     tv_status.setText("已同意");  
  99.                     tv_status.setVisibility(View.VISIBLE);  
  100.                 } else if (message.getStatus() == SystemMessageStatus.init) {  
  101.                     tv_status.setText("");  
  102.                     tv_status.setVisibility(View.GONE);  
  103.                     tv_agree.setVisibility(View.VISIBLE);  
  104.                     tv_refuse.setVisibility(View.VISIBLE);  
  105.                 }  
  106.                 tv_agree.setOnClickListener(new View.OnClickListener() {  
  107.                     @Override  
  108.                     public void onClick(View v) {  
  109.                         dealRequest(item.getMessage().getFromAccount(), position, true);  
  110.                     }  
  111.                 });  
  112.   
  113.                 tv_refuse.setOnClickListener(new View.OnClickListener() {  
  114.                     @Override  
  115.                     public void onClick(View v) {  
  116.                         dealRequest(item.getMessage().getFromAccount(), position, false);  
  117.                     }  
  118.                 });  
  119.             }  
  120.         };  
  121.         mAdapter.setItemLongClickListener(new OnItemLongClickListener() {  
  122.             @Override  
  123.             public void onItemLongClick(RViewHolder holder, int position) {  
  124.                 ignoreRequest(position);  
  125.             }  
  126.         });  
  127.   
  128.         mAdapter.setItemClickListener(new OnItemClickListener() {  
  129.             @Override  
  130.             public void onItemClick(RViewHolder holder, int position) {  
  131.                 showAccountInfo(position);  
  132.             }  
  133.         });  
  134.   
  135.         mRecyclerView.setLayoutManager(new LinearLayoutManager(this));  
  136.         mRecyclerView.setAdapter(mAdapter);  
  137.   
  138.         // Tool Bar  
  139.         mIvBack.setOnClickListener(new View.OnClickListener() {  
  140.             @Override  
  141.             public void onClick(View v) {  
  142.                 finish();  
  143.             }  
  144.         });  
  145.   
  146.         // 初始化好友添加通知監聽,收到信息後刷新頁面  
  147.         NimSysMsgHandler.getInstance().setMessageListener(new SystemMessageListener() {  
  148.             @Override  
  149.             public void addFriendNotify() {  
  150.                 loadAddFriendNotify();  
  151.             }  
  152.         });  
  153.   
  154.         loadAddFriendNotify();  
  155.     }  
  156.   
  157.     /** 
  158.      * 讀取好友添加通知數據 
  159.      */  
  160.     private void loadAddFriendNotify() {  
  161.         List<SystemMessageType> types = new ArrayList<>();  
  162.         types.add(SystemMessageType.AddFriend);  
  163.   
  164.         // 獲取「添加朋友」消息列表  
  165.         List<SystemMessage> msgList = NIMClient.getService(SystemMessageService.class)  
  166.                 .querySystemMessageByTypeBlock(types, 0, LOAD_MESSAGE_COUNT);  
  167.   
  168.         // 根據對方賬戶,獲取賬戶信息,構建顯示 item 數據  
  169.         AddFriendNotify notify;  
  170.         List<AddFriendNotify> notifyInfoList = new ArrayList<>();  
  171.         for (SystemMessage message : msgList) {  
  172.             // 若用戶已選擇忽略這條消息,則跳過不顯示  
  173.             if (message.getStatus() == SystemMessageStatus.ignored) {  
  174.                 continue;  
  175.             }  
  176.             NimUserInfo userInfo = NimUserHandler.getInstance().getUserInfo();  
  177.             //若獲取不到該條記錄的賬戶數據,也跳過不顯示  
  178.             if (userInfo == null) {  
  179.                 return;  
  180.             }  
  181.   
  182.             notify = new AddFriendNotify();  
  183.             notify.setMessage(message);  
  184.             notify.setMyFriend(NimFriendHandler.getInstance().CheckIsMyFriend(message.getFromAccount()));  
  185.             notify.setUserInfo(userInfo);  
  186.             notifyInfoList.add(notify);  
  187.         }  
  188.   
  189.         // 刷新界面  
  190.         mNotifyInfoList.clear();  
  191.         mNotifyInfoList.addAll(notifyInfoList);  
  192.         mAdapter.notifyDataSetChanged();  
  193.   
  194.         // 將「添加朋友」消息至爲已讀  
  195.         NIMClient.getService(SystemMessageService.class)  
  196.                 .resetSystemMessageUnreadCountByType(types);  
  197.     }  
  198.   
  199.     /** 
  200.      * 處理好友請求 
  201.      * 
  202.      * @param account  對方賬戶 
  203.      * @param position 列表位置 
  204.      * @param agree    是否同意 
  205.      */  
  206.     private void dealRequest(String account, int position, final boolean agree) {  
  207.         final SystemMessage message = mNotifyInfoList.get(position).getMessage();  
  208.         NIMClient.getService(FriendService.class)  
  209.                 .ackAddFriendRequest(account, agree).setCallback(new RequestCallback<Void>() {  
  210.             @Override  
  211.             public void onSuccess(Void param) {  
  212.                 SystemMessageStatus status;  
  213.                 if (agree) {  
  214.                     status = SystemMessageStatus.passed;  
  215.                 } else {  
  216.                     status = SystemMessageStatus.declined;  
  217.                 }  
  218.                 NIMClient.getService(SystemMessageService.class)  
  219.                         .setSystemMessageStatus(message.getMessageId(), status);  
  220.                 message.setStatus(status);  
  221.                 mAdapter.notifyDataSetChanged();  
  222.                 haveChange = true;  
  223.             }  
  224.   
  225.             @Override  
  226.             public void onFailed(int code) {  
  227.                 ToastUtils.showMessage(CheckNotifyListActivity.this"處理失敗,code:" + code);  
  228.             }  
  229.   
  230.             @Override  
  231.             public void onException(Throwable exception) {  
  232.                 ToastUtils.showMessage(CheckNotifyListActivity.this"處理出錯:" + exception.getMessage());  
  233.             }  
  234.         });  
  235.     }  
  236.   
  237.     /** 
  238.      * 刪除並忽略該條記錄 
  239.      * @param position 所在位置 
  240.      */  
  241.     private void ignoreRequest(final int position) {  
  242.         new AlertDialog.Builder(this)  
  243.                 .setMessage("是否刪除該條記錄?")  
  244.                 .setCancelable(true)  
  245.                 .setPositiveButton("確定"new DialogInterface.OnClickListener() {  
  246.                     @Override  
  247.                     public void onClick(DialogInterface dialog, int which) {  
  248.                         SystemMessage message = mNotifyInfoList.get(position).getMessage();  
  249.                         NIMClient.getService(SystemMessageService.class)  
  250.                                 .setSystemMessageStatus(message.getMessageId(),  
  251.                                         SystemMessageStatus.ignored);  
  252.                         mNotifyInfoList.remove(position);  
  253.                         mAdapter.notifyDataSetChanged();  
  254.                         dialog.dismiss();  
  255.         new AlertDialog.Builder(this)  
  256.                 .setMessage("是否刪除該條記錄?")  
  257.                 .setCancelable(true)  
  258.                 .setPositiveButton("確定"new DialogInterface.OnClickListener() {  
  259.                     @Override  
  260.                     public void onClick(DialogInterface dialog, int which) {  
  261.                         SystemMessage message = mNotifyInfoList.get(position).getMessage();  
  262.                         NIMClient.getService(SystemMessageService.class)  
  263.                                 .setSystemMessageStatus(message.getMessageId(),  
  264.                                         SystemMessageStatus.ignored);  
  265.                         mNotifyInfoList.remove(position);  
  266.                         mAdapter.notifyDataSetChanged();  
  267.                         dialog.dismiss();  
  268. new DialogInterface.OnClickListener() {  
  269.                     @Override  
  270.                     public void onClick(DialogInterface dialog, int which) {  
  271.                         SystemMessage message = mNotifyInfoList.get(position).getMessage();  
  272.                         NIMClient.getService(SystemMessageService.class)  
  273.                                 .setSystemMessageStatus(message.getMessageId(),  
  274.                                         SystemMessageStatus.ignored);  
  275.                         mNotifyInfoList.remove(position);  
  276.                         mAdapter.notifyDataSetChanged();  
  277.                         dialog.dismiss();  
  278.                     }  
  279.                 })  
  280.                 .setNegativeButton("取消"new DialogInterface.OnClickListener() {  
  281.                                         SystemMessageStatus.ignored);  
  282.                   &nbs
相關文章
相關標籤/搜索