Пример #1
0
  void CRasterTerrainModel::Update(CErrorMetric const & metric, GLUtils::CViewFrustum const & frustum) 
  {
    InitGLResources();

    mActivePatches.clear();
    RecursiveUpdate(mRoot, metric, frustum);
  }
Пример #2
0
void dd::World::Update(double dt)
{
	for (auto pair : m_Systems)
	{
		const std::string &type = pair.first;
		auto system = pair.second;
		EventBroker->Process(type);
		system->Update(dt);
		RecursiveUpdate(system, dt, 0);
	}

	ProcessEntityRemovals();
}
void VertexCoordRemapper::UpdateAndResetIndex()
{
    DEBUG_DEBUG("mesh update update reset index");
    // this sets scale, height, and width.
    MeshRemapper::UpdateAndResetIndex();
    // we need to record the output projection for flipping around 180 degrees.
    output_projection = visualization_state->GetOptions()->getProjection();
    o_width = visualization_state->GetOptions()->getWidth();
    o_height = visualization_state->GetOptions()->getHeight();
    // we want to make a remapped mesh, get the transformation we need:
//    HuginBase::SrcPanoImage *src = visualization_state->GetSrcImage(image_number);
    transform.createInvTransform(*image, *(visualization_state->GetOptions()));
    // use the scale to determine edge lengths in pixels for subdivision
//    DEBUG_INFO("updating mesh for image " << image_number << ", using scale "
//              << scale << ".\n");
    // find key points used for +/- 180 degree boundary correction
    // {x|y}_add_360's are added to a value near the left/top boundary to get
    // the corresponding point over the right/bottom boundary.
    // other values are used to check where the boundary is.
    OutputProjectionInfo *info = visualization_state->GetProjectionInfo();
    x_add_360 = info->GetXAdd360();
    radius = info->GetRadius();
    y_add_360 = info->GetYAdd360();
    x_midpoint = info->GetMiddleX();
    y_midpoint = info->GetMiddleY();
    lower_bound = info->GetLowerX();
    upper_bound = info->GetUpperX();
    lower_bound_h = info->GetLowerY();
    upper_bound_h = info->GetUpperY();
    // Find the cropping region of the source image, so we can stick to the
    // bounding rectangle.
    SetCrop();
    // the tree needs to know how to use the croping information for generating
    tree.x_crop_scale = crop_x2 - crop_x1;
    tree.x_crop_offs = crop_x1;
    tree.y_crop_scale = crop_y2 - crop_y1;
    tree.y_crop_offs = crop_y1;
    // make the tree reflect the transformation
    RecursiveUpdate(0, 0, 0);
    // now set up for examining the tree contents.
    tree.ResetIndex();
    done_node = true;
}
Пример #4
0
  void CRasterTerrainModel::RecursiveUpdate(Patch * p, CErrorMetric const & metric, GLUtils::CViewFrustum const & frustum) 
  {
    p->tessLevel = 0;
    if (frustum.Intersects(p->bbmin, p->bbmax)) {
      if (metric.Evaluate(p->bbmin, p->bbmax, p->error) && !p->IsLeaf()) {

        for (glm::uint i=0; i < 4; ++i)
          if (p->childs[i])
            RecursiveUpdate(p->childs[i], metric, frustum);
      }
      else {
        p->Commit();
        p->ReleaseChilds();
        p->propagateTessLevel(0);
        mActivePatches.push_back(p);
      }
    }
    else {
      p->Release();
      p->ReleaseChilds();
    }
  }
