Question

I am new in android. I write a program that ball moves via accelerometer sensor and this good works. I use Timer and schedule method for this(schedule(mTimerTask, delay,period);) I have two buttons in my screen and i want when user click in positive button, period and delay value increases and when clicked in negative button, these values decreases. I write this code but the changes values in onClick method not fix in onResume method. I know onResume method called as a part of the life cycle but i dont know how can i solve my problem! please help me :) thanks

public class MainActivity extends Activity {

    float result=0;
    BallView ball=null;
    Handler redrawHandler=new Handler();
    //
    Timer mTimer;
    TimerTask mTimerTask;
    //
    int mSrcWidth,mSrcHeight;
    PointF mBallPos,mBallSpd;
    //
    Button positiveBtn;
    Button negativeBtn;
    //
    int delay=10;
    int period=10;

    @Override
    public void onCreate(Bundle savedInstanceState){
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        positiveBtn=(Button)findViewById(R.id.positiveBtn);
        negativeBtn=(Button)findViewById(R.id.negativeBtn);

        Log.e("onclick", "in oncreate");

        getWindow().setFlags(0xFFFFFFFF, LayoutParams.FLAG_FULLSCREEN|LayoutParams.FLAG_KEEP_SCREEN_ON);

        final FrameLayout frame=(FrameLayout)findViewById(R.id.main_view);

        //
        Display display=getWindowManager().getDefaultDisplay();

        mSrcWidth=display.getWidth();
        mSrcHeight=display.getHeight();
        mBallPos=new PointF();
        mBallSpd=new PointF();

        mBallPos.x=mSrcWidth/2;
        mBallPos.y=mSrcHeight/2;
        mBallSpd.x=0;
        mBallSpd.y=0;

        ball=new BallView(this,mBallPos.x,mBallPos.y,10);
        frame.addView(ball);
        //
        ball.invalidate();


        positiveBtn.setOnClickListener(onClickListener);
        negativeBtn.setOnClickListener(onClickListener);

        SensorManager sm=(SensorManager)getSystemService(Context.SENSOR_SERVICE);

        sm.registerListener(new SensorEventListener(){

            public void onAccuracyChanged(Sensor sensor, int accuracy) {
                // TODO Auto-generated method stub

            }

            public void onSensorChanged(SensorEvent event) {
                // TODO Auto-generated method stub
                //
                mBallSpd.x=-event.values[0];
                mBallSpd.y=event.values[1];
            }
        //  
        },sm.getSensorList(Sensor.TYPE_ACCELEROMETER).get(0), SensorManager.SENSOR_DELAY_NORMAL);

        Log.e("onclick", "in onsensor");
    }

    private OnClickListener onClickListener=new OnClickListener(){

        public void onClick(View v) {
            // TODO Auto-generated method stub
            switch(v.getId()){
            case R.id.negativeBtn:
                if(delay<=5&&period<=5)
                    delay=period=5;
                else{
                    delay=delay-10;
                    period=period-10;
                }
            break;
            case R.id.positiveBtn:
                if(delay>=50&&period>=50)
                    delay=period=150;
                else{
                    delay=delay+10;
                    period=period+10;
                }
                break;
            }

            Log.e("delay","="+ delay);
            Log.e("period","="+ period);
        }


    } ;

    @Override
    public void onPause(){
        mTimer.cancel();
        mTimer=null;
        mTimerTask=null;
        super.onPause();
    }

    @Override
    public void onResume(){

        mTimer=new Timer();
        mTimerTask=new TimerTask(){
            public void run(){

                //Log.e("in ", "onResume()");

                //positiveBtn.setOnClickListener(onClickListener);
                //negativeBtn.setOnClickListener(onClickListener);

                mBallPos.x+=mBallSpd.x;
                mBallPos.y+=mBallSpd.y;
                if(mBallPos.x>=mSrcWidth)
                    mBallPos.x=mSrcWidth;
                if(mBallPos.y>=mSrcHeight)
                    mBallPos.y=mSrcHeight;
                if(mBallPos.x<=0)
                    mBallPos.x=0;
                if(mBallPos.y<=0)
                    mBallPos.y=0;

                ball.x=mBallPos.x;
                ball.y=mBallPos.y;

                redrawHandler.post(new Runnable(){

                    public void run() {
                        // TODO Auto-generated method stub
                        ball.invalidate();
                    }

                });
            }
        };

        mTimer.schedule(mTimerTask, delay,period);
        super.onResume();
    }
Was it helpful?

Solution

Implement onSaveInstanceState like so:

@Override
public void onSaveInstanceState(Bundle savedInstanceState) {
    // Save the user's current game state
    savedInstanceState.putInt("STATE_DELAY", delay);
    savedInstanceState.putInt("STATE_PERIOD", period);

    // Always call the superclass so it can save the view hierarchy state
    super.onSaveInstanceState(savedInstanceState);
}

and then inside your onCreate try to restore them (if they have been set) like so:

// Check whether we're recreating a previously destroyed instance
if (savedInstanceState != null) {
    // Restore value of members from saved state
    delay = savedInstanceState.getInt("STATE_DELAY");
    period = savedInstanceState.getInt("STATE_PERIOD");
}

And finally as I wrote in the comments of the question have a look at the Recreating an Activity training page.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top