Author Topic: Trivial 2D particle explosions I can't stop watching...  (Read 4340 times)

0 Members and 1 Guest are viewing this topic.

Offline STxAxTIC

  • Library Staff
  • Forum Resident
  • Posts: 1091
  • he lives
    • View Profile
Trivial 2D particle explosions I can't stop watching...
« on: February 02, 2019, 11:36:59 pm »
Code: QB64: [Select]
  1. '#lang "qb"              ' freebasic edit 2011-06
  2. delayconst = 900000 ' freebasic edit 2011-06
  3. 'CLEAR                  ' freebasic edit 2011-06
  4.  
  5.  
  6. LOCATE 1, 2: INPUT "Enter number of particles (default is 80): ", num
  7. IF num = 0 THEN num = 80
  8. DIM x(num), y(num), xold(num), yold(num), v0x(num), v0y(num), col(num)
  9.  
  10. start:
  11. iterations = 0
  12. 'g = RND * 10 + 20
  13. g = RND * 15 + 25
  14. xdamp = RND * .15 + .55
  15. ydamp = RND * .15 + .55
  16. exploderadius = 200 '75
  17. numobstacles = 0
  18. iterationmax = 1200
  19.  
  20. choosecol:
  21. bgcol = INT(RND * 14)
  22. wallcol = 0 'INT(RND * 14)'change to zero for spider mode
  23. IF bgcol = wallcol THEN GOTO choosecol
  24.  
  25. LINE (1, 1)-(639, 479), bgcol, BF
  26. LINE (1, 1)-(639, 479), wallcol, B
  27.  
  28. 'Draw obstacles randomly.
  29. FOR i = 1 TO numobstacles
  30.     LINE (RND * 640, RND * 480)-(RND * 640, RND * 480), wallcol, B
  31.  
  32. 'Make predetermined obstacles.
  33. 'LINE (50, 75)-(600, 125), wallcol, B
  34.  
  35. 'Toggle for random starting position.
  36. xshift = RND * 640
  37. yshift = RND * 480
  38. 'Toggle for fixed starting position
  39. 'xshift = 100
  40. 'yshift = 100
  41.  
  42. FOR i = 1 TO num
  43.     speed = RND * 90
  44.     ang1 = RND * 2 * 3.141592653589793#
  45.     ang2 = RND * 2 * 3.141592653589793#
  46.     x(i) = xshift + RND * exploderadius * COS(ang1)
  47.     y(i) = yshift + RND * exploderadius * SIN(ang1)
  48.     v0x(i) = 1.5 * speed * COS(ang2)
  49.     v0y(i) = speed * SIN(ang2)
  50.     dotcol:
  51.     col(i) = INT(RND * 13 + 1)
  52.     IF col(i) = bgcol OR col(i) = wallcol THEN GOTO dotcol
  53.     IF POINT(x(i), y(i)) = wallcol OR x(i) < 1 OR x(i) > 639 OR y(i) < 1 OR y(i) > 479 THEN i = i - 1
  54.     dv = SQR((v0x(i)) ^ 2 + (v0y(i)) ^ 2)
  55.     IF dv > vmax THEN vmax = dv
  56.     PSET (x(i), y(i)), col(i)
  57.  
  58. dt = .995 / vmax
  59. 'PRINT dt
  60.  
  61.  
  62.     idel = 0: DO: idel = idel + 1: LOOP UNTIL idel > delayconst ' freebasic edit 2011-06
  63.  
  64.     iterations = iterations + 1
  65.     smax = 0
  66.     FOR i = 1 TO num
  67.         xold(i) = x(i)
  68.         yold(i) = y(i)
  69.         v0x(i) = v0x(i) + 0 * dt
  70.         v0y(i) = v0y(i) + g * dt
  71.         xtmp = x(i) + v0x(i) * dt
  72.         ytmp = y(i) + v0y(i) * dt
  73.         IF POINT(xtmp, yold(i)) = wallcol THEN v0x(i) = v0x(i) * -1 * xdamp
  74.         IF POINT(xold(i), ytmp) = wallcol THEN v0y(i) = v0y(i) * -1 * ydamp
  75.         x(i) = x(i) + v0x(i) * dt
  76.         y(i) = y(i) + v0y(i) * dt
  77.         'Recolor stagnant particles.
  78.         xx = x(i) - xold(i)
  79.         yy = y(i) - yold(i)
  80.         IF SQR(xx ^ 2 + yy ^ 2) < .05 THEN col(i) = bgcol
  81.         PSET (xold(i), yold(i)), 0 'bgcol
  82.         PSET (x(i), y(i)), col(i)
  83.         ds = SQR((y(i) - yold(i)) ^ 2 + (x(i) - xold(i)) ^ 2)
  84.         IF ds > smax THEN smax = ds
  85.     NEXT
  86.     IF smax > .95 THEN dt = dt * (1 - .01)
  87.     IF smax < .9 THEN dt = dt * (1 + .01)
  88.     IF iterations > iterationmax THEN
  89.         SLEEP 2
  90.         GOTO start
  91.     END IF
  92.     LINE (19, 459)-(151, 471), wallcol, B
  93.     LINE (20, 460)-(20 + 130 * (iterations / iterationmax), 470), 15, BF
  94.  