void VertexCoordRemapper::RecursiveUpdate(unsigned int node_num,
                                   unsigned int stretch_x, unsigned stretch_y)
{
    // find where we are and what we are mapping
    // TODO? GetPosition is called by GetInputCoordinates, reuse results?
    unsigned int x, y, row_size, depth;
    tree.GetPosition(node_num, x, y, row_size, depth);
    tree.GetInputCoordinates(node_num, tex_coords);
    TreeNode *node = &tree.nodes[node_num],
             *parent = (depth) ?
                       &tree.nodes[tree.GetParentId(x, y, row_size, depth)] : 0,
             *left = (x % 2) ?
                        &tree.nodes[tree.GetIndex(x-1, y, row_size, depth)] : 0,
             *top = (y % 2) ?
                        &tree.nodes[tree.GetIndex(x, y-1, row_size, depth)] : 0;
    bool valid[2][2];
    for (unsigned short int i = 0; i < 2; i++)
    {
        for (unsigned short int j = 0; j < 2; j++)
        {
            if (depth == 0)
            {
                // the top level has no parent, so we must calculate all points
                valid[i][j] =
                      transform.transformImgCoord(node->verts[i][j][0],
                                                  node->verts[i][j][1],
                                                  tex_coords[i][j][0] * width,
                                                  tex_coords[i][j][1] * height);
            } else
            // Look up where the point in the tree so far. If this is the first
            // occurrence of this point, we'll calculate the value.
            if (i == x %2 && j == y%2 && depth)
            {
                // extract a corner from the parent.
                node->verts[i][j][0] = parent->verts[i][j][0];
                node->verts[i][j][1] = parent->verts[i][j][1];
                valid[i][j] = !(parent->flags & (transform_fail_flag << (j*2 +i)));
            } else if (x % 2 && !i) {
                // copy from the left
                node->verts[0][j][0] = left->verts[1][j][0];
                node->verts[0][j][1] = left->verts[1][j][1];
                valid[i][j] = !(left->flags & (transform_fail_flag << (j *2 + 1)));
            } else if (y % 2 && !j) {
                // copy from the top
                node->verts[i][0][0] = top->verts[i][1][0];
                node->verts[i][0][1] = top->verts[i][1][1];
                valid[i][j] = !(top->flags & (transform_fail_flag << (2 + i)));
            } else {
                // We can't find it easily, try a more expensive search.
                // this will linearly interpolate along the edges where the
                // subdivision was higher, avoiding gaps when the detail level
                // was lower above or to the left.
                if (!tree.GetTransform(x + i * (1 << stretch_x),
                                       y + j * (1 << stretch_y),
                                       depth, x, y, node->verts[i][j][0],
                                       node->verts[i][j][1]))
                {
                    // We can't find it, so calculate it:
                    valid[i][j] =
                      transform.transformImgCoord(node->verts[i][j][0],
                                                  node->verts[i][j][1],
                                                  tex_coords[i][j][0] * width,
                                                  tex_coords[i][j][1] * height);
                    // If the face results from a patch subdivision (for
                    // aligning a subdivided face, otherwise it need not exist),
                    // use the midpoint of the parent's vertices instead of
                    // calculating a transformed one, so we can use less
                    // subdivision on the other side.
                    // subdivision in x
                    // FIXME there are still gaps. I think there's a logic error
                    if (   depth // not on the top level.
                        // patching in y
                        && (parent->flags & patch_flag_x)
                        // we must be in the middle of the split, the nodes on
                        // the corners of the parent line up anyway.
                        && ((i + x) % 2)
                        // we should be on the side away from the subdivison
                        // (+ve y).
                        && j
                        // If we are alao split in y we can use the middle
                        // node to provide more detail.
                        && (!((parent->flags & split_flag_y) && !(y % 2)))
                        // don't do this if we cross the 180 degree seam
                        && (!(parent->flags & (vertex_side_flag_start * 15))))
                    {
                        node->verts[i][1][0] = (parent->verts[0][1][0]
                                               + parent->verts[1][1][0]) / 2.0;
                        node->verts[i][1][1] = (parent->verts[0][1][1]
                                               + parent->verts[1][1][1]) / 2.0;
                    }
                    // subdivision in y
                    if (   depth
                        && (parent->flags & patch_flag_y)
                        && ((j + y) % 2)
                        && i
                        && (!((parent->flags & split_flag_x) && !(x % 2)))
                        && (!(parent->flags & (vertex_side_flag_start * 15))))
                    {
                        node->verts[1][j][0] = (parent->verts[1][0][0]
                                               + parent->verts[1][1][0]) / 2.0;
                        node->verts[1][j][1] = (parent->verts[1][0][1]
                                               + parent->verts[1][1][1]) / 2.0;
                    }
                } else {
                    // we managed to find it from data already known.
                    valid[i][j] = true;
                }
            }
        }
    }
    
    // now for the recursion
    // which directions should we divide in?
    TestSubdivide(node_num);
    // add the flags for invlaid transormations
    for (unsigned int i = 0; i < 2; i++)
    {
        for (unsigned int j = 0; j < 2; j++)
        {
            if (!valid[i][j])
            {
                node->flags |= transform_fail_flag << (j * 2 + i);
            }
        }
    }
    // if the face should be split, now recurse to the child nodes.
    if (node->flags & (split_flag_x | split_flag_y))
    {
        // we will split at least one way.
        if (!(node->flags & split_flag_x))
        {
            // we are not splitting across x, but will will across y.
            // so the quad will be twice as wide
            stretch_x++;
        }
        else if (!(node->flags & split_flag_y))
        {
            stretch_y++;
        }
        // find the top left sub-quad
        x *= 2;
        y *= 2;
        row_size *= 2;
        depth++;
        // the top left is always generated
        RecursiveUpdate(tree.GetIndex(x, y, row_size, depth),
                        stretch_x, stretch_y);
        // split in x
        if (node->flags & split_flag_x)
        {
            RecursiveUpdate(tree.GetIndex(x + 1, y, row_size, depth),
                            stretch_x, stretch_y);
        }
        // split in y
        if (node->flags & split_flag_y)
        {
            RecursiveUpdate(tree.GetIndex(x, y + 1, row_size, depth),
                            stretch_x, stretch_y);
            // if we are splitting in both directions, do the lower right corner
            if (node->flags & split_flag_x)
            {
                RecursiveUpdate(tree.GetIndex(x + 1, y + 1, row_size, depth),
                    stretch_x, stretch_y);
            }
        }
    }
}