简体   繁体   中英

OpenGL and OOP programming

I want to structure my OpenGL program in classes, at first, I think I'll have Mesh, Shader, Vertex, Face (indicates) classes. Shader is a class for handling shader operations like create, compile, link, bind, unbind. Mesh contains a shader, list of Vertex and list of Face, it will create buffers, draw object to screen using attached shader, Hence all objects (like Box, Sphere, Monkey, TeaPot, ..) will inherited from Mesh class (or even use Mesh class directly). The problem is in the draw method of Mesh: each shader have different attribute and uniform variables, ... I can't find a way to draw object with dynamic shader. Is my OOP model not good? or are there any ways to do this?

I just want my program will like below:

Vertex vertices[] = {....};
Face faces[] = {...}; // Indicates
Shader color_shader = ColorShader::getOne();
Mesh box;
box.pushVertices(vertices);
box.pushFaces(faces);
box.shader = color_shader;
box.buildObject();

In render method like this:

box.draw(MVP);

Can anyone one suggest me a way to draw object with dynamic shader or other ways to do that thing?

Assembled from comments:

Conventionally mesh is just a geometry. Material is a shader (more generally - effect) and its parameters. And something like 'sceneobject' - virtual node entity that contains reference to mesh (or other object type) and materials. I highly doubt mesh should draw itself - this approach lacks flexibility, and isn't making much sense.

I think you should use something like 'renderer' or 'render_queue' or whatever it called, that takes objects to draw (bundles of meshes and materials) and draws them somewhen. It will even allow you to sort rendering queue to minimise state switches (switching shaders/shader parameters/textures have performance cost).

Attributes comes from mesh (maybe it would be easier to use some standard names like 'position', 'normal', 'texcoord0', ...). As for uniforms - there's more than one way. Eg you have a material file with contents like

use_effect phong_single_texture;
texture t0 = "path_to_texture";
vec3 diffuse_colour = { 1, 0, 0 };

Then you load this file into material structure, link it with effect (what you called 'shader'), texture, etc.. Then renderer pulls this all together and setups attributes and uniforms by names.

Side note :

OOP everywhere isn't very good if you aim for high performance, but it is good for educational purpose. Whenever your experience is good enough - google something like 'data oriented design', but it isn't easy topic.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM