Passing instructions from the user interface stream to the rendering stream (GLSurfaceView)

Customization: RelativeLayout with GLSurfaceView and a button as shown.

enter image description here

Problem: Suppose I have other models of triangles (the one in the picture is the original model) ... I want to change the models cyclically at the click of a button. Since the button is in the user interface thread, and glSurfaceView works in a separate thread, I don’t know exactly how to pass information / instructions to it. I know this thing is called Handler in Android, which may be useful in this case ... But I need help here.

Edit: If Handler is the right way, I need to know how to add Looper to this handler ... The documentation says add looper.prepare() at the start of the run () method. But glSurfaceView creates the stream implicitly, as a result of which the run () method is not directly accessible.

+2
source share
2 answers

I don’t think that you need to use handlers to solve this problem, but you may need to set up a way to organize your classes.

Here is an example of an organizational structure that can solve your problem:

Action class

 public class MainActivity extends Activity { private int modelNumber = 0; private ArrayList<Model> models = new ArrayList<Model>(); private YourRendererClass renderer; @Override public void onCreate(Bundle savedInstanceState) { ... // Setup GLSurfaceView GLSurfaceView surface = new GLSurfaceView(this); setContentView(surface); renderer = new YourRendererClass(); surface.setRenderer(renderer); // Set up models models.add(new Model(x, y, size etc..)); models.add(new Model(x, y, size etc..)); models.add(new Model(x, y, size etc..)); etc. // Display first model renderer.setCurrentModel(models.get(modelNumber)); ... } // Called by the button press: // Use android:onClick="onClick" // in your layout xml file within button public void onClick(View view){ // Make it loop round modelNumber++; if(modelNumber>=models.size()){ modelNumber=0; } // Display current model renderer.setCurrentModel(models.get(modelNumber)); } } 

Renderer class

 public class YourRendererClass implements Renderer { private Model currentModel; @Override public void onDrawFrame(GL10 gl) { // ** Your existing set-up code **// // Draw model if (currentModel!=null){ currentModel.draw(gl); } } public void setCurrentModel(Model model){ currentModel = model; } } 

Model class

 public class Model { // Holds model information private int size; private int x; private int y; // etc... public model(int x, int y, int size etc...){ this.x=x; this.y=y; this.size=size; // etc.... } public void draw(GL10 gl) { // ** Draw model based on model information fields above ** } } 

The above code is untested, since I do not have access to your drawing code, but the structure should work if it is executed correctly. I tried to make it clear where you have to insert your own code for it to work. In particular, I was not sure what defines each of your different models, so you need to include enough local variables in the Model class to define them.

Hope my answer helps, let me know if you have any questions.

Tim

+4
source

You should look at queueEvent! This is a very convenient way to transfer information from the user interface stream for rendering Thread:

 queueEvent(new Runnable(){ @Override public void run() { mRenderer.method(); }}); 
0
source

All Articles