Handler漏れ防止の正しい使用姿勢

2024 ワード

ある年ある月ある日VLCのソースコードで見かけたのでまとめてみます

public class WeakHandler extends Handler {
    private final WeakReference mHandlerReference;

    public WeakHandler(T owner) {
        mHandlerReference = new WeakReference<>(owner);
    }


    @Override
    public void handleMessage(Message msg) {
        final T owner = getOwner();
        if (owner != null) {
            owner.handleMessage(msg);
        }
    }

    public interface MessageListener {
        public void handleMessage(Message msg);
    }

    public T getOwner() {
        return this.mHandlerReference.get();
    }

    public void clear() {
        mHandlerReference.clear();
    }
}

activityで使用

public class HandlerActivity extends Activity implements MyWeakHandler.MessageListener {

    private static MyWeakHandler sHandler;//       ,         
    public static final int MSG_ON_A = 0x111;
    public static final int MSG_ON_B = 0x112;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        sHandler = new MyWeakHandler<>(this);
    }


    @Override
    protected void onDestroy() {
        super.onDestroy();
        sHandler.removeCallbacksAndMessages(null);//          
        sHandler.clear();
        sHandler=null;
    }

    private void backgroundWorkA() {

        .....
        //    ,      run    Android         ,        BluetoothAdapter.LeScanCallback  onLeScan()    
        sHandler.obtainMessage(MSG_ON_A).sendToTarget();
        .....
    }

    private void backgroundWorkB() {

        ....
        //    
        sHandler.obtainMessage(MSG_ON_B).sendToTarget();
        .....
    }

    @Override
    public void handleMessage(Message msg) {
        switch (msg.what) { //      
            case MSG_ON_A:
                break;
            case MSG_ON_B:
                break;
        }

    }
}