Satheesh Kumar
Satheesh Kumar

Reputation: 716

How to solve lag in Live Wallpaper?

I'm creating my first live wallpaper in which snow will produce on random location and start animate.But it lags. This was my code.

There is no error in the code but it lags.If i increased the number of snows,it lags more. How to solve lag?

public class CybWallpaper extends WallpaperService {

    @Override
    public Engine onCreateEngine() {
        return new Mywall();
    }
    public class Mywall extends Engine
    {
        int x[]=new int[30],y[]=new int[30];
        int isr=0;
        int scw,sch;
        Canvas dra;
        int temps[]=new int[30];
        boolean isft=true;


        Handler hand=new Handler();
        boolean isrun;
        Random ran=new Random();
        Runnable iterate=new Runnable()
        {
            @Override
            public void run() {
                slower();
                drawframe();
            }

        };



        @Override
        public void onSurfaceCreated(SurfaceHolder holder) {
            // TODO Auto-generated method stub
            super.onSurfaceCreated(holder);


        }

        @Override
        public void onSurfaceChanged(SurfaceHolder holder, int format,
                int width, int height) {
            // TODO Auto-generated method stub
            super.onSurfaceChanged(holder, format, width, height);
            slower();
            drawframe();
        }

        protected void drawframe() {
            // TODO Auto-generated method stub
            SurfaceHolder sh=getSurfaceHolder();


               dra = null;
               try {
                  dra = sh.lockCanvas();
                  if (dra != null) {

                        for(int i=0;i<30&&isft;i++)
                        {
                            x[i]=ran.nextInt(dra.getWidth());
                            y[i]=ran.nextInt(dra.getHeight());
                            temps[i]=30+ran.nextInt(100);

                        }
                        isft=false;
                        dra.drawARGB(255, 0,0, 0);
                        drawsnow(dra,30);

                  }
               } finally {
                  if (dra != null)
                     sh.unlockCanvasAndPost(dra);
               }
        }

        private void drawsnow(Canvas dra,int n) {
            // TODO Auto-generated method stub
            Bitmap snow=BitmapFactory.decodeResource(getResources(), R.drawable.snow80);
            Bitmap te[]=new Bitmap[30];


            for(int i=0;i<n;i++)
            {
                te[i]=Bitmap.createScaledBitmap(snow, temps[i], temps[i], false);
                dra.drawBitmap(te[i], x[i]-(te[i].getWidth()/2), y[i]-(te[i].getHeight()/2), null);
                //Snow to and fro
                if(isr==0&&x[i]!=140)
                    x[i]+=1;
                else
                    isr=1;

                if(isr==1&&x[i]!=120)
                    x[i]-=1;
                else
                    isr=0;

                if(y[i]<dra.getHeight())
                    y[i]+=6;
                else
                {
                    y[i]=0;
                    x[i]=ran.nextInt(dra.getWidth());
                    temps[i]=30+ran.nextInt(100);
                }
            }

            //Toast.makeText(getApplicationContext(), Float.toString(cx), Toast.LENGTH_SHORT).show();               

        }

        protected void slower() {
            // TODO Auto-generated method stub
            hand.removeCallbacks(iterate);
             if (isrun) {
                hand.postDelayed(iterate, 1000/30);
             }

        }

        @Override
        public void onSurfaceDestroyed(SurfaceHolder holder) {
            // TODO Auto-generated method stub
            super.onSurfaceDestroyed(holder);
            isrun=false;
            hand.removeCallbacks(iterate);
            Toast.makeText(getApplicationContext(), "Destroyed", Toast.LENGTH_SHORT).show();
        }

        @Override
        public void onTouchEvent(MotionEvent event) {
            // TODO Auto-generated method stub
            super.onTouchEvent(event);
        }

        @Override
        public void onVisibilityChanged(boolean visible) {
            // TODO Auto-generated method stub
            super.onVisibilityChanged(visible);
            isrun=visible;
            if(isrun)
            {
                slower();
                drawframe();
            }
            else
            {
                hand.removeCallbacks(iterate);
            }
            //Toast.makeText(getApplicationContext(), "Visi", Toast.LENGTH_SHORT).show();
        }

    }

}

Did i coded correctly?

Upvotes: 0

Views: 1416

Answers (2)

vanloi999
vanloi999

Reputation: 485

            Bitmap snow=BitmapFactory.decodeResource(getResources(), R.drawable.snow80);
            Bitmap te[]=new Bitmap[30];

I think you do something wrong here. Your code continuously decodeResource ==> waste a lot of memory and CPU ==> make your program slow, instead of doing this, you should declare a global "snow" variable.

Upvotes: 3

corn3lius
corn3lius

Reputation: 4985

your lag is in the decoding resources.

Bitmap snow=BitmapFactory.decodeResource(getResources(), R.drawable.snow80);
Bitmap te[]=new Bitmap[30];

I would move that to the onSurfaceCreated function and use a member object.

Upvotes: 1

Related Questions