www.mtkn.jp

Manuscripts for my personal webpage.
git clone https://git.mtkn.jp/www.mtkn.jp
Log | Files | Refs | LICENSE

xlib_playground5.html (3261B)


      1 <h1>Xlibで遊んでみる5</h1>
      2 <time>2023-01-03</time>
      3 
      4 <p>
      5 前回: <a href="xlib_playground4.html">Xlibで遊んでみる4</a>
      6 </p>
      7 <p>
      8 言語: C言語<br />
      9 ソースコード: \
     10 <a href="https://git.mtkn.jp/xlib_playground">git</a>
     11 </p>
     12 
     13 <h2>円の衝突判定とその処理</h2>
     14 <p>
     15 前回四角形で行っていた衝突判定とその処理を今回は円でした。\
     16 衝突の判定は二つの円の中心間の距離と、各円の半径の和を比較するだけなので\
     17 簡単である:
     18 </p>
     19 <pre><code>\
     20 struct circle {
     21 	float ppx, ppy;  // previous position (center)
     22 	float px, py;    // current position (center)
     23 	float vx, vy;    // velocity
     24 	int r;           // radius
     25 	int m;           // mass
     26 };
     27 
     28 int
     29 circle_test_collision(struct circle *c1, struct circle *c2)
     30 {
     31 	return (c1-&gt;px - c2-&gt;px) * (c1-&gt;px - c2-&gt;px) +
     32 	       (c1-&gt;py - c2-&gt;py) * (c1-&gt;py - c2-&gt;py) &lt;
     33 		   (c1-&gt;r + c2-&gt;r) * (c1-&gt;r + c2-&gt;r);
     34 }
     35 </code></pre>
     36 
     37 <p>
     38 衝突後は前回と同じく弾性衝突として処理した。\
     39 四角形とは違い、衝突方向の場合分けが不要なので楽である。
     40 </p>
     41 <pre><code>
     42 void
     43 circle_handle_collision_mm(struct circle *c1, struct circle *c2)
     44 {
     45 	if (!circle_test_collision(c1, c2))
     46 		return;
     47 
     48 	float col_px = c2-&gt;px - c1-&gt;px;
     49 	float col_py = c2-&gt;py - c1-&gt;py;
     50 	float col_pr = sqrtf(col_px * col_px + col_py * col_py);
     51 	col_px /= col_pr;
     52 	col_py /= col_pr;
     53 
     54 	c1-&gt;px = c1-&gt;px - col_px / 2;
     55 	c1-&gt;py = c1-&gt;py - col_py / 2;
     56 	c2-&gt;px = c2-&gt;px + col_px / 2;
     57 	c2-&gt;py = c2-&gt;py + col_py / 2;
     58 }
     59 
     60 void
     61 circle_handle_collision_elastic(struct circle *c1, struct circle *c2)
     62 {
     63 	if(!circle_test_collision(c1, c2))
     64 		return;
     65 
     66 	float col_px = c2-&gt;px - c1-&gt;px;
     67 	float col_py = c2-&gt;py - c1-&gt;py;
     68 	float col_pr = sqrtf(col_px * col_px + col_py * col_py);
     69 	col_px /= col_pr;
     70 	col_py /= col_pr;
     71 	float nor_px = col_py;
     72 	float nor_py = -col_px;
     73 
     74 	float m1 = c1-&gt;m;
     75 	float m2 = c2-&gt;m;
     76 
     77 	float col_1v = c1-&gt;vx * col_px + c1-&gt;vy * col_py;
     78 	float col_2v = c2-&gt;vx * col_px + c2-&gt;vy * col_py;
     79 
     80 	float col_1vxn = (2*m2/(m1+m2)*col_2v + (m1-m2)/(m1+m2)*col_1v) * col_px;
     81 	float col_1vyn = (2*m2/(m1+m2)*col_2v + (m1-m2)/(m1+m2)*col_1v) * col_py;
     82 	float col_2vxn = (2*m1/(m1+m2)*col_1v + (m2-m1)/(m1+m2)*col_2v) * col_px;
     83 	float col_2vyn = (2*m1/(m1+m2)*col_1v + (m2-m1)/(m1+m2)*col_2v) * col_py;
     84 
     85 	float nor_1vx = nor_px * (c1-&gt;vx * nor_px + c1-&gt;vy * nor_py);
     86 	float nor_1vy = nor_py * (c1-&gt;vx * nor_px + c1-&gt;vy * nor_py);
     87 	float nor_2vx = nor_px * (c2-&gt;vx * nor_px + c2-&gt;vy * nor_py);
     88 	float nor_2vy = nor_py * (c2-&gt;vx * nor_px + c2-&gt;vy * nor_py);
     89 
     90 	c1-&gt;vx = col_1vxn + nor_1vx;
     91 	c1-&gt;vy = col_1vyn + nor_1vy;
     92 	c2-&gt;vx = col_2vxn + nor_2vx;
     93 	c2-&gt;vy = col_2vyn + nor_2vy;
     94 
     95 	circle_handle_collision_mm(c1, c2);
     96 }
     97 </code></pre>
     98 
     99 <h2>完成品</h2>
    100 <p>
    101 <a href="https://git.mtkn.jp/xlib_playground/file/ex5/ex5.c.html">git</a>
    102 </p>
    103 <p>
    104 <video controls>
    105 <source src="videos/ex5.webm" type="video/webm">
    106 </video>
    107 </p>
    108 
    109 <h2>参考</h2>
    110 <ul>
    111 <li><a href="https://tronche.com/gui/x/xlib/">The Xlib Manual(html conversion)</a></li>
    112 </ul>
    113 <p>
    114 次の記事: \
    115 <a href="xlib_playground6.html">Xlibで遊んでみる6</a>
    116 </p>