You're not done when it works, you're done when it's right.

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
    • View Profile
Re: Trivial 2D particle explosions I can't stop watching...
« Reply #1 on: February 03, 2019, 03:45:16 am »
Here is a mod
Code: QB64: [Select]
  1. _TITLE "trivial 2D explosions" 'STxAxTIC mod B+ 2019-02-03
  2. CONST xmax = 1200
  3. CONST ymax = 700
  4. SCREEN _NEWIMAGE(xmax, ymax, 32)
  5.  
  6. np = 150 'npber of particles
  7. DIM x(np), y(np), xold(np), yold(np), v0x(np), v0y(np), col(np) AS _UNSIGNED LONG
  8.  
  9. nr = 1500 'number of rocks
  10. DIM rx(nr), ry(nr), rw(nr), rh(nr), rc(nr) AS _UNSIGNED LONG
  11. FOR i = 0 TO nr
  12.     rx(i) = -50 + RND * xmax
  13.     ry(i) = .66 * ymax + RND * .5 * ymax
  14.     rw(i) = 30 + RND * 150
  15.     rh(i) = 10 + RND * 40
  16.     r = 200 * RND
  17.     rc(i) = _RGB32(r, .45 * r, .2 * r)
  18.  
  19. no = 40
  20. DIM ox(no), oy(no), ow(no), oh(no)
  21. FOR i = 0 TO no
  22.     ox(i) = RND * xmax
  23.     oy(i) = .66 * ymax + RND * .5 * ymax
  24.     ow(i) = 30 + RND * 150
  25.     oh(i) = 10 + RND * 40
  26.  
  27.  
  28. wallcol = _RGB32(200, 100, 50)
  29. g = 55
  30. xdamp = .1
  31. ydamp = .1
  32. exploderadius = 10
  33.  
  34.  
  35. start:
  36. iterations = 0
  37. 'Toggle for random starting position.
  38. xshift = RND * xmax
  39. yshift = RND * ymax
  40.  
  41. 'sky
  42. FOR y = 0 TO ymax
  43.     LINE (0, y)-(xmax, y), _RGB32(.05 * i, .05 * i, .25 * i), BF
  44. 'rocks
  45. FOR i = 0 TO nr
  46.     LINE (rx(i), ry(i))-STEP(rw(i), rh(i)), rc(i), BF
  47.  
  48. 'Draw obstacles randomly
  49. FOR i = o TO no
  50.     LINE (ox(i), oy(i))-STEP(ow(i), oh(i)), wallcol, BF
  51.  
  52. FOR i = 1 TO np
  53.     speed = RND * 85 + 5
  54.     ang1 = RND * 2 * 3.141592653589793#
  55.     ang2 = RND * 2 * 3.141592653589793#
  56.     x(i) = xshift + RND * exploderadius * COS(ang1)
  57.     y(i) = yshift + RND * exploderadius * SIN(ang1)
  58.     v0x(i) = speed * COS(ang2)
  59.     v0y(i) = speed * SIN(ang2)
  60.     dotcol:
  61.     col(i) = _RGB32(RND * 255, RND * 255, RND * 255)
  62.     IF col(i) = bgcol OR col(i) = wallcol THEN GOTO dotcol
  63.     IF POINT(x(i), y(i)) = wallcol OR x(i) < 0 OR x(i) > xmax OR y(i) < 0 OR y(i) > ymax THEN i = i - 1
  64.     dv = SQR((v0x(i)) ^ 2 + (v0y(i)) ^ 2)
  65.     IF dv > vmax THEN vmax = dv
  66.     fcirc x(i), y(i), 3, col(i)
  67. dt = .995 / vmax
  68.  
  69.  
  70.     'sky
  71.     FOR y = 0 TO ymax
  72.         LINE (0, y)-(xmax, y), _RGB32(.05 * i, .05 * i, .25 * i), BF
  73.     NEXT
  74.     'rocks
  75.     FOR i = 0 TO nr
  76.         LINE (rx(i), ry(i))-STEP(rw(i), rh(i)), rc(i), BF
  77.     NEXT i
  78.  
  79.     'Draw obstacles randomly
  80.     FOR i = o TO no
  81.         LINE (ox(i), oy(i))-STEP(ow(i), oh(i)), wallcol, BF
  82.     NEXT i
  83.  
  84.  
  85.     iterations = iterations + 1
  86.     smax = 0
  87.     FOR i = 1 TO np
  88.         xold(i) = x(i)
  89.         yold(i) = y(i)
  90.         v0x(i) = v0x(i) + 0 * dt
  91.         v0y(i) = v0y(i) + g * dt
  92.         xtmp = x(i) + v0x(i) * dt
  93.         ytmp = y(i) + v0y(i) * dt
  94.         IF POINT(xtmp, yold(i)) = wallcol THEN v0x(i) = v0x(i) * -1 * xdamp
  95.         IF POINT(xold(i), ytmp) = wallcol THEN v0y(i) = v0y(i) * -1 * ydamp
  96.         x(i) = x(i) + v0x(i) * dt
  97.         y(i) = y(i) + v0y(i) * dt
  98.         fcirc x(i), y(i), 3, col(i)
  99.         ds = SQR((y(i) - yold(i)) ^ 2 + (x(i) - xold(i)) ^ 2)
  100.         IF ds > smax THEN smax = ds
  101.     NEXT
  102.     IF smax > .95 THEN dt = dt * (1 - .01)
  103.     IF smax < .9 THEN dt = dt * (1 + .01)
  104.     _DISPLAY
  105.     _LIMIT 200
  106.     IF iterations > 1500  THEN GOTO start
  107.  
  108.  
  109. SUB fcirc (CX AS LONG, CY AS LONG, R AS LONG, k AS _UNSIGNED LONG)
  110.     DIM subRadius AS LONG, RadiusError AS LONG
  111.     DIM X AS LONG, Y AS LONG
  112.  
  113.     subRadius = ABS(R)
  114.     RadiusError = -subRadius
  115.     X = subRadius
  116.     Y = 0
  117.  
  118.     IF subRadius = 0 THEN PSET (CX, CY), k: EXIT SUB
  119.  
  120.     ' Draw the middle span here so we don't draw it twice in the main loop,
  121.     ' which would be a problem with blending turned on.
  122.     LINE (CX - X, CY)-(CX + X, CY), k, BF
  123.  
  124.     WHILE X > Y
  125.         RadiusError = RadiusError + Y * 2 + 1
  126.         IF RadiusError >= 0 THEN
  127.             IF X <> Y + 1 THEN
  128.                 LINE (CX - Y, CY - X)-(CX + Y, CY - X), k, BF
  129.                 LINE (CX - Y, CY + X)-(CX + Y, CY + X), k, BF
  130.             END IF
  131.             X = X - 1
  132.             RadiusError = RadiusError - X * 2
  133.         END IF
  134.         Y = Y + 1
  135.         LINE (CX - X, CY - Y)-(CX + X, CY - Y), k, BF
  136.         LINE (CX - X, CY + Y)-(CX + X, CY + Y), k, BF
  137.     WEND
  138.  

