Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: New user, first project - physics sim - particles in a box (various settings)  (Read 4439 times)

0 Members and 2 Guests are viewing this topic.

stuart88

  • Newbie
  • *
  • Posts: 11
    • View Profile
    • Email
Hi all

I couldn't find an 'intros/newbies' area here so figured I'd dive in here with my first post!

I'm a student of physics and recently got into the idea of putting basic (or complex) physics principles into my own simulators.

So to start I've just thrown together a little attempt at simulating particles in a box. It consists of a larger red (player) ball which you can move around to collide with other particles in the box. Manipulable settings include player mass, particle mass, gravity strength, number of particles, 'anti-gravity' player ball, 'freeze' the particles, and - my favourite - turn on electric fields around all the particles so they repel each other.

There's no 'gaming' element to it, but I'm pleased nonetheless as I've seen that it's possible to quite easily put physics into games. My next effort will probably be something relating to quantum mechanics or fluid dynamics. I'm in the process of learning geophysical fluid dynamics now too so in future I hope to do some basic planetary simulations (in 3D?), where the user can do things like set the rotation speed, gravity, density of atmosphere, generate clouds or ocean currents etc. Along the way I might have a go at making some games out of these things too.

Anyway, here's my first little project  :) - https://github.com/Stuart88/Particles

Full executable is available in the RAR archive on GitHub, or alternatively the source code is there along with the necessary font and sprite files

(click to show/hide)


JayhawkZombie

  • Jr. Member
  • **
  • Posts: 76
    • View Profile
Cool man!

If you want to render a ton of particles, I might recommend instanced rendering: https://learnopengl.com/#!Advanced-OpenGL/Instancing

And idk if this will help, but this article mentions a bit on linear solvers while doing an example of a smoke shader, which might help if you want to try doing fluids: https://gamedevelopment.tutsplus.com/tutorials/how-to-write-a-smoke-shader--cms-25587

Hapax

  • Hero Member
  • *****
  • Posts: 3379
  • My number of posts is shown in hexadecimal.
    • View Profile
    • Links
It looks like instancing would require the use of direct OpenGL so a "compromise" would be to use vertex arrays via SFML. That way you can draw everything with one draw call and still stick to using SFML stuff.
Selba Ward -SFML drawables
Cheese Map -Drawable Layered Tile Map
Kairos -Timing Library
Grambol
 *Hapaxia Links*

stuart88

  • Newbie
  • *
  • Posts: 11
    • View Profile
    • Email
Cheers for the replies. That stuff about instancing (and openGL in general) is new territory for me but I'll definitely have a look. I did wonder how games with many thousands of entities manage to deal with such information.

The smoke simulator looked extremely awesome too. Definitely helped a ton with getting my head around the best way to do it. The bottom part of the article about velocity fields was fascinating (and obvious actually as it's a basic premise of most vector calculus in physics - I definitely should have known that  ::) ! )

I'll provide an update whenever the next little physics sim is made. Might just try the smoke/fluid sim next. :)

JayhawkZombie

  • Jr. Member
  • **
  • Posts: 76
    • View Profile
It looks like instancing would require the use of direct OpenGL so a "compromise" would be to use vertex arrays via SFML. That way you can draw everything with one draw call and still stick to using SFML stuff.

sf::VertexArray would be a much better way compared to rendering a sprite for every item.
From what I can find instanced rendering depends on glDrawElementsInstanced and GL_DRAW_INDIRECT_BUFFER, so it would require OpenGL 4.0+, which would be a problem for older computers.

SFML works very nicely with inserting custom OpenGL code, thankfully!

Instanced rendering isn't too much worse than a normal draw call. I haven't seen the internals of how VertexArray is rendered/how much faster it is than other primitives in SFML.
Just looked at it.  Will be MUCH faster than rendering a separate primitive for each.
OP could do that by putting each particle on the same texture and just setting the texcoords for each array accordingly.

  sf::RenderWindow window(sf::VideoMode(800, 800), "SFML works!");
  window.setVerticalSyncEnabled(false);

  sf::VertexArray Vertices = sf::VertexArray(sf::Quads, 16);

  sf::Texture Bullets;
 
  if (!Bullets.loadFromFile("bulletSprites.png")) {
    return EXIT_FAILURE;
  }

  sf::IntRect Particle1{ 173, 112, 11, 11 };
  sf::IntRect Particle2{ 188, 112, 11, 11 };
  sf::IntRect Particle3{ 203, 112, 11, 11 };

  Vertices[0].position = { 50, 50 }; Vertices[0].texCoords = { 173,      112 };
  Vertices[1].position = { 70, 50 }; Vertices[1].texCoords = { 173 + 11, 112 };
  Vertices[2].position = { 70, 70 }; Vertices[2].texCoords = { 173 + 11, 112 + 11 };
  Vertices[3].position = { 50, 70 }; Vertices[3].texCoords = { 173,      112 + 11 };

  Vertices[4].position = { 150, 150 }; Vertices[4].texCoords = { 188,      112 };
  Vertices[5].position = { 170, 150 }; Vertices[5].texCoords = { 188 + 11, 112 };
  Vertices[6].position = { 170, 170 }; Vertices[6].texCoords = { 188 + 11, 112 + 11 };
  Vertices[7].position = { 150, 170 }; Vertices[7].texCoords = { 188,      112 + 11 };

  Vertices[8].position  = { 75,  250 }; Vertices[8].texCoords  = { 203,      112 };
  Vertices[9].position  = { 100, 250 }; Vertices[9].texCoords  = { 203 + 11, 112 };
  Vertices[10].position = { 100, 275 }; Vertices[10].texCoords = { 203 + 11, 112 + 11 };
  Vertices[11].position = { 75,  275 }; Vertices[11].texCoords = { 203,      112 + 11 };

  Vertices[12].position = { 150, 350 }; Vertices[12].texCoords = { 173,      112 };
  Vertices[13].position = { 170, 350 }; Vertices[13].texCoords = { 173 + 11, 112 };
  Vertices[14].position = { 170, 370 }; Vertices[14].texCoords = { 173 + 11, 112 + 11 };
  Vertices[15].position = { 150, 370 }; Vertices[15].texCoords = { 173,      112 + 11 };

  sf::RenderStates State;
  State.texture = &Bullets;

...

window.clear(sf::Color::Black);
window.draw(Vertices, State);
window.display();
 

Result:

stuart88

  • Newbie
  • *
  • Posts: 11
    • View Profile
    • Email
Ok I've just had a read of the stuff on vertex arrays. More fascinating stuff, cheers :)