使用Activity和Delegate與適配器交互

在這個Demo裏,我們會分析如何通過委託模式(Delegation Pattern)幫助開發者把所有的業務邏輯從適配器中移到Activity中。我們創建一個簡單的應用程序,通過該應用程序可以向列表中添加電話號碼,列表中每一行都有一個Remove按鈕,用於刪除電話號碼。

在適配器中實現“Remove”按鈕的點擊處理器,但是,並不在適配器中實現刪除對象的方法。我們通過一個委託接口調用Activity的方法刪除對象。首先創建適配器的代碼,如下所示:

package com.example.huangfei.myapplication;

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.TextView;

import java.util.List;

/**
 * Created by huangfeihong on 2015/12/19.
 */
public class NumbersAdapter extends ArrayAdapter<Integer> {

    //定義委託接口
    public interface NumbersAdapterDelegate {
        void removeItem(Integer value);
    }

    private Context mContext;
    private LayoutInflater mInflater;
    private NumbersAdapterDelegate mDelegate;

    public NumbersAdapter(Context context, List<Integer> objects) {
        super(context, 0, objects);
        mContext = context;
        mInflater = LayoutInflater.from(context);
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        if (convertView == null)
            convertView = mInflater.inflate(R.layout.number_row, parent, false);

        final Integer value = getItem(position);
        TextView tv = (TextView) convertView.findViewById(R.id.numbers_row_text);
        tv.setText(value.toString());

        View button = convertView.findViewById(R.id.numbers_row_button);
        button.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                if (null != mDelegate) {//刪除對象
                    mDelegate.removeItem(value);
                }
            }
        });

        return convertView;
    }

    //爲適配器設置委託對象
    public void setDelegate(NumbersAdapterDelegate delegate) {
        mDelegate = delegate;
    }
}

現在適配器已經準備就緒,接下來分析Activity的代碼:

package com.example.huangfei.myapplication;

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.Toast;

import java.util.ArrayList;

public class MainActivity extends Activity implements NumbersAdapter.NumbersAdapterDelegate {
    private static final String TAG = MainActivity.class
            .getCanonicalName();

    private ListView mListView;
    private ArrayList<Integer> mNumbers;
    private NumbersAdapter mAdapter;
    private EditText mEditText;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        mEditText = (EditText) findViewById(R.id.main_edittext);
        mListView = (ListView) findViewById(R.id.main_listview);
        mNumbers = new ArrayList<Integer>();
        mAdapter = new NumbersAdapter(this, mNumbers);
        mListView.setAdapter(mAdapter);
    }

    @Override
    protected void onResume() {
        super.onResume();
        //註冊委託對象
        mAdapter.setDelegate(this);
    }

    @Override
    protected void onPause() {
        super.onPause();
        //取消註冊委託對象
        mAdapter.setDelegate(null);
    }

    @Override
    public void removeItem(Integer value) {
        //從列表中移除指定項
        mNumbers.remove(value);
        Toast.makeText(this, "Removed object: " + value, Toast.LENGTH_SHORT).show();
        mAdapter.notifyDataSetChanged();
    }

    public void addNumber(View v) {
        String value = mEditText.getText().toString().trim();
        try {
            mNumbers.add(Integer.valueOf(value));
            mEditText.setText("");
            mAdapter.notifyDataSetChanged();
        } catch (NumberFormatException e) {
            Log.e(TAG, "Couldn't convert to integer the string: " + value);
        }
    }
}

委託模式在IOS開發中也被大量使用。比如,創建HTTP請求時,開發者可以設置一個委託對象,當請求處理完畢後指定一些操作。當編寫程序時,我們應時刻注意使用委託對象來組織代碼。

代碼地址

發佈了86 篇原創文章 · 獲贊 6 · 訪問量 11萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章