Friday, 15 April 2011

java - How to use Android's Looper in a drawing thread -



java - How to use Android's Looper in a drawing thread -

i'm trying create simple aeroplane game build skills , have fun. i've nail roadblock threads, loopers, , message queues when trying pass message ontouch event of textview thread drawing airplanes. i'm going seek include essential bits of code below , utilize "..." indicate omitted lines.

i'm drawing in separate, old-fashioned android thread. here's constructor of thread:

public class benthread extends thread { ... public benthread(surfaceholder surfaceholder, context context, bensurfaceview surfaceview) { this.surfaceholder = surfaceholder; this.context = context; this.surfaceview = surfaceview; this.isrunning = false; bitmap planeimage = bitmapfactory.decoderesource( context.getresources(), r.drawable.fighters); aeroplane = new airplane(50, 50, 2, 0, planeimage); }

before show run method, note there's surfaceview creates , starts thread when surfacechanged() called. in oncreate() of main activity, create final instance of custom surfaceview:

final bensurfaceview surfaceview = (bensurfaceview) findviewbyid(r.id.surfaceview);

in ui layout, there textview sitting @ bottom center ontouchlistener hooked up. in ontouch(), motionevent.action_down, next line called:

surfaceview.thread.handler.sendemptymessage(1);

back thread class, handler empty message created in run method, along looper creation:

public void run() { super.run(); looper.prepare(); // creates message queue thread messagequeue queue = looper.myqueue(); queue.addidlehandler(new idlehandler() { @override public boolean queueidle() { looper.mylooper().quit(); homecoming false; } }); handler = new handler() { @override public void handlemessage(message msg) { log.i("handling", "something"); } }; looper.loop(); while (isrunning) { currenttime = system.currenttimemillis(); // spin in while loop while while ((currenttime - previoustime) < refresh_rate) { currenttime = system.currenttimemillis(); } airplane.move(); canvas = surfaceholder.lockcanvas(); if (canvas != null) { surfaceview.draw(canvas); airplane.draw(canvas); surfaceholder.unlockcanvasandpost(canvas); } } }

now if run is, nice little animation of airplanes moving across screen. but, when click button @ bottom, see log sent message dead thread. well, guess killed in idlehandler. allow me comment out quit method:

// looper.mylooper().quit();

now app looks considerably less exciting:

but, when click button @ bottom , @ log, there proof message has been handled! big question is, how can run message loop , still see animation?

after phone call looper.loop(), should not homecoming until thread ready stop. having game loop after looper.loop() phone call doesn't create sense. @ point thread "dead" in sense looper no longer listening messages.

if want thread run in while (isrunning), that. if want message-driven, that. don't seek both in same thread. (and please don't spin on cpu -- eats battery on mobile device.)

you can find notes game loops, , surfaceview , threading, in appendices , b of this article. there various examples of animated rendering using handler in grafika. example, "record gl app" activity uses choreographer send message render thread whenever it's time draw.

java android multithreading surfaceview

No comments:

Post a Comment