Exemplo n.º 1
0
    SettingsMap* ConfigManager::GetSection(const Urho3D::String& section, bool create)
    {
        // Empty section gets assigned to main map
        if (section == Urho3D::String::EMPTY)
            return &_map;

        // Split section into submaps
        Urho3D::Vector<Urho3D::String> split;

        unsigned splitPos = 0;

        if (ConfigFile::ParseHeader(section).Empty())
        {
            return &_map;
        }

        // Split sections by '.' or '/'
        // Comments will ignore splits behind them
        while (splitPos != Urho3D::String::NPOS)
        {
            // Find next comment split
            auto commentSplitPos = splitPos;
            auto hashPos = section.Find("#", commentSplitPos);
            auto slashesPos = section.Find("//", commentSplitPos);
            commentSplitPos = (hashPos < slashesPos) ? hashPos : slashesPos;

            // Find next split
            auto lastSplitPos = splitPos;
            auto dotPos = section.Find(".", lastSplitPos);
            auto slashPos = section.Find("/", lastSplitPos);
            splitPos = (dotPos < slashPos) ? dotPos : slashPos;

            // Ignore splits after comments
            splitPos = (commentSplitPos <= splitPos) ? Urho3D::String::NPOS : splitPos;

            int length = splitPos - lastSplitPos;
            if (splitPos == Urho3D::String::NPOS)
            {
                length = section.Length() - lastSplitPos;
            }
            
            auto sub = section.Substring(lastSplitPos, length);

            if (sub != Urho3D::String::EMPTY)
                split.Push(sub);
        }

        SettingsMap* currentMap = &_map;
        for (auto itr = split.Begin(); itr != split.End(); itr++)
        {
            auto section = *itr;

            // Find section
            SettingsMap* newMap = 0;
            for (auto map_itr = currentMap->Begin(); map_itr != currentMap->End(); map_itr++)
            {
                if (map_itr->first_ == section)
                {
                    newMap = static_cast<SettingsMap*>(map_itr->second_.GetVoidPtr());

                    // Key exists, but is not a SettingsMap
                    if (!newMap)
                    {
                        return 0;
                    }

                    // Key exists
                    break;
                }
            }

            // Key does not exist
            if (!newMap)
            {
                if (create)
                {
                    currentMap->operator[](section) = new SettingsMap();
                    newMap = static_cast<SettingsMap*>((*currentMap)[section].GetVoidPtr());
                }
            }

            if (newMap)
            {
                currentMap = newMap;
            }
        }

        return currentMap;
    }
Exemplo n.º 2
0
// ----------------------------------------------------------------------------
void Hull::SetMesh(Polyhedron* polyhedron)
{
    faces_.Clear();
    edges_.Clear();
    hullMesh_ = polyhedron;

    if(hullMesh_->FaceCount() == 0)
        return;

    Urho3D::Vector<Urho3D::Vector3> trianglePositions;

    Polyhedron::ConstIterator vertexIt = hullMesh_->Begin();
    while(vertexIt != hullMesh_->End())
    {
        Vertex* v0 = *vertexIt++;
        Vertex* v1 = *vertexIt++;
        Vertex* v2 = *vertexIt++;

        // Accumulate positions of triangle centres for average position
        trianglePositions.Push(
            (v0->position_ + v1->position_ + v2->position_) / 3.0f
        );

        // Add face
        faces_.Push(Face(v0, v1, v2));
    }

    // Average triangle centres to get centre of hull
    centre_ = Urho3D::Vector3::ZERO;
    for(Urho3D::Vector<Urho3D::Vector3>::ConstIterator it = trianglePositions.Begin();
        it != trianglePositions.End();
        ++it)
    {
        centre_ += *it;
    }
    centre_ /= trianglePositions.Size();

    // Make sure each triangle's normal vector is pointing away from centre of
    // the hull
    for(Urho3D::Vector<Face>::Iterator it = faces_.Begin();
        it != faces_.End();
        ++it)
    {
        Urho3D::Vector3 outwards = it->GetVertex(0)->position_ - centre_;
        if(outwards.DotProduct(it->GetNormal()) < 0)
            it->FlipNormal();
    }

    // With the centre and normals calculated, we can use that information to
    // construct edges. Each edge stores the normal vectors of both triangles
    // it joins in order to calculate if a projected point is projected from
    // the correct angle or not.
    //
    // We iterate the polyhedron and the triangles list simultaneously, because
    // it is more efficient to check for joined edges using the polyhedron data
    // structure than the triangles list. The triangles list is required to get
    // the calculated and adjusted normals.
    vertexIt = hullMesh_->Begin();
    Urho3D::Vector<Face>::ConstIterator triangleIt = faces_.Begin();
    for(; vertexIt != hullMesh_->End(); triangleIt++)
    {
        Vertex* vertex[3];
        vertex[0] = *vertexIt++;
        vertex[1] = *vertexIt++;
        vertex[2] = *vertexIt++;

        // find the three adjacent triangles
        Urho3D::Vector<Face>::ConstIterator triangleIt2 = faces_.Begin();
        Polyhedron::ConstIterator vertexIt2 = hullMesh_->Begin();
        for(; vertexIt2 != hullMesh_->End(); triangleIt2++)
        {
            Vertex* vertex2[3];
            vertex2[0] = *vertexIt2++;
            vertex2[1] = *vertexIt2++;
            vertex2[2] = *vertexIt2++;

            // skip self
            if(vertexIt == vertexIt2)
                continue;

            // joined[2] will contain two Vertex objects if we find an edge
            // that is shared between the two current triangles.
            Vertex* joined[2];
            Vertex** joinedPtr = joined;
            for(unsigned char i = 0; i != 3; ++i)
                for(unsigned char j = 0; j != 3; ++j)
                    if(vertex[i] == vertex2[j])
                        *joinedPtr++ = vertex[i];

            // Calculate number of vertices that were found joined.
            unsigned joinedCount = joinedPtr - joined;
            assert(joinedCount != 3);
            if(joinedCount != 2)
                continue;

            // Found a joined edge, add it
            edges_.Push(Edge(
                joined[0],
                joined[1],
                triangleIt->GetNormal(),
                triangleIt2->GetNormal()
            ));

            // Make sure edge boundary check points outwards from the hull's
            // centre
            Urho3D::Vector2 bary = edges_.Back().ProjectAndTransformToBarycentric(centre_);
            if(edges_.Back().ProjectionAngleIsInBounds(edges_.Back().TransformToCartesian(bary), centre_))
                edges_.Back().FlipBoundaryCheck();
        }
    }
}