hmm... this runs nicely for awhile and then freezes up?
« Last Edit: February 03, 2019, 04:01:43 am by bplus »

Offline STxAxTIC

  • Library Staff
  • Forum Resident
  • Posts: 1091
  • he lives
    • View Profile
Re: Trivial 2D particle explosions I can't stop watching...
« Reply #2 on: February 03, 2019, 08:31:20 am »
Glad to have caught your attention for a moment bplus. Always keeping it real with mods!

Bplus is not just a man, but an operator! The formula for making a fun mod is evidently:

bplus(program) = program++
You're not done when it works, you're done when it's right.

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
    • View Profile
Re: Trivial 2D particle explosions I can't stop watching...
« Reply #3 on: February 03, 2019, 12:07:33 pm »
Another mod :-))

Code: QB64: [Select]
  1. _TITLE "trivial 2D explosions B+ mod 2" 'STxAxTIC mod B+ 2019-02-03
  2. ' 2019-02-03 use a bg& for background instead of redraws each loop, that should cool down CPU
  3. '  rounder rocks, more fiddle with numbers
  4.  
  5. CONST xmax = 1200
  6. CONST ymax = 700
  7. SCREEN _NEWIMAGE(xmax, ymax, 32)
  8. _SCREENMOVE 100, 20
  9.  
  10. np = 500 'number of particles
  11. DIM x(np), y(np), xold(np), yold(np), v0x(np), v0y(np), col(np) AS _UNSIGNED LONG
  12.  
  13. nr = 3500 'number of rocks
  14. DIM rx(nr), ry(nr), rw(nr), rh(nr), rc(nr) AS _UNSIGNED LONG
  15. FOR i = 0 TO nr \ 2
  16.     rx(i) = RND * xmax
  17.     ry(i) = .5 * ymax + RND * .25 * ymax + rx(i) * .09
  18.     rw(i) = ry(i) * ry(i) * .00015
  19.     rh(i) = .3 * rw(i)
  20.     r = 200 * RND
  21.     rc(i) = _RGB32(r, .45 * r, .2 * r)
  22. FOR i = nr \ 2 + 1 TO nr
  23.     rx(i) = RND * xmax
  24.     ry(i) = .5 * ymax + RND * .75 * ymax + rx(i) * .09
  25.     rw(i) = ry(i) * ry(i) * .00015
  26.     rh(i) = .3 * rw(i)
  27.     r = 200 * RND
  28.     rc(i) = _RGB32(r, .45 * r, .2 * r)
  29.  
  30. no = 80 'number of rock bounce reflectors
  31. DIM ox(no), oy(no), ow(no), oh(no)
  32. FOR i = 0 TO no
  33.     ox(i) = RND * xmax
  34.     oy(i) = .5 * ymax + RND * .75 * ymax + ox(i) * .09
  35.     ow(i) = oy(i) * oy(i) * .00015
  36.     oh(i) = .3 * ow(i)
  37.  
  38.  
  39. wallcol = _RGB32(200, 100, 50)
  40. g = 95
  41. xdamp = .07
  42. ydamp = .07
  43. exploderadius = 10
  44.  
  45. 'draw background
  46. bgrd& = _NEWIMAGE(xmax, ymax, 32)
  47. _DEST bgrd&
  48. 'sky
  49. FOR y = 0 TO ymax
  50.     LINE (0, y)-(xmax, y), _RGB32(.1 * y, .1 * y, .15 * y), BF
  51. 'rocks
  52. FOR i = 0 TO nr
  53.     EllipseFill rx(i), ry(i), rw(i), rh(i), rc(i)
  54.     'LINE (rx(i), ry(i))-STEP(rw(i), rh(i)), rc(i), BF
  55.  
  56. 'Draw obstacles randomly
  57. FOR i = o TO no
  58.     EllipseFill ox(i), oy(i), ow(i), oh(i), wallcol
  59.     'LINE (ox(i), oy(i))-STEP(ow(i), oh(i)), wallcol, BF
  60.  
  61.  
  62. start:
  63. iterations = 0
  64. 'Toggle for random starting position.
  65. xshift = RND * xmax
  66. yshift = RND * ymax * .6
  67.  
  68.  
  69. FOR i = 1 TO np
  70.     speed = RND * 150 + 1
  71.     ang1 = RND * 2 * 3.141592653589793#
  72.     ang2 = RND * 2 * 3.141592653589793#
  73.     x(i) = xshift + RND * exploderadius * COS(ang1)
  74.     y(i) = yshift + RND * exploderadius * SIN(ang1)
  75.     v0x(i) = speed * COS(ang2)
  76.     v0y(i) = speed * SIN(ang2)
  77.     dotcol:
  78.     col(i) = _RGB32(RND * 255, RND * 255, RND * 255)
  79.     IF col(i) = bgcol OR col(i) = wallcol THEN GOTO dotcol
  80.     IF POINT(x(i), y(i)) = wallcol OR x(i) < 0 OR x(i) > xmax OR y(i) < 0 OR y(i) > ymax THEN i = i - 1
  81.     dv = SQR((v0x(i)) ^ 2 + (v0y(i)) ^ 2)
  82.     IF dv > vmax THEN vmax = dv
  83. dt = .995 / vmax
  84.  
  85.     _PUTIMAGE , bgrd&, 0
  86.     iterations = iterations + 1
  87.     smax = 0
  88.     FOR i = 1 TO np
  89.         xold(i) = x(i)
  90.         yold(i) = y(i)
  91.         v0x(i) = v0x(i) + .1 * dt
  92.         v0y(i) = v0y(i) + g * dt + .2 'more gravity
  93.         xtmp = x(i) + v0x(i) * dt
  94.         ytmp = y(i) + v0y(i) * dt
  95.         IF POINT(xtmp, yold(i)) = wallcol THEN v0x(i) = v0x(i) * -1 * xdamp
  96.         IF POINT(xold(i), ytmp) = wallcol THEN v0y(i) = v0y(i) * -1 * ydamp
  97.         x(i) = x(i) + v0x(i) * dt
  98.         y(i) = y(i) + v0y(i) * dt
  99.         EllipseFill x(i), y(i), 3, 3, col(i)
  100.         ds = SQR((y(i) - yold(i)) ^ 2 + (x(i) - xold(i)) ^ 2)
  101.         IF ds > smax THEN smax = ds
  102.     NEXT
  103.     IF smax > .95 THEN dt = dt * (1 - .01)
  104.     IF smax < .9 THEN dt = dt * (1 + .01)
  105.     _DISPLAY
  106.     _LIMIT 200
  107.     IF iterations > 1500 THEN GOTO start
  108.  
  109. ' with Steve's EllipseFill, who needs CircleFill?
  110. SUB EllipseFill (cx AS INTEGER, cy AS INTEGER, rx AS INTEGER, ry AS INTEGER, c AS _UNSIGNED LONG)
  111.     DIM a AS LONG, b AS LONG
  112.     DIM x AS LONG, y AS LONG
  113.     DIM xx AS LONG, yy AS LONG
  114.     DIM sx AS LONG, sy AS LONG
  115.     DIM e AS LONG
  116.  
  117.     a = 2 * rx * rx
  118.     b = 2 * ry * ry
  119.     x = rx
  120.     xx = ry * ry * (1 - rx - rx)
  121.     yy = rx * rx
  122.     sx = b * rx
  123.  
  124.     DO WHILE sx >= sy
  125.         LINE (cx - x, cy - y)-(cx + x, cy - y), c, BF
  126.         IF y <> 0 THEN LINE (cx - x, cy + y)-(cx + x, cy + y), c, BF
  127.  
  128.         y = y + 1
  129.         sy = sy + a
  130.         e = e + yy
  131.         yy = yy + a
  132.  
  133.         IF (e + e + xx) > 0 THEN
  134.             x = x - 1
  135.             sx = sx - b
  136.             e = e + xx
  137.             xx = xx + b
  138.         END IF
  139.     LOOP
  140.  
  141.     x = 0
  142.     y = ry
  143.     xx = rx * ry
  144.     yy = rx * rx * (1 - ry - ry)
  145.     e = 0
  146.     sx = 0
  147.     sy = a * ry
  148.  
  149.     DO WHILE sx <= sy
  150.         LINE (cx - x, cy - y)-(cx + x, cy - y), c, BF
  151.         LINE (cx - x, cy + y)-(cx + x, cy + y), c, BF
  152.  
  153.         DO
  154.             x = x + 1
  155.             sx = sx + b
  156.             e = e + xx
  157.             xx = xx + b
  158.         LOOP UNTIL (e + e + yy) > 0
  159.  
  160.         y = y - 1
  161.         sy = sy - a
  162.         e = e + yy
  163.         yy = yy + a
  164.  
  165.     LOOP
  166.  
  167.  
  168.  
« Last Edit: February 03, 2019, 12:16:33 pm by bplus »

Offline STxAxTIC

  • Library Staff
  • Forum Resident
  • Posts: 1091
  • he lives
    • View Profile
Re: Trivial 2D particle explosions I can't stop watching...
« Reply #4 on: February 03, 2019, 02:22:31 pm »
Man, that one's beautiful. Makes this thread earn its title.
You're not done when it works, you're done when it's right.

Offline Pete

  • Forum Resident
  • Posts: 2361
  • Cuz I sez so, varmint!
    • View Profile
Re: Trivial 2D particle explosions I can't stop watching...
« Reply #5 on: February 03, 2019, 03:51:56 pm »
Mark has too much 4th dimension on his hands... at least I hope that's time. Anyway, back to livin' in a 2D world! Now if someone can just invent a time machine and travel this stuff back to when Atari was born, they'd make a fortune. It's kind of a shame this kind of math is not my kind of thing, but it isn't. I mean I'm always amazed at how much happens on the screen with so few statements to make things happen; that's quite something.

Anyway, nice work guys...

Pete
Want to learn how to write code on cave walls? https://www.tapatalk.com/groups/qbasic/qbasic-f1/