Draw on canvas with a delay - "make onDraw () slower"

I use functions for canvas like drawCircle and drawPoint in android. It works great.

But now the problem is to draw these different elements with a delay, so it looks like an animation.

What mechanism should I use? Tried with async, but I don't like this way of doing this.

Should I use some kind of timer that just draws at intervals or are there other smart ways to do this?

+6
source share
3 answers

I use this strategy, first declare Handler and Runnable this way:

private final Observable mObservable = new Observable(); private final static int TIME_STEP_MS = 5; private final Handler mHandler = new Handler(); private final Runnable mTimeManager = new Runnable() { public void run() { mObservable.notifyObservers(TIME_STEP_MS); mHandler.postDelayed(mTimeManager, TIME_STEP_MS); } }; 

Then, when I want to start my time manager, I just call mTimeManager.run () and it will start to periodically notify my Observer (previously added).

If for some reason you need to stop the timer or something that you just do:

  mHandler.removeCallbacks(mTimeManager); 

[EDIT - more complete code]

Well, than making it clearer, I first created a special Observable object, such as [this optional]:

  private final Observable mObservable = new Observable() { public void notifyObservers() { setChanged(); super.notifyObservers(); }; @Override public void notifyObservers(Object data) { setChanged(); super.notifyObservers(data); }; }; 

the reason is that I cannot call setChanged () outside the Observable class - it is protected, if it has not changed, it does not notify the browser.

Other declarations are saved in the same way as shown above, now I need to run this TimeManager somewhere, my application is LiveWallpaper, and I do all the materials for rendering into a class that extends Thread , but you do not need that, I made a method for called resumeDrawing() , this one is called right after super.start(); in my @Override from public synchronized void start() from the Thread class, the method looks like this:

  public void resumeDrawing() { if (!mTimeManagerRunning) // just a boolean field in my class { System.err.println("Resuming renderer."); // just for debug mTimeManager.run(); mTimeManagerRunning = true; } else { System.err.println("Renderer already running."); // just for debug } } 

and it is dual:

  public void pauseDrawing() { if (mTimeManagerRunning) { System.err.println("Pausing renderer."); mHandler.removeCallbacks(mTimeManager); mTimeManagerRunning = false; } else { System.err.println("Renderer already paused."); } } 

Ok, now we can start and stop the time manager, but who is listening? No one! therefore, let add'em: In the constructor of my Renderer, I add an Observer to my mObservable object, one of them is Renderer itself, so my rendering extends Thread and implements Observer :

  @Override // from Observer interface public void update(Observable arg0, Object arg1) { mElapsedMsRedraw += (Integer) arg1; if (mElapsedMsRedraw >= mDrawingMsPerFrame) { mElapsedMsRedraw = 0; drawEm(); // refresh the canvas and stuff } } 

to add observers that you just do mObservable.addObserver(THE_OBJECT - Implements Observer)

you can see that I do not reprocess my material every time I am notified, because I use this TimeManager for others, and not just update the Canvas , like updating the position of objects that I want to draw just inside.

So, you need to slow down the drawing in order to change the way internal objects change during the passage, I mean your circles and points, etc., or you can use your time step, I recommend the first.

Was it clearer? Hope this helps.

+3
source

I would use a timer or create an animation. You can create animations that will do all kinds of things, including changing transparency over time.

Here 's the Android documentation for animation resources

+1
source

I believe that there can be difficult ways to do this, but for my needs I used a simple method that has many advantages: First I create coordinate records (and any other data) for each point in the drawing - instead of drawing the points in place - and then reproduces them using a timer (Android handler, preferably). It also offers many options as long as the actual drawing: pause, speed / slower, back, ... I don’t know if this method can be used for complex drawings, but it is great for drawing shapes, curves, surfaces, etc.

0
source

Source: https://habr.com/ru/post/927386/


All Articles