Ejemplo n.º 1
0
osg::Vec3 CameraModel::get_translation() const {
    osg::Vec4 eye( _eye[0], _eye[1], _eye[2], 1.0);
    osg::Vec4 t = -(eye*get_rot());
    freemovr_assert(t[3]==1.0);
    osg::Vec3 result(t[0], t[1], t[2]);
    return result;
}
Ejemplo n.º 2
0
quat & mat4::get_rot(quat& q) const
{
	mat3 m;
	get_rot(m);
	q.FromMatrix(m);
    return q;
}
Ejemplo n.º 3
0
Variant Node2D::edit_get_state() const {

	Array state;
	state.push_back(get_pos());
	state.push_back(get_rot());
	state.push_back(get_scale());

	return state;

}
Ejemplo n.º 4
0
void unit_vehicle::update(int dt, world &w)
{
    if (hp <= 0)
        return;

    if (m_first_update)
    {
        m_first_update = false;

        if (!m_follow.expired())
        {
            auto f = m_follow.lock();
            vec3 diff = get_pos() - f->get_pos();
            if (diff.length() < m_params.formation_radius)
                m_formation_offset = f->get_rot().rotate_inv(diff);
            else
                m_formation_offset.set(0, 0, -15.0f);
        }

        m_ground = (get_pos().y - w.get_height(get_pos().x, get_pos().z)) < 5.0f;
        if (m_ground)
        {
            //ToDo: gear anim
        }
        else
        {
            if (m_params.speed_min > 0.01f)
                m_vel = get_rot().rotate(vec3::forward() * m_params.speed_cruise);
            m_dpos = vec3();
        }

        return;
    }

    float kdt = dt * 0.001f;

    vec3 target_dir;
    bool has_target = false;

    if (m_target.expired())
    {
        if (m_ai > ai_default && m_target_search != search_none)
        {
            const bool air = m_ai == ai_air_to_air || m_ai == ai_air_multirole,
            ground = m_ai == ai_air_to_ground || m_ai == ai_air_multirole;

            float min_dist = 10000.0f;
            for (int i = 0; i < w.get_planes_count() + w.get_units_count(); ++i)
            {
                object_ptr t;
                if (i < w.get_planes_count())
                {
                    auto p = w.get_plane(i);
                    if (is_ally(p, w))
                        continue;

                    t = p;
                }
                else
                {
                    if (m_target_search == search_player)
                        continue;

                    auto u = w.get_unit(i - w.get_planes_count());
                    if (is_ally(u))
                        continue;

                    t = u;
                }

                if (!t->is_targetable(air, ground))
                    continue;

                const float dist = (t->get_pos() - get_pos()).length();
                if(dist >= min_dist)
                    continue;

                m_target = t;
                min_dist = dist;
            }
        }
    }
    else
    {
        if (m_target.lock()->hp <= 0)
            m_target.reset();
    }

    bool not_path_not_follow = false;

    if (!m_path.empty())
    {
        has_target = true;
        target_dir = m_path.front() - get_pos();
        if (target_dir.length() < m_vel.length() * kdt * m_params.target_radius)
        {
            if (m_path_loop)
                m_path.push_back(m_path.front());
            m_path.pop_front();
            if (m_path.empty())
                has_target = false;
            else
                target_dir = m_path.front() - get_pos();
        }
    }
    else if (!m_follow.expired())
    {
        has_target = true;
        auto f = m_follow.lock();
        target_dir = f->get_pos() + f->get_rot().rotate(m_formation_offset) - (get_pos() + get_vel() * kdt);
        //+ f->get_vel() * kdt //player's plane is already updated, ToDo
    }
    else
        not_path_not_follow = true;

    if (!m_target.expired())
    {
        auto t = m_target.lock();
        const auto dir = t->get_pos() + t->get_rot().rotate(vec3(0, 0, -20.0)) - (get_pos() + get_vel() * kdt);

        if (not_path_not_follow)
        {
            target_dir = dir;
            has_target = true;
        }

        for (auto &wp: m_weapons)
        {
            if (wp.cooldown > 0)
            {
                wp.cooldown -= dt;
                continue;
            }

            if (dir.length() > wp.params.lockon_range)
                continue;

            wp.cooldown = wp.params.reload_time;
            auto m = w.add_missile(wp.params.id.c_str(), wp.mdl);
            if (!m)
                continue;

            m->phys->pos = get_pos();
            m->phys->rot = get_rot();
            m->phys->vel = get_vel();

            m->phys->target_dir = dir;
            m->target = m_target;
        }
    }

    if (has_target)
    {
        const float eps=1.0e-6f;
        const float target_dist = target_dir.length();
        const vec3 v=target_dir / target_dist;
        const float xz_sqdist=v.x*v.x+v.z*v.z;

        const auto rot = get_rot();
        const auto pyr = rot.get_euler();

        const nya_math::angle_rad new_yaw=(xz_sqdist>eps*eps)? (atan2(v.x,v.z)) : pyr.y;
        nya_math::angle_rad new_pitch=(fabsf(v.y)>eps)? (-atan2(v.y,sqrtf(xz_sqdist))) : 0.0f;
        nya_math::angle_rad new_roll;
        if (!m_follow.expired())
            new_roll = m_follow.lock()->get_rot().get_euler().z;

        vec3 pos = get_pos() + m_vel * kdt;
        const float h = w.get_height(pos.x, pos.z);
        if ((new_pitch > 0.0f && pos.y <= h + m_params.height_min) || (new_pitch < 0.0f && pos.y >= h + m_params.height_max))
            new_pitch = 0.0f;

        const auto ideal_rot = quat(new_pitch, new_yaw, new_roll);

        const float angle_diff = rot.rotate(vec3::forward()).angle(target_dir).get_deg();
        if (fabsf(angle_diff) > 0.001f)
        {
            const float turn_k = nya_math::clamp((180.0f / angle_diff) * m_params.turn_speed * kdt, 0.0, 1.0);
            m_render->mdl.set_rot(quat::slerp(rot, ideal_rot, turn_k));
        }

        float speed = m_vel.length();
        float want_speed = target_dist / kdt;
        if (!m_follow.expired())
        {
            const float target_speed = m_follow.lock()->get_vel().length();
            float decel_time = (speed - target_speed) / m_params.decel;
            if (target_dist / (speed + m_params.accel * kdt) < decel_time)
                want_speed = target_speed;
        }

        want_speed = nya_math::clamp(want_speed, m_params.speed_min, std::min(m_params.speed_max, m_speed_limit));
        speed = tend(speed, want_speed, m_params.accel * kdt, m_params.decel * kdt);
        m_vel = get_rot().rotate(vec3(0.0, 0.0, speed));
    }
    else if (m_params.speed_min < 0.01f)
    {
        float speed = m_vel.length();
        if (speed > 0.0f)
        {
            speed = tend(speed, 0.0f, m_params.accel * kdt, m_params.decel * kdt);
            m_vel = get_rot().rotate(vec3(0.0, 0.0, speed));
        }
    }

    vec3 pos = get_pos() + m_vel * kdt;

    const float h = w.get_height(pos.x, pos.z);
    pos.y = nya_math::clamp(pos.y, h + m_params.height_min, h + m_params.height_max); //ToDo

    set_pos(pos);
}
Ejemplo n.º 5
0
void Node2D::rotate(float p_radians) {

	set_rot( get_rot() + p_radians);
}
Ejemplo n.º 6
0
float Node2D::_get_rotd() const {

	return Math::rad2deg(get_rot());
}
Ejemplo n.º 7
0
int main()
{
    setup_resources();

    config::register_var("screen_width", "1000");
    config::register_var("screen_height", "562");
    config::register_var("master_volume", "10");
    config::register_var("music_volume", "5");

    platform platform;
    if (!platform.init(config::get_var_int("screen_width"), config::get_var_int("screen_height"), "Open Horizon 7th demo"))
        return -1;

    std::vector<joystick_config> joysticks;

    for (int i = 0; glfwJoystickPresent(i); ++i)
    {
        const char *name = glfwGetJoystickName(i);

        joystick_config j;
        j.init(name);
        joysticks.push_back(j);

        int axis_count = 0, buttons_count = 0;
        glfwGetJoystickAxes(i, &axis_count);
        glfwGetJoystickButtons(i, &buttons_count);
        printf("joy%d: %s %d axis %d buttons\n", i, name, axis_count, buttons_count);
    }

    renderer::scene scene;
    sound::world sound_world;
    game::world world(scene, sound_world, scene.hud);
    game::mission game_mode_ms(world);
    game::free_flight game_mode_ff(world);
    game::deathmatch game_mode_dm(world);
    game::team_deathmatch game_mode_tdm(world);
    game::hangar hangar(scene);
    game::game_mode *active_game_mode = 0;
    game::plane_controls controls;
    game::network_client client;
    game::network_server server;

    gui::menu menu(sound_world);
    gui::menu_controls menu_controls;

    platform::key_callback kcb = std::bind(&gui::menu::on_input, &menu, std::placeholders::_1);
    platform.set_keyboard_callback(kcb);

    int mx = platform.get_mouse_x(), my = platform.get_mouse_y();
    int screen_width = platform.get_width(), screen_height = platform.get_height();
    scene.resize(screen_width, screen_height);
    scene.loading(true);
    nya_render::clear(true, true);
    scene.draw();
    platform.end_frame();

    sound_world.set_volume(config::get_var_int("master_volume") / 10.0f);
    sound_world.set_music_volume(config::get_var_int("music_volume") / 10.0f);

    menu.init();
    sound_world.set_music("BGM_menu");

    bool viewer_mode = false;
    bool is_client = false, is_server = false;

    gui::menu::on_action on_menu_action = [&](const std::string &event)
    {
        if (event == "start")
        {
            sound_world.stop_music();
            const char *music_names[] = {"BGM_ms10_08", "BGM_ms06", "BGM_ms08x", "BGM_ms11a", "BGM_ms11b", "BGM_ms12_02"};
            sound_world.set_music(music_names[rand() % (sizeof(music_names) / sizeof(music_names[0]))]);

            auto location = menu.get_var("map");
            auto plane = menu.get_var("ac");
            const int color = atoi(menu.get_var("color").c_str());

            is_client = false, is_server = false;

            scene.loading(true);
            nya_render::clear(true, true);
            scene.draw();
            platform.end_frame();
            scene.loading(false);

            auto mode = menu.get_var("mode");
            auto mp_var = menu.get_var("multiplayer");
            if (mp_var == "server")
            {
                world.set_network(&server);
                auto port = menu.get_var_int("port");
                server.open(port, config::get_var("name").c_str(), mode.c_str(), menu.get_var("map").c_str(), menu.get_var_int("max_players"));
                if (menu.get_var("mp_public") == "true")
                    game::servers_list::register_server(port);
                is_server = true;
            }
            else if (mp_var == "client")
            {
                world.set_network(&client);
                client.start();
                is_client = true;
            }

            if (mode == "ms")
            {
                active_game_mode = &game_mode_ms;
                game_mode_ms.start(plane.c_str(), color,  menu.get_var("mission").c_str());
            }
            else if (mode == "dm")
            {
                const int bots_count = (is_client || is_server) ? 0 : 11;

                active_game_mode = &game_mode_dm;
                game_mode_dm.start(plane.c_str(), color, 0, location.c_str(), bots_count);
            }
            else if (mode == "tdm")
            {
                const int bots_count = (is_client || is_server) ? 0 : 7;

                active_game_mode = &game_mode_tdm;
                game_mode_tdm.start(plane.c_str(), color, 0, location.c_str(), bots_count);
            }
            else if (mode == "ff")
            {
                active_game_mode = &game_mode_ff;
                game_mode_ff.start(plane.c_str(), color, location.c_str());
            }
        }
        else if (event == "connect")
        {
            menu.set_error("");
            client.disconnect();
            auto port = menu.get_var_int("port");
            if (client.connect(menu.get_var("address").c_str(), port))
            {
                menu.send_event("map=" + client.get_server_info().location);
                menu.send_event("mode=" + client.get_server_info().game_mode);
                menu.send_event("screen=ac_select");
            }
            else
                menu.set_error(client.get_error());
        }
        else if (event == "viewer_start")
        {
            viewer_mode = true;
            scene.camera.add_delta_rot(0.2f, 2.5f);
        }
        else if (event == "viewer_update_bg")
        {
            hangar.set_bkg(menu.get_var("bkg").c_str());
        }
        else if (event == "viewer_update_ac")
        {
            const auto dr = scene.camera.get_delta_rot();
            hangar.set_plane(menu.get_var("ac").c_str());
            scene.camera.add_delta_rot(dr.x, dr.y - 3.14f);
        }
        else if (event == "viewer_update_color")
        {
            const auto dr = scene.camera.get_delta_rot();
            const int color = atoi(menu.get_var("color").c_str());
            hangar.set_plane_color(color);
            scene.camera.add_delta_rot(dr.x, dr.y - 3.14f);
        }
        else if (event == "viewer_end")
        {
            viewer_mode = false;
            hangar.end();
        }
        else if (event == "update_volume")
        {
            sound_world.set_volume(config::get_var_int("master_volume") / 10.0f);
            sound_world.set_music_volume(config::get_var_int("music_volume") / 10.0f);
        }
        else if (event == "update_joy_config")
        {
            if (!joysticks.empty())
                joysticks.front().update_config();
        }
        else if (event == "exit")
        {
            server.close();
            client.disconnect();
            platform.terminate();
        }
        else
            printf("unknown event: %s\n", event.c_str());
    };

    menu.set_callback(on_menu_action);

    bool reset_camera = false;

    unsigned long app_time = nya_system::get_time();
    while (!platform.should_terminate())
    {
        unsigned long time = nya_system::get_time();
        int dt = int(time - app_time);

        if (dt > 1000 && !is_client && !is_server)
            dt = 1000;

        app_time = time;

        static bool speed10x = false, last_pause = false, paused = false;

        if (platform.get_width() != screen_width || platform.get_height() != screen_height)
        {
            screen_width = platform.get_width(), screen_height = platform.get_height();
            scene.resize(screen_width, screen_height);

            config::set_var("screen_width", std::to_string(screen_width));
            config::set_var("screen_height", std::to_string(screen_height));
        }

        if (!active_game_mode)
            menu.update(dt, menu_controls);

        if (active_game_mode)
        {
            if (!paused)
            {
                active_game_mode->update(speed10x ? dt * 10 : dt, controls);

                //camera - tracking enemy
                auto p = world.get_player();
                if (p && p->change_target_hold_time >= game::plane::change_target_hold_max_time && !p->targets.empty() && !p->targets.front().target.expired())
                {
                    static auto last_target = p->targets.front().target;
                    if (last_target.expired() || last_target.lock() != p->targets.front().target.lock())
                    {
                        last_target = p->targets.front().target;
                        p->change_target_hold_time = game::plane::change_target_hold_max_time;
                    }

                    auto t = p->targets.front().target.lock();
                    auto tdir = t->get_pos() - p->get_pos(); // + (t->get_vel() - p->get_vel()) * (dt * 0.001f)
                    nya_math::quat q(nya_math::vec3::forward(), tdir);
                    q = nya_math::quat::invert(p->get_rot()) * q;

                    auto da = q.get_euler();
                    scene.camera.reset_delta_rot();

                    const float k = nya_math::min((p->change_target_hold_time - game::plane::change_target_hold_max_time) / 500.0f, 1.0);

                    scene.camera.add_delta_rot(da.x * k, -da.y * k);
                    reset_camera = true;
                }
            }

            scene.draw();

            //util debug draw
            nya_render::clear(false, true);
            nya_render::set_state(nya_render::state());
            nya_render::set_modelview_matrix(nya_scene::get_camera().get_view_matrix());
            get_debug_draw().set_line_width(2.0f);
            get_debug_draw().set_point_size(3.0f);
            get_debug_draw().draw();
        }
        else
        {
            nya_render::clear(true, true);

            if (viewer_mode)
            {
                hangar.update(dt);
                scene.draw();
            }

            menu.draw(scene.ui_render);
        }

        const char *ui_ref = 0;
        //ui_ref = "ui_ref4.tga";
        if (ui_ref)
        {
            static nya_scene::texture ui_ref_texture(ui_ref);
            static std::vector<gui::rect_pair> ui_ref_rects(1);
            ui_ref_rects[0].r.w = scene.ui_render.get_width();
            ui_ref_rects[0].r.y = scene.ui_render.get_height();
            ui_ref_rects[0].r.h = -scene.ui_render.get_height();
            ui_ref_rects[0].tc.w = ui_ref_texture.get_width();
            ui_ref_rects[0].tc.h = ui_ref_texture.get_height();
            static int alpha_anim = 0;
            alpha_anim += dt;
            alpha_anim = alpha_anim % 4000;
            //alpha_anim = 1000;
            scene.ui_render.draw(ui_ref_rects, ui_ref_texture, nya_math::vec4(1.0, 1.0, 1.0, fabsf(alpha_anim / 2000.0f - 1.0)));
        }

        platform.end_frame();

        //controls

        controls = game::plane_controls();
        menu_controls = gui::menu_controls();

        if (platform.get_mouse_lbtn())
            scene.camera.add_delta_rot((platform.get_mouse_y() - my) * 0.03, (platform.get_mouse_x() - mx) * 0.03);

        if (platform.get_mouse_rbtn())
            scene.camera.add_delta_pos(0, 0, my - platform.get_mouse_y());

        mx = platform.get_mouse_x(), my = platform.get_mouse_y();

        bool pause = false;
        for (int i = 0; i < (int)joysticks.size(); ++i)
        {
            int axes_count = 0, buttons_count = 0;
            const float *axes = glfwGetJoystickAxes(i, &axes_count);
            const unsigned char *buttons = glfwGetJoystickButtons(i, &buttons_count);
            joysticks[i].update(axes, axes_count, buttons, buttons_count);
            joysticks[i].apply_controls(controls, pause);

            if (!active_game_mode)
            {
                if (i == 0 && !menu.joy_update(axes, axes_count, buttons, buttons_count))
                    joysticks[i].apply_controls(menu_controls);
            }
        }

        if (platform.get_key(GLFW_KEY_W)) controls.throttle = 1.0f;
        if (platform.get_key(GLFW_KEY_S)) controls.brake = 1.0f;
        if (platform.get_key(GLFW_KEY_A)) controls.rot.y = -1.0f;
        if (platform.get_key(GLFW_KEY_D)) controls.rot.y = 1.0f;
        if (platform.get_key(GLFW_KEY_UP)) controls.rot.x = 1.0f, menu_controls.up = true;
        if (platform.get_key(GLFW_KEY_DOWN)) controls.rot.x = -1.0f, menu_controls.down = true;
        if (platform.get_key(GLFW_KEY_LEFT)) controls.rot.z = -1.0f, menu_controls.left = true;
        if (platform.get_key(GLFW_KEY_RIGHT)) controls.rot.z = 1.0f, menu_controls.right = true;

        if (platform.get_key(GLFW_KEY_LEFT_CONTROL)) controls.mgun = true;
        if (platform.get_key(GLFW_KEY_LEFT_SHIFT)) controls.mgun = true;
        if (platform.get_key(GLFW_KEY_SPACE)) controls.missile = true, menu_controls.next = true;
        if (platform.get_key(GLFW_KEY_F)) controls.flares = true;
        if (platform.get_key(GLFW_KEY_Q)) controls.change_weapon = true;
        if (platform.get_key(GLFW_KEY_E)) controls.change_target = true;
        if (platform.get_key(GLFW_KEY_R)) controls.change_radar = true;
        if (platform.get_key(GLFW_KEY_V)) controls.change_camera = true;

        if (platform.was_pressed(GLFW_KEY_ESCAPE)) menu_controls.prev = true;
        if (platform.was_pressed(GLFW_KEY_ENTER)) menu_controls.next = true;

        if (active_game_mode)
        {
            if (((pause && pause != last_pause) || platform.was_pressed(GLFW_KEY_P)) && !is_server && !is_client)
                scene.pause(paused = !paused);
            last_pause = pause;

            bool should_stop = platform.was_pressed(GLFW_KEY_ESCAPE);
            if (is_client && !client.is_up())
                should_stop = true;
            if (is_server && !server.is_up())
                should_stop = true;

            if (should_stop)
            {
                if (paused)
                    scene.pause(paused = !paused);
                active_game_mode->end();
                active_game_mode = 0;
                server.close();
                client.disconnect();
                world.set_network(0);
                sound_world.stop_sounds();
                menu_controls.prev = false;
                if (is_client)
                    menu.send_event("screen=mp_connect");

                sound_world.set_music("BGM_menu");
            }
        }

        speed10x = platform.get_key(GLFW_KEY_RIGHT_SHIFT) && !is_client && !is_server;

        if (controls.change_camera || (reset_camera && !controls.change_target))
        {
            scene.camera.reset_delta_rot();
            reset_camera = false;
        }

        if (!joysticks.empty() && !platform.get_mouse_lbtn() && !controls.change_target)
        {
            scene.camera.reset_delta_rot();
            scene.camera.add_delta_rot(-controls.cam_rot.x * nya_math::constants::pi_2, -controls.cam_rot.y * nya_math::constants::pi);
        }

        if (platform.was_pressed(GLFW_KEY_COMMA))
            debug_variable::set(debug_variable::get() - 1);
        if (platform.was_pressed(GLFW_KEY_PERIOD))
            debug_variable::set(debug_variable::get() + 1);

        if (!active_game_mode) //force limit 60 fps in menu
        {
            int sleep_time = 1000/60 - int(nya_system::get_time() - time);
            if (sleep_time > 0)
                std::this_thread::sleep_for(std::chrono::milliseconds(sleep_time));
        }
    }

    server.close();
    client.disconnect();
    sound::release_context();
    platform.terminate();

    return 0;
}
Ejemplo n.º 8
0
void Node2D::rotate(float p_degrees) {

	set_rot( get_rot() + p_degrees);
}
Ejemplo n.º 9
0
osg::Matrix CameraModel::get_rot_inv() const {
    osg::Matrix result;
    // OSG doesn't have a transpose matrix function?
    result.invert( get_rot() );
    return result;
}
Ejemplo n.º 10
0
void model_draw(const shader_t *s, GLuint utrans, GLuint uquats,
                const GLuint *texture, const uint32_t *mdl,
                int anim_id, double frame, const float *teamcolor,
                const float *color, uint16_t tex_over)
{
    /* assumes valid model data */
    uint8_t ngeo, teamcolor_end, nbone, nanim;
    const uint8_t *p, *tr, *qt;

    const chunkinfo_t *ck;
    const anim_t *anim;
    const bone_t *b;
    vec3 trans, ptrans;
    vec4 rot, prot;
    int vis, i, offset, tex;

    vec3 rtrans[maxbones];
    vec4 rotation[maxbones];

    /* parse header */
    p = (const uint8_t*)mdl;
    ngeo = p[0];
    teamcolor_end = p[1];
    nbone = p[2];
    nanim = p[3];

    anim = (const anim_t*)&p[4];
    ck = (const chunkinfo_t*)&anim[nanim];
    p = (const uint8_t*)&ck[ngeo];
    anim += anim_id;

    vis = anim->vis;
    frame = frame * anim->frames;

    /* calculate transformations for frame */
    i = 0;
    do {
        b = (const bone_t*)p;
        tr = (const uint8_t*)&b[1];
        qt = tr + nanim;
        p = qt + nanim;
        p = align4(p);

        get_trans(&trans, p, tr, anim_id, frame);
        p += b->keyframes[0] * sizeof(keyframe_t);

        get_rot(&rot, p, qt, anim_id, frame);
        p += b->keyframes[1] * sizeof(keyframe4_t);

        if(b->parent < 0) {
            ptrans = vec3(0.0, 0.0, 0.0);
            prot = vec4(0.0, 0.0, 0.0, 1.0);
        } else {
            ptrans = rtrans[b->parent];
            prot = rotation[b->parent];
        }

        rotation[i] = mul4(rot, prot);
        trans = add3(ptrans, qrot3(add3(b->pivot, trans), prot));
        rtrans[i] = add3(qrot3(neg3(b->pivot), rotation[i]), trans);
    } while (++i < nbone);

    /* load transformations */
    glUniform4fv(uquats, nbone, (float*)rotation);
    glUniform3fv(utrans, nbone, (float*)rtrans);

    //GLuint test;
    //glGenBuffers(1, &test);
    //
    //glBufferData(GL_ELEMENT_ARRAY_BUFFER, ck[ngeo - 1].index, indices, GL_STATIC_DRAW);

    /* draw visible vertices */
    i = 0;
    offset = 0;
    tex = 0xFFFF;
    glUniform4fv(s->k, 1, teamcolor);
    glUniform4fv(s->samp, 1, color);
    do {
        if(i == teamcolor_end)
            glUniform4fv(s->k, 1, transparency);

        if((vis & (1 << i))) {
            if (tex_over != 0xFFFF) {
                glBindTexture(GL_TEXTURE_2D, tex_over == 0xFFFE ? 0 : texture[tex_over]);
            } else if (ck[i].texture != tex) {
                tex = ck[i].texture;
                glBindTexture(GL_TEXTURE_2D, texture[tex]);
            }

            glDrawElements(GL_TRIANGLES, ck[i].index - offset, GL_UNSIGNED_SHORT, (void*)(size_t)offset);
        }
        offset = ck[i].index;
    } while(++i != ngeo);

    //glDeleteBuffers(1, &test);
}
Ejemplo n.º 11
0
/* todo: implement this correctly */
vec3 model_gettrans(const uint32_t *mdl, int anim_id, double frame, int bone)
{
    uint8_t ngeo, nbone, nanim;
    const uint8_t *p, *tr, *qt;

    const chunkinfo_t *ck;
    const anim_t *anim;
    const bone_t *b;
    vec3 trans, ptrans;
    vec4 rot, prot;
    int i;

    vec3 translation[maxbones];
    vec3 rtrans[maxbones];
    vec4 rotation[maxbones];

    if (bone == 0xFF)
        return vec3(0.0, 0.0, 0.0);

    /* parse header */
    p = (const uint8_t*)mdl;
    ngeo = p[0];
    nbone = p[2];
    nanim = p[3];

    anim = (const anim_t*)&p[4];
    ck = (const chunkinfo_t*)&anim[nanim];
    p = (const uint8_t*)&ck[ngeo];
    anim += anim_id;

    frame = frame * anim->frames;

    /* calculate transformations for frame */
    i = 0;
    do {
        b = (const bone_t*)p;
        tr = (const uint8_t*)&b[1];
        qt = tr + nanim;
        p = qt + nanim;
        if(nanim & 1) { /* alignment */
            p += 2;
        }

        get_trans(&trans, p, tr, anim_id, frame);
        p += b->keyframes[0] * sizeof(keyframe_t);

        get_rot(&rot, p, qt, anim_id, frame);
        p += b->keyframes[1] * sizeof(keyframe4_t);

        if(b->parent < 0) {
            ptrans = vec3(0.0, 0.0, 0.0);
            prot = vec4(0.0, 0.0, 0.0, 1.0);
        } else {
            ptrans = rtrans[b->parent];
            prot = rotation[b->parent];
        }

        rotation[i] = mul4(rot, prot);
        translation[i] = add3(ptrans, qrot3(add3(b->pivot, trans), prot));
        rtrans[i] = add3(qrot3(neg3(b->pivot), rotation[i]), translation[i]);

        if (i == bone)
            return translation[i];

    } while(++i < nbone);

    return vec3(0.0, 0.0, 0.0);
}