X-Git-Url: http://git.tdb.fi/?a=blobdiff_plain;f=source%2F3d%2Foverlay.cpp;h=2a26915a6e5fce5288254ac8b9d3af907bac7f5b;hb=9b8a32cf7371bc5fae8ce239a212469511c459e6;hp=bc206f987ac6c930275edbce4c9700e29dc1896d;hpb=02c9a9779954d993cb73fe5f7a72b0847e87f633;p=r2c2.git diff --git a/source/3d/overlay.cpp b/source/3d/overlay.cpp index bc206f9..2a26915 100644 --- a/source/3d/overlay.cpp +++ b/source/3d/overlay.cpp @@ -1,15 +1,11 @@ -/* $Id$ - -This file is part of the MSP Märklin suite -Copyright © 2010 Mikkosoft Productions, Mikko Rasa -Distributed under the GPL -*/ - #include #include #include +#include +#include #include -#include +#include +#include #include #include "overlay.h" #include "track.h" @@ -18,11 +14,9 @@ Distributed under the GPL using namespace std; using namespace Msp; -namespace Marklin { +namespace R2C2 { -Overlay3D::Overlay3D(const Graphics::Window &w, const GL::Camera &c, const GL::Font &f): - window(w), - camera(c), +Overlay3D::Overlay3D(const GL::Font &f): font(f) { } @@ -30,17 +24,17 @@ Overlay3D::~Overlay3D() { for(map::iterator i=graphics.begin(); i!=graphics.end(); ++i) delete i->second; - for(map::iterator i=icons.begin(); i!=icons.end(); ++i) + for(map::iterator i=icons.begin(); i!=icons.end(); ++i) delete i->second; } -void Overlay3D::set_label(const Track3D &track, const string &label) +void Overlay3D::set_label(const Object3D &track, const string &label) { get_icon(track).label = label; update_icon(get_icon(track)); } -void Overlay3D::add_graphic(const Track3D &track, const string &grf_name) +void Overlay3D::add_graphic(const Object3D &track, const string &grf_name) { const GL::Mesh *grf = get_graphic(grf_name); if(!grf) @@ -53,7 +47,7 @@ void Overlay3D::add_graphic(const Track3D &track, const string &grf_name) update_icon(icon); } -void Overlay3D::remove_graphic(const Track3D &track, const string &grf_name) +void Overlay3D::remove_graphic(const Object3D &track, const string &grf_name) { const GL::Mesh *grf = get_graphic(grf_name); Icon &icon = get_icon(track); @@ -62,15 +56,15 @@ void Overlay3D::remove_graphic(const Track3D &track, const string &grf_name) update_icon(icon); } -void Overlay3D::clear_graphics(const Track3D &track) +void Overlay3D::clear_graphics(const Object3D &track) { get_icon(track).graphics.clear(); update_icon(get_icon(track)); } -void Overlay3D::clear(const Track3D &track) +void Overlay3D::clear(const Object3D &track) { - map::iterator i = icons.find(&track); + map::iterator i = icons.find(&track); if(i!=icons.end()) { delete i->second; @@ -78,68 +72,55 @@ void Overlay3D::clear(const Track3D &track) } } -void Overlay3D::render(const GL::Tag &tag) const +void Overlay3D::render(GL::Renderer &renderer, const GL::Tag &) const { - if(tag==0) + unsigned fb_width = GL::Framebuffer::current()->get_width(); + unsigned fb_height = GL::Framebuffer::current()->get_height(); + + GL::Renderer::Push push(renderer); + GL::MatrixStack::Push push_proj(GL::MatrixStack::projection()); + + GL::MatrixStack::projection() = GL::Matrix::scaling(2.0/fb_width, 2.0/fb_height, 1.0); + + glLineWidth(1); + + int size = int(font.get_native_size()+0.5); + float spacing = round(size*1.1)/size; + float baseline = round((0.5-font.get_ascent()*0.5-font.get_descent()*0.5)*size)/size; + + for(map::const_iterator i=icons.begin(); i!=icons.end(); ++i) { - GL::matrix_mode(GL::PROJECTION); - GL::push_matrix(); - GL::load_identity(); - GL::scale(2.0/window.get_width(), 2.0/window.get_height(), 1.0); - GL::matrix_mode(GL::MODELVIEW); - GL::push_matrix(); - GL::load_identity(); + if(!i->first->is_visible()) + continue; + + const Icon &icon = *i->second; - glLineWidth(1); + GL::Vector3 p = renderer.get_camera()->project(i->first->get_node()); + p.x = int(p.x*0.5*fb_width-icon.width*size/2); + p.y = int(p.y*0.5*fb_height); - int size = int(font.get_default_size()+0.5); - float spacing = round(size*1.1)/size; - float baseline = round((0.5-font.get_ascent()*0.5-font.get_descent()*0.5)*size)/size; + GL::Renderer::Push push2(renderer); + renderer.matrix_stack() = GL::Matrix::translation(p); + renderer.matrix_stack() *= GL::Matrix::scaling(size); - for(map::const_iterator i=icons.begin(); i!=icons.end(); ++i) + icon.background.draw(renderer); + + glColor3f(0.0, 1.0, 0.0); + for(vector::const_iterator j=icon.graphics.begin(); j!=icon.graphics.end(); ++j) { - const Icon &icon = *i->second; - - const Point &pos = i->first->get_track().get_position(); - Point minp; - Point maxp; - i->first->get_type().get_bounds(0, minp, maxp); - float rot = i->first->get_track().get_rotation(); - float c = cos(rot); - float s = sin(rot); - - GL::Vector3 p((minp.x+maxp.x)/2, (minp.y+maxp.y)/2, 0); - p = GL::Vector3(pos.x+c*p.x-s*p.y, pos.y+s*p.x+c*p.y, pos.z+0.02); - p = camera.project(p); - - GL::PushMatrix push_mat; - p.x = int(p.x*0.5*window.get_width()-icon.width*size/2); - p.y = int(p.y*0.5*window.get_height()); - GL::translate(p.x, p.y, p.z); - GL::scale_uniform(size); - - icon.background.draw(); - - glColor3f(0.0, 1.0, 0.0); - for(vector::const_iterator j=icon.graphics.begin(); j!=icon.graphics.end(); ++j) - { - (*j)->draw(); - GL::translate(spacing, 0, 0); - } - - GL::translate(0, baseline, 0); - font.draw_string(icon.label); - GL::Texture::unbind(); + (*j)->draw(renderer); + renderer.matrix_stack() *= GL::Matrix::translation(spacing, 0, 0); } - GL::matrix_mode(GL::PROJECTION); - GL::pop_matrix(); - GL::matrix_mode(GL::MODELVIEW); - GL::pop_matrix(); + renderer.matrix_stack() *= GL::Matrix::translation(0, baseline, 0); + renderer.set_texture(&font.get_texture()); + icon.text.draw(renderer); } + + glColor3f(1.0, 1.0, 1.0); } -Overlay3D::Icon &Overlay3D::get_icon(const Track3D &track) +Overlay3D::Icon &Overlay3D::get_icon(const Object3D &track) { Icon *&icon = icons[&track]; if(!icon) @@ -158,7 +139,7 @@ const GL::Mesh *Overlay3D::get_graphic(const string &name) { DataFile::load(*grf, (FS::Path("icons")/(name+".mesh")).str()); } - catch(const Exception &e) + catch(const exception &e) { IO::print("Error loading overlay graphic '%s': %s\n", name, e.what()); delete grf; @@ -175,30 +156,41 @@ void Overlay3D::update_icon(Icon &icon) icon.width = max(icon.graphics.size()*1.1+font.get_string_width(icon.label), 1.0); - GL::MeshBuilder bld(icon.background); - bld.color(0.2f, 0.2f, 0.2f, 0.7f); - - bld.begin(GL::TRIANGLE_FAN); - bld.vertex(0.4, 0.5); - bld.vertex(icon.width-0.4, 0.5); - bld.vertex(icon.width-0.4, 1.2); - for(int i=4; i<=12; ++i) - bld.vertex(0.4+cos(i*M_PI/8)*0.7, 0.5+sin(i*M_PI/8)*0.7); - bld.end(); - - bld.begin(GL::TRIANGLE_FAN); - bld.vertex(icon.width-0.4, 0.5); - bld.vertex(0.4, 0.5); - bld.vertex(0.4, -0.2); - for(int i=-4; i<=4; ++i) - bld.vertex(icon.width-0.4+cos(i*M_PI/8)*0.7, 0.5+sin(i*M_PI/8)*0.7); - bld.end(); + { + GL::MeshBuilder bld(icon.background); + bld.color(0.05f, 0.05f, 0.05f, 0.7f); + + bld.begin(GL::TRIANGLE_FAN); + bld.vertex(0.4, 0.5); + bld.vertex(icon.width-0.4, 0.5); + bld.vertex(icon.width-0.4, 1.2); + for(int i=4; i<=12; ++i) + bld.vertex(0.4+cos(i*M_PI/8)*0.7, 0.5+sin(i*M_PI/8)*0.7); + bld.end(); + + bld.begin(GL::TRIANGLE_FAN); + bld.vertex(icon.width-0.4, 0.5); + bld.vertex(0.4, 0.5); + bld.vertex(0.4, -0.2); + for(int i=-4; i<=4; ++i) + bld.vertex(icon.width-0.4+cos(i*M_PI/8)*0.7, 0.5+sin(i*M_PI/8)*0.7); + bld.end(); + } + + icon.text.clear(); + + { + GL::MeshBuilder bld(icon.text); + bld.color(0.0f, 1.0f, 0.0f); + font.build_string(icon.label, bld); + } } Overlay3D::Icon::Icon(): width(1.0), - background((GL::COLOR4_UBYTE, GL::VERTEX2)) + background((GL::COLOR4_UBYTE, GL::VERTEX2)), + text((GL::COLOR4_UBYTE, GL::TEXCOORD2, GL::VERTEX2)) { } -} // namespace Marklin +} // namespace R2C2