Blame simulator.cpp

57bda0
57bda0
#include <iostream></iostream>
57bda0
57bda0
#include <gl gl.h=""></gl>
57bda0
57bda0
#include "simulator.h"
57bda0
57bda0
57bda0
void SimulatorXYZA::simulate(const Track &track, Real tool_radius) {
57bda0
    points.clear();
57bda0
    simu_index = 0;
57bda0
    x0 = x1 = 0;
57bda0
57bda0
    if (!raster.get_data() || track.points.empty()) return;
57bda0
    
57bda0
    std::cout << "SimulatorXYZA::simulate" << std::endl;
57bda0
    
57bda0
    x0 = x1 = track.points.front().position.x;
57bda0
    Real max_radius = 0;
57bda0
    for(PointList::const_iterator i = track.points.begin(); i != track.points.end(); ++i) {
57bda0
        Real radius = sqrt(i->position.y*i->position.y + i->position.z*i->position.z);
57bda0
        if (max_radius < radius) max_radius = radius;
57bda0
        if (x0 > i->position.x) x0 = i->position.x;
57bda0
        if (x1 < i->position.x) x1 = i->position.x;
57bda0
    }
57bda0
    raster.fill(max_radius);
57bda0
    
57bda0
    if (x1 + 1e-5 < x0) {
57bda0
        std::cout << "SimulatorXYZA::simulate: zero bound" << std::endl;
57bda0
        return;
57bda0
    }
57bda0
    
57bda0
    Real h = raster.get_height();
57bda0
    Real kx = raster.get_width()/(x1 - x0);
57bda0
    Real ka = 1/360.0;
57bda0
    Real kr = h/(2*M_PI);
57bda0
57bda0
    Real dx = fabs(tool_radius*kx);
57bda0
    int index = 0;
57bda0
    for(PointList::const_iterator i = track.points.begin(); i != track.points.end(); ++i, ++index) {
57bda0
        Real radius = sqrt(i->position.y*i->position.y + i->position.z*i->position.z);
57bda0
        if (radius < 1e-5) radius = 1e-5;
57bda0
        Real dy = fabs(tool_radius/radius*kr);
57bda0
        
57bda0
        Real x = (i->position.x - x0)*kx;
57bda0
        Real y = i->angle*ka;
57bda0
        y = (y - floor(y))*h;
57bda0
57bda0
        raster.touch(index, radius, x, y, dx, dy, points);
57bda0
        if (y - dy < 0)
57bda0
            raster.touch(index, radius, x, y + h, dx, dy, points);
57bda0
        if (y + dy > h)
57bda0
            raster.touch(index, radius, x, y - h, dx, dy, points);
57bda0
        
57bda0
        if (index % 1000 == 0)
57bda0
            std::cout << "." << std::flush;
57bda0
        if (index % 100000 == 0)
57bda0
            std::cout << std::endl << std::flush;
57bda0
    }
57bda0
    simu_index = (int)points.size();
57bda0
57bda0
    std::cout << "SimulatorXYZA::simulate: done" << std::endl;
57bda0
}
57bda0
    
57bda0
void SimulatorXYZA::scroll_to(int index) {
57bda0
    while(simu_index < (int)points.size() && points[simu_index].index <= index)
57bda0
        points[simu_index++].apply_next(raster);
57bda0
    while(simu_index > 0 && points[simu_index-1].index > index)
57bda0
        points[--simu_index].apply_prev(raster);
57bda0
}
57bda0
    
57bda0
void SimulatorXYZA::draw() const {
57bda0
    int w = raster.get_width();
57bda0
    int h = raster.get_height();
57bda0
    if (w < 2 || h < 2) return;
57bda0
57bda0
    Vector3 v, v0, v1;
57bda0
    
57bda0
    Real kx = (x1 - x0)/w;
57bda0
    Real ka = 2*M_PI/h;
57bda0
57bda0
    glEnable(GL_LIGHTING);
57bda0
    
57bda0
    glColor4d(0, 0, 1, 0.5);
57bda0
    
57bda0
    glBegin(GL_TRIANGLE_STRIP);
57bda0
    for(int r = 0; r < h; ++r) {
57bda0
        int rr = r ? r-1 : h-1;
57bda0
        Real a0 = rr*ka;
57bda0
        Real a1 = r*ka;
57bda0
        Real s0 = sin(a0), s1 = sin(a1);
57bda0
        Real c0 = cos(a0), c1 = cos(a1);
57bda0
        for(int c = 0; c < w; ++c) {
57bda0
            v0.x = v1.x = x0 + c*kx;
57bda0
            Real r0 = raster[rr][c];
57bda0
            Real r1 = raster[r][c];
57bda0
            v0.y = -s0*r0, v0.z = c0*r0;
57bda0
            v1.y = -s1*r1, v1.z = c1*r1;
57bda0
            
57bda0
            Vector3 dv0(v0.x - v.x, v0.y - v.y, v0.z - v.z);
57bda0
            Vector3 dv1(v1.x - v.x, v1.y - v.y, v1.z - v.z);
57bda0
            Vector3 norm(
57bda0
                dv0.y*dv1.z - dv0.z*dv1.y,
57bda0
                dv0.z*dv1.x - dv0.x*dv1.z,
57bda0
                dv0.x*dv1.y - dv0.y*dv1.x );
57bda0
            Real l = sqrt(norm.x*norm.x + norm.y*norm.y + norm.z*norm.z);
57bda0
            l = l > 1e-5 ? 1/l : 0;
57bda0
            glNormal3d(norm.x*l, norm.y*l, norm.z*l);
57bda0
57bda0
            if (!c) glVertex3dv(v0.c);
57bda0
            glVertex3dv(v0.c);
57bda0
            glVertex3dv(v1.c);
57bda0
            v = v1;
57bda0
        }
57bda0
        glVertex3dv(v.c);
57bda0
    }
57bda0
    glEnd();
57bda0
57bda0
    glDisable(GL_LIGHTING);
57bda0
}