Ostatnio zmodyfikowano wczoraj o godz. 8:05
tBane Temat założony przez niniejszego użytkownika |
[OpenGL GLFW GLAD] Snowstorm - Czyli system cząstek i płatki śniegu » 2025-01-27 18:24:29 Cześć. Uczę się OpenGL GLFW GLAD. Zastanawiam się jak pracować z systemem cząstek takim np. jak SnowStorm lub deszcz. Czy prawidłowym podejściem będzie stworzenie menadżera cząstek i dla każdej cząstki generować VAO dla quad oraz renderować na nim teksturę i w ten sposób to wszystko generować? |
|
DejaVu |
» 2025-01-27 20:51:20 Prawidłowym podejściem jest zrobienie 'czegokolwiek' co działa w pierwszej iteracji, aby nauczyć się/zrozumieć jak takie rzeczy się implementuje. W kolejnej iteracji możesz zacząć się zastanawiać 'co zrobić lepiej'. Jeżeli chcesz 'od razu' zrobić 'dobrze', to poszukaj artykułów na ten temat lub zapytaj ChatGPT i pomęcz go trochę pytaniami, w tym również kwestionuj proponowane rozwiązania. |
|
tBane Temat założony przez niniejszego użytkownika |
» 2025-01-28 16:27:54 Dobra. Mam pomysł jak dobrze wygenerować SnowStorm. Dziś spróbuję napisać i jak się uda to wrzucę kod. |
|
tBane Temat założony przez niniejszego użytkownika |
» 2025-01-28 20:36:51 Częściowo napisane. Jeszcze trzeba napisać renderowanie tekstury dla każdego płatka śniegu zamiast rysowania punktu oraz dać różne prędkości opadania. Jutro wrzucę poprawiony kod a dziś no tylko tyle. https://youtu.be/D9VtoZeobHg#ifndef SnowStorm_hpp #define SnowStorm_hpp
class FallingSnowflake { public: float speed = 0.1f; };
class SnowStorm { public: glm::vec3 rect_position; glm::vec3 rect_size; short falling_snowflakes_count; std::random_device rd; std::mt19937 generator; std::vector < FallingSnowflake * > falling_snowflakes; std::vector < float > falling_snowflakes_positions; unsigned int _VAO; unsigned int _VBO; int _width, _height, _nrChannels; unsigned int _texture_snowflake; Program * _program; SnowStorm() { rect_position = glm::vec3( 0, 20, 0 ); rect_size = glm::vec3( 2, 5, 2 ); falling_snowflakes_count = 1000; generator = std::mt19937( rd() ); for( short i = 0; i < falling_snowflakes_count; i++ ) { falling_snowflakes.push_back( new FallingSnowflake() ); glm::vec3 pos = generateFallingSnowFlakePosition(); falling_snowflakes_positions.push_back( pos.x ); falling_snowflakes_positions.push_back( pos.y ); falling_snowflakes_positions.push_back( pos.z ); } glGenVertexArrays( 1, & _VAO ); glBindVertexArray( _VAO ); glGenBuffers( 1, & _VBO ); glBindBuffer( GL_ARRAY_BUFFER, _VBO ); glBufferData( GL_ARRAY_BUFFER, falling_snowflakes_positions.size() * sizeof( float ), falling_snowflakes_positions.data(), GL_STATIC_DRAW ); glVertexAttribPointer( 0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof( float ),( void * ) 0 ); glEnableVertexAttribArray( 0 ); glBindVertexArray( 0 ); loadTextureOfSnowflake( "snowflake.png" ); _program = new Program( snow_vertex_shader_source, snow_fragment_shader_source ); } ~SnowStorm() { glDeleteVertexArrays( 1, & _VAO ); glDeleteBuffers( 1, & _VBO ); glDeleteTextures( 1, & _texture_snowflake ); for( auto & snow: falling_snowflakes ) { delete snow; } delete _program; } void loadTextureOfSnowflake( std::string texture_pathfile ) { glGenTextures( 1, & _texture_snowflake ); glBindTexture( GL_TEXTURE_2D, _texture_snowflake ); stbi_set_flip_vertically_on_load( true ); unsigned char * data = stbi_load( texture_pathfile.c_str(), & _width, & _height, & _nrChannels, 0 ); if( data ) { GLenum format = _nrChannels == 4 ? GL_RGBA: GL_RGB; glTexImage2D( GL_TEXTURE_2D, 0, format, _width, _height, 0, format, GL_UNSIGNED_BYTE, data ); glGenerateMipmap( GL_TEXTURE_2D ); } else std::cout << "Failed to load texture\n"; stbi_image_free( data ); } glm::vec3 generateFallingSnowFlakePosition() { glm::vec3 pos; std::uniform_real_distribution < > dis; dis = std::uniform_real_distribution < >( rect_position.x - rect_size.x / 2.0f, rect_position.x + rect_size.x / 2.0f ); pos.x = rect_position.x + dis( generator ); dis = std::uniform_real_distribution < >( 0, rect_position.y + rect_size.y / 2.0f ); pos.y = rect_position.y + dis( generator ); dis = std::uniform_real_distribution < >( rect_position.z - rect_size.z / 2.0f, rect_position.z + rect_size.z / 2.0f ); pos.z = rect_position.z + dis( generator ); return pos; } void update() { for( short i = 0; i < falling_snowflakes_count; i++ ) { falling_snowflakes_positions[ i * 3 + 1 ] -= falling_snowflakes[ i ]->speed; if( falling_snowflakes_positions[ i * 3 + 1 ] < 0 ) { glm::vec3 pos = generateFallingSnowFlakePosition(); falling_snowflakes_positions[ i * 3 ] = pos.x; falling_snowflakes_positions[ i * 3 + 1 ] = pos.y; falling_snowflakes_positions[ i * 3 + 2 ] = pos.z; } } glBindBuffer( GL_ARRAY_BUFFER, _VBO ); glBufferSubData( GL_ARRAY_BUFFER, 0, falling_snowflakes_positions.size() * sizeof( float ), falling_snowflakes_positions.data() ); glBindBuffer( GL_ARRAY_BUFFER, 0 ); } void draw( Camera * cam ) { glUseProgram( _program->shader_program ); glActiveTexture( GL_TEXTURE0 ); glBindTexture( GL_TEXTURE_2D, _texture_snowflake ); glUniform1i( glGetUniformLocation( _program->shader_program, "texture1" ), 0 ); glUniform3f( glGetUniformLocation( _program->shader_program, "fogColor" ), 0.25f, 0.25f, 0.25f ); glUniform1f( glGetUniformLocation( _program->shader_program, "fogStart" ), 1.0f ); glUniform1f( glGetUniformLocation( _program->shader_program, "fogEnd" ), 15.0f ); glm::mat4 view = cam->GetViewMatrix(); glm::mat4 projection = glm::perspective( glm::radians( 45.0f ), 800.0f / 600.0f, 0.1f, 100.0f ); glm::mat4 model = glm::mat4( 1.0f ); model = glm::translate( model, rect_position ); glUniformMatrix4fv( glGetUniformLocation( _program->shader_program, "projection" ), 1, GL_FALSE, & projection[ 0 ][ 0 ] ); glUniformMatrix4fv( glGetUniformLocation( _program->shader_program, "view" ), 1, GL_FALSE, & view[ 0 ][ 0 ] ); glUniformMatrix4fv( glGetUniformLocation( _program->shader_program, "model" ), 1, GL_FALSE, & model[ 0 ][ 0 ] ); glPointSize( 5.0f ); glBindVertexArray( _VAO ); glDrawArrays( GL_POINTS, 0, falling_snowflakes_count ); glBindVertexArray( 0 ); } };
#endif
|
|
tBane Temat założony przez niniejszego użytkownika |
» 2025-02-08 08:20:07 Witam ponownie. Próbuję wygenerować płatki śniegu z tekstury. Stworzyłem vector z danymi wierzchołków i współrzędnych tekstur, zrobiłem glGenBuffer dla nich (vertices) i teraz muszę to jakoś przesłać do layoutów w shaderach. Nie wiem jak to zrobić. Pomoże ktoś ? SnowStorm( Program * program ) { rect_position = glm::vec3( 0, 20, 0 ); rect_size = glm::vec3( 15, 5, 15 ); falling_snowflakes_count = 1000; generator = std::mt19937( rd() ); for( short i = 0; i < falling_snowflakes_count; i++ ) { falling_snowflakes.push_back( new FallingSnowflake() ); glm::vec3 pos = generateFallingSnowFlakePosition(); falling_snowflakes_positions.push_back( pos.x ); falling_snowflakes_positions.push_back( pos.y ); falling_snowflakes_positions.push_back( pos.z ); } std::vector < float > snowflake_vertices = { - 0.1f, - 0.1f, 0.0f, 0.0f, 0.0f, 0.1f, - 0.1f, 0.0f, 1.0f, 0.0f, - 0.1f, 0.1f, 0.0f, 0.0f, 1.0f, 0.1f, 0.1f, 0.0f, 1.0f, 1.0f }; glGenVertexArrays( 1, & _VAO ); glBindVertexArray( _VAO ); glGenBuffers( 1, & _positions ); glGenBuffers( 1, & _vertices ); glBindBuffer( GL_ARRAY_BUFFER, _positions ); glBufferData( GL_ARRAY_BUFFER, falling_snowflakes_positions.size() * sizeof( float ), falling_snowflakes_positions.data(), GL_STATIC_DRAW ); glVertexAttribPointer( 0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof( float ),( void * ) 0 ); glEnableVertexAttribArray( 0 ); glBindBuffer( GL_ARRAY_BUFFER, _vertices ); glBufferData( GL_ARRAY_BUFFER, snowflake_vertices.size() * sizeof( float ), snowflake_vertices.data(), GL_STATIC_DRAW ); glVertexAttribPointer( 1, 3, GL_FLOAT, GL_FALSE, 3 * sizeof( float ),( void * ) 0 ); glEnableVertexAttribArray( 0 ); glVertexAttribPointer( 2, 3, GL_FLOAT, GL_FALSE, 3 * sizeof( float ),( void * )( 3 * sizeof( float ) ) ); glEnableVertexAttribArray( 0 ); glBindVertexArray( 0 ); loadTextureOfSnowflake( "textures/snowflake.png" ); _program = program; }
|
|
tBane Temat założony przez niniejszego użytkownika |
» 2025-02-09 12:52:21 Chyba udało mi się trochę uporządkować kod. Ale nadal nie działa. Nie renderuje ani opadających płatków śniegu, ani tym bardziej opadających prostokątów. Video z programu ... : https://www.youtube.com/watch?v=KvaZpBbEdk4Screenshoty: class FallingSnowflake { public: float speed = 0.1f; };
class SnowStorm { public: glm::vec3 rect_position; glm::vec3 rect_size; short falling_snowflakes_count; std::random_device rd; std::mt19937 generator; std::vector < FallingSnowflake * > falling_snowflakes; std::vector < float > falling_snowflakes_positions; unsigned int _VAO; unsigned int _positions; unsigned int _vertices; int _width, _height, _nrChannels; unsigned int _texture_snowflake; Program * _program; SnowStorm( Program * program ) { rect_position = glm::vec3( 0, 20, 0 ); rect_size = glm::vec3( 15, 5, 15 ); falling_snowflakes_count = 1000; generator = std::mt19937( rd() ); for( short i = 0; i < falling_snowflakes_count; i++ ) { falling_snowflakes.push_back( new FallingSnowflake() ); glm::vec3 pos = generateFallingSnowFlakePosition(); falling_snowflakes_positions.push_back( pos.x ); falling_snowflakes_positions.push_back( pos.y ); falling_snowflakes_positions.push_back( pos.z ); } std::vector < float > snowflake_vertices = { - 0.1f, - 0.1f, 0.0f, 0.0f, 0.0f, 0.1f, - 0.1f, 0.0f, 1.0f, 0.0f, - 0.1f, 0.1f, 0.0f, 0.0f, 1.0f, 0.1f, 0.1f, 0.0f, 1.0f, 1.0f }; glGenVertexArrays( 1, & _VAO ); glBindVertexArray( _VAO ); glGenBuffers( 1, & _positions ); glBindBuffer( GL_ARRAY_BUFFER, _positions ); glBufferData( GL_ARRAY_BUFFER, falling_snowflakes_positions.size() * sizeof( float ), falling_snowflakes_positions.data(), GL_STATIC_DRAW ); glEnableVertexAttribArray( 0 ); glVertexAttribPointer( 0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof( float ),( void * ) 0 ); glGenBuffers( 1, & _vertices ); glBindBuffer( GL_ARRAY_BUFFER, _vertices ); glBufferData( GL_ARRAY_BUFFER, snowflake_vertices.size() * sizeof( float ), snowflake_vertices.data(), GL_STATIC_DRAW ); glEnableVertexAttribArray( 1 ); glVertexAttribPointer( 1, 3, GL_FLOAT, GL_FALSE, 5 * sizeof( float ),( void * ) 0 ); glEnableVertexAttribArray( 2 ); glVertexAttribPointer( 2, 2, GL_FLOAT, GL_FALSE, 5 * sizeof( float ),( void * )( 3 * sizeof( float ) ) ); glBindVertexArray( 0 ); loadTextureOfSnowflake( "textures/snowflake.png" ); _program = program; } ~SnowStorm() { glDeleteVertexArrays( 1, & _VAO ); glDeleteBuffers( 1, & _positions ); glDeleteBuffers( 1, & _vertices ); glDeleteTextures( 1, & _texture_snowflake ); for( auto & snow: falling_snowflakes ) { delete snow; } } };
|
|
tBane Temat założony przez niniejszego użytkownika |
» 2025-02-10 07:32:16 jak ktoś potrafi wygenerować deszcz lub opadający popiół to też może być :P |
|
tBane Temat założony przez niniejszego użytkownika |
» 2025-02-10 08:32:51 Mam rozwiązanie ale słabe tzn. zamiast traktować cząsteczki jako zbiór pozycji mogę je przetwarzać jako osobne obiekty. Tylko to rozwiązanie znacznie spowolni działanie programu. |
|
« 1 » 2 |