Jump to content
  • Advertisement


  • Content Count

  • Joined

  • Last visited

Community Reputation

355 Neutral

About lephyrius

  • Rank
  1. I have a shader it works good. The problem is that it's on my computer and I might port this to an iOS or Android device. The thing is that on desktop it's things like: in/out instead of attributes/varying (differences between GLSL and GLSL ES) Sooo I feel like I need two different types of shaders. I want to keep it simple and people expect things to run anywhere. Especially if it's a 2D game with some 3D effects. What is the best course of action? 1. Have different shader files for different platforms. 2. Preprocessor defines for things like in/out and attributes/varying. 3. Something different like some kind of universal GLSL that basically compile different versions in the asset "baking" process. Also is possible to define constants from the C++ code or is it easier to just prepend them to the GLSL source?
  2.   I want to have thumbnails of screenshots from moments in the game. First I thought that I could just resize them but then it looks kinda ugly and a bit distorted. So then I just crop it in the middle after that. The problem is that I don't think it looks cool enough. So what I'm thinking is that I could mark the explosions, bullets and magic with "relevance" dots or run the image through a "Feature Detection" like a SURF or SIFT to mark the images with interesting stuff. I'm thinking of doing a collage/toplist of cool(= gives out most score) stuff when the level is complete. The problem is that it's really slow to do brute force and I want it the instant the level is complete. What I want is a function that basically given an width/height and an image gives me back the cropped version of the most intense place in the image.     Nope I want a specific size of the rectangle.
  3. If I have a rectangle of random size and it has random dots in it.( = Rectangle A) I want to take a rectangle that's inside A to cover as many dots as possible.   Is there any possible way of doing this without going bruteforce: iterating through all the dots and use them as a corner of the rectangle only saving the one with most dots in it?
  4. lephyrius

    Render queue ids/design?

      I totally see that it creates a lot of problems storing everything in a 64 bit value. Woah I didn't know that it's 3 times slower to compare a 64 bit value. So I thought that it was as fast 32-bit compare on 64 bit computers.   The thing is that I don't feel I need to go this route cramming everything into 64-bit it was just that it was the first idea that came to me and I tried to stick to that idea. Im quiet open to any idea. Initially I wanted some input so that I could avoid the worst bottlenecks and design decisions.   I really like the idea that Hodgman gave me to just treat the sorting key as a binary blob that is only used for sorting. That's something I would never have thought of if it wasn't for this thread.   Hmmm... Coming up with a "perfect key" is impossible to do I know it now. It's almost like an AI that needed to create these keys. Has someone tried building something like a neural network to create keys? The inputs are shaders, uniforms, textures, vbos, ibos, z-depth, transparent and some other stuff. Output is a key. Training the network would be the draw calls or frame time. I think it would be slow but will it be slower than the all the unnecessary render state changes?     Wouldn't this create a bunch a of memory fragmentation? Or create a lot of dynamic dispatch?   I know writing branch free code is really hard so I guess that's ok.
  5. lephyrius

    Render queue ids/design?

    So you mean like a hashcode? Like murmurhash? That sounds perfect. The problem I see is that then everything with the same diffuse but not the same normal map will be totally different. It's like the material ids. Hmmm... I really don't like loosing that much control. Let's say I have a 16 bit number to play around with: 1. The first texture id = 8 bit 2. The second texture id = 8 bit   Maybe then have something that keeps track of all the texture ids usage(the number of texture ids used and store them in a array). When you call the "generate_material_id"/"generate_texture_id" then it checks all the current textures in the material and selects the two most used. That would ensure that most texture switches is possibly mitigated. Or are you thinking of something else?     Ohh! This is another solution I guess it's never black or white.     Why store the draw call data in the queue when you have state groups? Why not store the draw call data in the state groups? Why have a list of state groups isn't one enough?
  6. lephyrius

    Render queue ids/design?

    I've been thinking I got some sleep.   I think I need 2 types of ids. 1 for opaque objects and 1 for transparent. These lists just to clarify 1 = most significant bit. So for opaque objects: 1. Type(like a tiny header in this case = 0(opaque 3D)) = 2 bit 2. layer = 4 bit 3. shader = 7 bit 4. diffuse = 7 bit 5. normals = 7 bit 6. specular = 7 bit 7. IBO = 7 bit 8. VBO = 7 bit 9. z-index = 8 bit   Ok, this has now 2+4+7*6+8 = 56 bit Hmmm.. I think I could squeeze in another texture and that's a glow map that would mean: 2+4+7*7+8 = 63 bit Pretty close to 64.   So for the transparent objects: 1. Type(like a tiny header in this case = 1(transparent 3D)) = 2 bit 2. layer = 4 bit 3. z-index = 12 bit 4. shader = 7 bit 5. diffuse = 7 bit 6. normals = 7 bit 7. specular = 7 bit 8. IBO = 7 bit 9. VBO = 7 bit   So for this it's 2+4+12+7*6 = 60 bit. Also I could have 2 pools(1 for opaque and 1 for transparent) of shaders, diffuse textures, normals textures and specular textures. So I at least could get 256 IBO/VBO and texture combinations.   I think I need to think about this design a bit more so that I don't regret it in the future.
  7. lephyrius

    Render queue ids/design?

    Yeah! At first I was thinking that material is a combination of all the textures like diffuse, normals and specular. So let's say I have this structure:(I assume u mean that I need to have a single ID of 64-bit) Then the structure would be more like this: 1. type(3D opaque, 3D transparent,fullscreen effects like SMAA/HDR, 2D/UI) = 2 bit 2. z-index = 8 bit 3. shader = 7 bit 4. diffuse = 6 bit 5. normals = 6 bit 6. specular = 6 bit 7. IBO = 6 bit 8. VBO = 6 bit   This is really conservative! I get this to 2+8+7+5*6 = 47 bit   Is this a correct order? Should I maybe move z-index down a bit? Hmmm.. Layering. Couldn't this be solved with z-index? Now I got 17 bits to play around with. I should probably increase some bits. What do u think would be best to increase? Or Have I missed something that I need to have? Maybe I shouldn't exactly specify diffuse,normals and specular but then I would need some kind of "material_id" like before. This feels more sustainable at least and I can easily sort them. Maybe just have 3 texture pools and u could store them in different slots for the shader?   For shaders permutations this is most likely to be loaded when the game starts so then it's ok. Let's say we have 100 shader permutations and that would easily fit into 8 bit. My concern is with with textures(needs most likely 3 textures per model) and IBO:s/VBO:s(a lot more per model) . They will change when the game progresses and then I need to reuse the id:s. Because I must be able to squeeze everything into  64-bit in order to sort the render queue efficiently.   I really like the idea I also like the idea of using atomics. The problem is that it feels it could create too many ID:s if you just add up.
  8. I've deciding that I want a render queue!   I have decided 2 things: 1. Not submitting a new queue on each frame.(seems like it creates a lot of memory fragmentation). I will have to have some reference to the scenegraph then. Is this a bad thing? 2. Have separate queues to "opaque 3D", "transparent 3D" and "2D". Because they have a bit different sorting order. Im using OpenGL in my example but I feel that this could apply to any other API as well. So the ID is 64-bit you need to sort after. The parameters are in the priority order for the opaque 3D queue: 1. Shader id 2. Material id(probably an UBO or a combination of texture id) 3. VBO id 4. IBO id Now how do I combine the ids into one 64 bit integer? Something like this? uint64_t queue_id = ((shader_id % USHRT_MAX) << 48) | ((material_id % USHRT_MAX) << 32) | ((vbo_id % USHRT_MAX) << 16) | ibo_id % USHRT_MAX Is there some other way of compacting the 32-bits numbers into 16-bit? Or should I maybe create more of a wrapper around the GL ids? So the shader permutation class: class Shader { public: uint16_t id; GLuint shader_id; }; And have a manager(factory) that takes care of assigning ids that is compact.   class ShaderManager {   public:     Shader& get(const char* filename);  // The shader configuration file.     std::map<std::string, uint16_t> loaded_shaders;   std::vector<uint16_t> free_ids;   std::vector<Shader> shaders; }; Hmmm.. This solution is probably a bit more compact and robust. Hmmm... I don't think I ever will have 65535 different shaders, materials, vbos or ibos at least not at the same time. Then I could use uint8 and add z order also. Maybe I should have different kind of queues so that:   class ShaderCommand { public:   GLuint shader_id;     std::vector<MaterialQueue> texture_queue; }; class ShaderQueue { // The root of the tree. public: ShaderCommand& add(); void remove(ShaderCommand& command);   void render(); std::vector<ShaderCommand> commands; }; // This is just an example of the render function. void ShaderQueue::render() {   // Sort the commands based on shader_id.(skipped)   GLuint current_shader_id = 0;   for (ShaderCommand& command : commands  ) {     glUseProgram(command.shader_id);     // Apply the shader!     for (TextureQueue& queue : command.texture_queue  ) {       queue.render();     }   } } class MaterialCommand { public:   size_t material_id;   GLuint textures[4];  // Probably will be ubo:s but I use textures for now for simplicity.       std::vector<MaterialQueue> texture_queue; }; class MaterialQueue { public: MaterialCommand& add(); void remove(MaterialCommand& command);   void render(); std::vector<MaterialCommand> commands; }; The problem is that I feel that with this approach is that it probably creates more memory fragmentation(+ maybe some cache) and it's harder to change materials on things(I wonder how often that needs to be done). But this will be more of a bucket approach. Also another problem is that this needs a lot copying when I sort unless I use pointers for storing the command. Another problem I see is that like for instance a mesh node in the scene graph will need to have: ShaderCommand, MaterialCommand, VBOCommand and IBOCommand references in their nodes so they could change the Material, Shaders and VBO:s/IBO:s. At least it will solve the generating of the ids. Am I overthinking this now? Is there something I have totally missed? Or I need to have/think about?
  9. I really love the NGINX source code. It's documented very well but it's a bit too large to start with and not game related.  So that's my suggestion.
  10. I've been thinking about this. You are right it has really opened my eye to something also it's really nice and cache friendly to store models in that way. The problem is that isn't scripting languages one the reasons of using a scripting language is to use the garbage collector.   Hmmmm... Clean up after a level is loaded shouldn't be a problem when all the allocations are controlled by the engine itself. It certainly is faster to deallocate chunks of memory also more cache friendly.(almost feels like my C++ code becomes more C like) The thing is that I was thinking that scripting should be more a part of the engine rather than just a slave to the engine.
  11. I've been thinking of using Squirrel as a scripting language. My idea was to use the garbage collector as a memory manager:(squirrel as an example script) class Model { constructor(filename) { model_id = load_model(filename); } destructor() { unload_model(model_id); } model_id = null; } Something like this.(load_model and unload_model is native functions that are really easy to bind no need to worry about binding complicated classes) It's obvious that this isn't going to work. Because Squirrel is missing the destructor. Am I thinking of something wrong? Is there a reason why Squirrel doesn't have a destructor? Am I just using scripting in a wrong way? Are there any alternatives to Squirrel that is similar to it but with a destructor? Should I rethink the problem with binding to the native functions?
  12. I'm using GLee for GL 2.0 support. Thats not a problem. But now I investigate a bug so I need NVidia GLExpert for debugging. What include order do I need for the "nvapi.h" and "Glee.h"? I only get these errors: 1>graphicssubsystem.cpp(239): error C3861: 'glDrawBuffers': identifier not found 1>graphicssubsystem.cpp(257): error C3861: 'glGenBuffers': identifier not found 1>graphicssubsystem.cpp(258): error C3861: 'glBindBuffer': identifier not found 1>graphicssubsystem.cpp(265): error C3861: 'glBufferData': identifier not found 1>graphicssubsystem.cpp(277): error C3861: 'glDrawBuffers': identifier not found 1>graphicssubsystem.cpp(406): error C3861: 'glBlendEquation': identifier not found 1>graphicssubsystem.cpp(468): error C3861: 'glBindBuffer': identifier not found 1>graphicssubsystem.cpp(494): error C3861: 'glBindBuffer': identifier not found In any order I include them.
  13. lephyrius

    Absolutely FREE Sound Library

    How about cAudio ( http://caudio.deathtouchstudios.com/ ) it's zlib ?
  14. lephyrius

    Using 100 Degrees Instead Of 360

    I think it originates from: http://en.wikipedia.org/wiki/Sexagesimal The reason why an hour is 60 min. " Similarly, the practical unit of angular measure is the degree, of which there are 360 in a circle. There are 60 minutes of arc in a degree, and 60 seconds of arc in a minute. " - Wikipedia
  15. lephyrius

    Quick Question. Which IDE do you recommend?

    Xcode on Mac. But when it is possible I like to use Visual Studio + Visual Assist for C++.
  • Advertisement

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!