Qiita Teams that are logged in
You are not logged in to any team

Log in to Qiita Team
Community
OrganizationEventAdvent CalendarQiitadon (β)
Service
Qiita JobsQiita ZineQiita Blog
1
Help us understand the problem. What are the problem?
@hta393939

HSP3.5 HGIMG4 で剛体をキネティック(強制指定)モードにする

HSP3.5 HGIMG4 で剛体をキネマティック(強制指定)モードにする

HGIMG4 では三次元の物理演算剛体が使えますが、gppbind で3Dオブジェクトを3D物理演算剛体として指定すると基本的には setpos などでは移動できなくなり、3D物理演算に従った移動回転が発生します。
しかし gppset で GPPSET_KINEMATIC で x成分 に 1.0 を指定することでその物理演算剛体を強制指定モードに変更することができます。
注意する必要があるのはこの方法で移動させる場合は質量を 0.0 にしてはならないということです。

このキネマティックモードを利用してコインプッシャーもどきを作ってみました。
以下サンプルコードです。

#include "hgimg4.as"

    randomize
    gpreset
    setcls CLSMODE_SOLID, 0x000000

    whole_size = 32
    whole_half = whole_size / 2

    height_size = 2
    height_half = height_size / 2

    div_num = 4

    box_size = whole_size / div_num
    box_half = box_size / 2

    setborder whole_size * 2.0, whole_size * 2.0, whole_size * 2.0
// 前後移動イベント
    dim evs, 2
    foreach evs
        frs = 157, 163
        vel = double(box_size) / double(frs.cnt)

        newevent ev
        event_addpos ev, 0,0, - vel
        event_wait ev, frs.cnt
        event_addpos ev, 0,0, vel
        event_wait ev, frs.cnt
        event_jump ev, 0
        evs.cnt = ev
    loop

// プッシャー
    repeat 2
        i = cnt
        cols = 0x00ccff, 0x006699
        col = cols.i

        repeat div_num
            j = cnt
                repeat 3
                    k = cnt

                    gpbox id, box_size, col
                    x = (j * 2 - div_num / 2 - 1) * box_size / 2
                    y = box_half * (1 - i)
                    z = box_half * (-1 + i*2 - k*2)
                    setpos id, x, y, z
                    gppbind id, 1,2
                    gppset id, GPPSET_KINEMATIC, 1
                    setevent id, evs.i
                loop
        loop
    loop
// 黄色い箱
    repeat 200
        gpbox id, 2, 0xcccc00
        setpos id, rnd(7) - 3, whole_size / 2, rnd(7) - 3
        setobjmode id, OBJ_BORDER, 0
        gppbind id, 1, 2
        gppset id, GPPSET_DAMPING, 0,0
    loop
// 床壁
    gpfloor id, whole_size, whole_size, 0x006699
    gppbind id, 0
    repeat 3
        xs = -whole_half, 0, whole_half
        y = whole_half / 2
        zs = 0, -whole_half, 0
        ws = whole_size/2, whole_size, whole_size/2
        hs = whole_size, whole_size/2, whole_size
        rx = 0
        ry = 0
        rz = 0
        if cnt == 0 {
            rz = -64
        }
        if cnt == 1 {
            rx = 64
        }
        if cnt == 2 {
            rz = 64
        }
        gpfloor id, ws.cnt, hs.cnt, 0x339966
        setpos id, xs.cnt, y, zs.cnt
        setangr id, rx,ry,rz
        gppbind id, 0
    loop
// ライトとカメラ
    setangr GPOBJ_LIGHT, -16, -32,0
    setpos GPOBJ_CAMERA, 10, 20, 50
    gplookat GPOBJ_CAMERA, 0, 5, 0

    repeat
        getreq fps, SYSREQ_FPS

        stick key
        if key & 256 {
            gpbox id, 2, 0xcccc00
            setpos id, rnd(25)-12, whole_half, -whole_half
            setobjmode id, OBJ_BORDER, 0
            gppbind id, 1, 2
            gppset id, GPPSET_DAMPING, 0,0      
        }

        redraw 0        
        gpdraw
        pos 16,16
        color 224,224,224
        font "",48
        mes strf("%2d [fps]", fps)
        redraw 1
        await 1000/60
    loop
実行結果1
z04c1.png
黄色い箱がコインがわりのコインプッシャーです
実行結果2
z04c2.png
左クリックで黄色い箱を補充できます

プッシャーをキネマティックモードにしてイベントで前後移動させ、コイン代わりの箱は通常の3D物理演算で動作が決まるようになっています。

現状では gpbox ですべての辺の長さが等しい立方体しか生成できないため、立方体を複数並べてそれぞれの段の滝を実現しています。直方体とその形状の剛体も作れるようになると、もっと便利かなぁと思います。次期バージョンアップ時の追加に期待したいと思います。

参考

HSP3.5 hgimg4 を基礎から理解したい方は以下の記事がとてもおすすめです。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
1
Help us understand the problem. What are the problem?