Hello,

I've been wrestling for a few days with concurrency related to setting
up different threads for a game app.
I have made many versions, but they have all failed. At this point, I
just want to get a basic concurrent setup going. The worst part is
that it is the emulator that crashes, so DDMS reports nothing;
therefore I'm pretty clueless as to where the issue is.

The following code shows an activity (class Main), that calls classes
SceneManager, which creates a thread to be used to game logic stuff. A
3rd class, StatusChannel, is (will be) used to communicate status
information between the different threads (Eventually, there will also
be a OpenGL rendering thread).

The emulator crashes at different times. It may run for 20 seconds or
for 5 minutes.

The setContentView(R.layout.main) in the Activity class just the set
basic layout that Eclipse creates.

I've commented out the usage of Node (Created in the activity and
Accessed in SceneManager)

Here are the 3 classes.

Sorry for the code length.

############################# BEGIN Activity Class
###################################

public class Main extends Activity {
        private SceneManager mSceneManager;
        private volatile Node mSceneGraph = new Node();
        private volatile Status mStatusChannel = new Status();

    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        Log.d("-- Main", "onCreate()");
        super.onCreate(savedInstanceState);

        setContentView(R.layout.main);

        // Holds the scene assets, such as the stage,
        // the agents, camera, etc.
        mSceneManager = new SceneManager(mSceneGraph,
mStatusChannel);
        mSceneManager.onCreate();
    }

    @Override
    protected void onResume() {
        Log.d("-- Main", "onResume()");
        super.onResume();
        mSceneManager.onResume();
    }

    @Override
    protected void onPause() {
        Log.d("-- Main", "onPause()");
        super.onPause();
        mSceneManager.onPause();
    }

    @Override
    protected void onDestroy() {
        Log.d("-- Main", "onDestroy()");
        super.onDestroy();
        mSceneManager.onDestroy();
    }
}
################################## END Activity Class
######################################



################################# START SceneManager Class
##############################
public class SceneManager implements Runnable{
        private Thread mThread;
        private volatile Status mStatusChannel;
        private volatile Node mSceneGraph;

        private volatile long mMillis = 0;
        private volatile PrepareVisitor mPrepareVisitor;
        private volatile int mStatus = Status.UNKNOWN_STATUS;

        SceneManager(Node sceneGraph, Status statusChannel) {
                mPrepareVisitor = new PrepareVisitor();
                mStatusChannel = statusChannel;
                mSceneGraph = sceneGraph;
        mMillis = SystemClock.uptimeMillis();
                mThread  = new Thread(this);
                mThread.setName("LogicThread");
                mStatusChannel.setSceneManagerStatus(Status.READY_STATUS);
        }

        public void onCreate() {
                Log.d("-- SceneManager", "onCreate()...");
                // This will start the thread in a paused state.
                mThread.start();
        }

        public void onResume() {
                Log.d("-- SceneManager", "onResume()...");

                // Unpause the status manager, if it is currently paused.
                if (mStatusChannel.getSceneManagerStatus() == 
Status.PAUSED_STATUS)
{
                        
mStatusChannel.setSceneManagerStatus(Status.READY_STATUS);
                }
        }

        public void onPause() {
                Log.d("-- SceneManager", "onPause()...");
                if (mStatusChannel.getSceneManagerStatus() != 
Status.UNKNOWN_STATUS)
{
                        
mStatusChannel.setSceneManagerStatus(Status.PAUSED_STATUS);
                }
        }

        public void onDestroy() {
                mStatusChannel.setSceneManagerStatus(Status.QUIT_STATUS);
                try {
                        mThread.join();
                }
                catch (InterruptedException e) {
                        Log.d("-- SceneManager", "InterruptedException");
                }
        }

        /**
         *  This method should not be called by clients of this class.
         */
        @Override
        public void run() {
                Log.d("-- SceneManager", "Called...");

                // Main logic loop.
                outer: while (true) {

                        // How much time has elapsed since last call.
                        long timeDelta = SystemClock.uptimeMillis() - mMillis;

                        switch (mStatus) {
                        case Status.READY_STATUS:
                                //mPrepareVisitor.go(mSceneGraph, timeDelta);
                                break;
                        case Status.PAUSED_STATUS:
                                break;
                        case Status.QUIT_STATUS:
                                break outer;
                        case Status.UNKNOWN_STATUS:
                                int renderStatus = 
mStatusChannel.getRendererStatus();
                                if (renderStatus == Status.READY_STATUS) {
                                        
mStatusChannel.setSceneManagerStatus(Status.READY_STATUS);
                                }
                                break;
                        }

                        mStatus = mStatusChannel.getSceneManagerStatus();

                // Update the time.
                        mMillis = SystemClock.uptimeMillis();
                }
        }
}

################################# END SceneManager Class
##############################

############################## START Status Class
###################################
public class Status {

        /* Generic Statuses */
        public final static int UNKNOWN_STATUS = 0;
        public final static int READY_STATUS = 1;
        public final static int PAUSED_STATUS = 2;
        public final static int QUIT_STATUS = 3;

        /* Current statuses values */
        private int mSceneManagerStatus = UNKNOWN_STATUS ;
        private int mRendererStatus     = UNKNOWN_STATUS ;


        public synchronized int getSceneManagerStatus() {
                return mSceneManagerStatus;
        }

        public synchronized int getRendererStatus() {
                return mRendererStatus;
        }

        public synchronized void setSceneManagerStatus(int status) {
                mSceneManagerStatus = status;
        }

        public synchronized void setRendererStatus(int status) {
                mRendererStatus = status;
        }
}
############################## END Status Class
###################################

-- 
You received this message because you are subscribed to the Google
Groups "Android Developers" group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en

Reply via email to