将上下文传递给Handler

时间:2011-03-28 17:13:42

标签: android view handler android-context

是否可以将参数传递给Android Handler?我有两段代码。

new Thread(){
        public void run(){
            for(;;){
                uiCallback.sendEmptyMessage(0);
                Thread.sleep(2000); //sleep for 2 seconds
            }
        }
    }.start();


    private Handler uiCallback = new Handler(){
    public void handleMessage(Message msg){
        //add a new blossom to the blossom ArrayList!!
        blossomArrayList.add(new Blossom(context, R.drawable.blossom));
    }
};

我当然得到一个错误,因为Handler方法无法看到我的上下文。这可能是因为这段代码

public BoardView(Context context){
    super(context);

在其他地方看不到上下文,我想知道我是否可以将它作为参数传递给我的Handler。

编辑:我发布了两个主要代码片段来回答有关为什么我的Blossom对象需要上下文的问题。我自己并非100%确定>。>也许你可以看看,看看发生了什么。

public class Blossom{
private Bitmap blossom;
private float blossomX = 0;
private float blossomY = 0;
private Random generator = new Random();

public Blossom(Context context, int drawable)
{
    blossom = BitmapFactory.decodeResource(context.getResources(), drawable); 
    blossomX = generator.nextInt(300);
}

public Bitmap getBitmap()
{
    return blossom;
}

public float getBlossomX()
{
    return blossomX;
}

public float getBlossomY()
{
    return blossomY;
}

public void Fall(Canvas canvas, float boxY)
{
    //draws the flower falling
    canvas.drawBitmap(blossom, blossomX,
            blossomY = blossomY+3 , null);

    //collision detection, currently not working after 
    //implementing random start location

    //if(blossomY + 29 == boxY)
    //{
        //canvas.drawBitmap(blossom,0,0,null);
    //}

}
}


public class BoardView extends SurfaceView implements SurfaceHolder.Callback{
Context mContext;

Bitmap box = 
    (BitmapFactory.decodeResource
            (getResources(), R.drawable.box));

private BoardThread thread;
private float box_x = 140;
private float box_y = 378;
private float boxWidth = box.getWidth();
private float boxHeight = box.getHeight();
private ArrayList<Blossom> blossomArrayList = new ArrayList<Blossom>();;

boolean mode = false;

RectF boxRect = new RectF(box_x,box_y, box_x + boxWidth, box_y + boxHeight);

public BoardView(Context context){
    super(context);

    //surfaceHolder provides canvas that we draw on
    getHolder().addCallback(this);

    // controls drawings
    thread = new BoardThread(getHolder(),this);

    //pass variables to instance of Blossom
    //for(int i = 0; i <= 3; i++)
    //{
        //blossomArrayList.add(new Blossom(context, R.drawable.blossom));
    //}

    new Thread(){
        public void run(){
            for(;;){
                uiCallback.sendEmptyMessage(0);
                Thread.sleep(2000); //sleep for 2 seconds
            }
        }
    }.start();

    //intercepts touch events
    setFocusable(true);

}

@Override

public void onDraw(Canvas canvas){
    canvas.drawColor(Color.WHITE);  


    //draw box and set start location
    canvas.drawBitmap(box, box_x - (boxWidth/2), 
            box_y - (boxHeight/2), null);

    for(int i = 0; i<= 3; i++)
    {
        blossomArrayList.get(i).Fall(canvas, box_y);
    }

}

@Override
public boolean onTouchEvent(MotionEvent event){

    if(event.getAction() == MotionEvent.ACTION_DOWN){
        if(boxRect.contains(event.getX(),event.getY())){
            mode = true;
        }
    }

    if(event.getAction() == MotionEvent.ACTION_MOVE) {
        if(boxRect.contains(event.getX(),event.getY())){
            mode = true;
        }
        if(mode == true){
            box_x = (int)event.getX();
            boxRect.set(box_x,box_y, box_x + boxWidth, box_y + boxHeight);
        }

    }

    if(event.getAction() == MotionEvent.ACTION_UP){
        mode = false;
    }

    invalidate();

    return true;
}

@Override
public void surfaceChanged(SurfaceHolder holder, 
        int format, int width, int height ){

}

@Override
public void surfaceCreated(SurfaceHolder holder){
    thread.startRunning(true);
    thread.start();
}

@Override
public void surfaceDestroyed(SurfaceHolder holder){
    thread.startRunning(false);
    thread.stop();
}

private Handler uiCallback = new Handler(){
    public void handleMessage(Message msg){
        //add a new blossom to the blossom ArrayList!!
        blossomArrayList.add(new Blossom(context, R.drawable.blossom));
    }
};


}

2 个答案:

答案 0 :(得分:3)

如果您创建一个扩展Handler的子类,该怎么办?这样你就可以传递你想要的任何参数。

但出于好奇,为什么Blossom对象需要上下文对象?通常最好将逻辑与GUI依赖关系分开。

答案 1 :(得分:2)

创建一个扩展Handler的类,并存储对上下文的弱引用。这有助于防止出现一些内存问题。

public class SomeHandler extends Handler {

    // A weak reference to the enclosing context
    private WeakReference<Context> mContext;

    public SomeHandler (Context context) {
        mContext = new WeakReference<Context>(context);
    }

    public void handleMessage(Message msg) {

        // Get an actual reference to the DownloadActivity
        // from the WeakReference.
        Context context=mContext.get();
        ...
    }
}