osgDB::ReaderWriter::ReadResult readNodeFromArchive(osgDB::Archive& archive, const osgDB::ReaderWriter::Options* options) const
        {
            osgDB::ReaderWriter::ReadResult result(osgDB::ReaderWriter::ReadResult::FILE_NOT_FOUND);

            if (!archive.getMasterFileName().empty())
            {
                result = archive.readNode(archive.getMasterFileName(), options);
            }
            else
            {
                osgDB::Archive::FileNameList fileNameList;
                if (archive.getFileNames(fileNameList))
                {
                    typedef std::list< osg::ref_ptr<osg::Node> > Nodes;
                    Nodes nodes;
                    for(osgDB::Archive::FileNameList::iterator itr = fileNameList.begin();
                        itr != fileNameList.end();
                        ++itr)
                    {
                        result = archive.readNode(*itr, options);
                        if (result.validNode()) nodes.push_back(result.getNode());
                    }

                    if (!nodes.empty())
                    {
                        if (nodes.size()==1)
                        {
                            result = osgDB::ReaderWriter::ReadResult(nodes.front().get());
                        }
                        else
                        {
                            osg::ref_ptr<osg::Group> group = new osg::Group;
                            for(Nodes::iterator itr = nodes.begin();
                                itr != nodes.end();
                                ++itr)
                            {
                                group->addChild(itr->get());
                            }
                            result = osgDB::ReaderWriter::ReadResult(group.get());
                        }
                    }
                }
            }
            return result;
        }
示例#2
0
void Evaluator::subst_macros()
{
    int cntr = 0;
    Token gtok(0, 0);
    while (1)
    {
        if (++cntr > MAX_SUBST)
            throw Err("Too many macro substitutions: " + bug::to_string(MAX_SUBST) + ", possible recursion", gtok);

        bool weresubs = false;

        Nodes old = root->children;
        root->children.clear();

        Nodes leftovers;
        for (auto i : old)
        {
            Instruction * pin = get<Instruction>(NOTHR, i);
            if (pin)
            {
                for (auto j : leftovers)
                    i->children[0]->children[1]->children.push_back(j);

                leftovers.clear();

                root->addChild(i);
                continue;
            }

            Macuse * u = get<Macuse>(LNFUN, i);
            gtok = u->tok();

            if (u->name() == "@end")
            {
                for (auto j : u->children[0]->children)
                    leftovers.push_back(j);
                continue;
            }

            Nodes inject = Macros(root).process_macuse(*u);

            if (!inject.empty())
            {
                Pnode pn = inject.front();
                Instruction * pin = get<Instruction>(NOTHR, pn);
                if (pin)
                {
                    for (auto j : leftovers)
                        pn->children[0]->children[1]->children.push_back(j);
                }
                else
                {
                    Macuse * pu = get<Macuse>(LNFUN, pn);
                    for (auto j : leftovers)
                        pu->children[0]->children.push_back(j);
                }

                leftovers.clear();
            }

            for (auto j : inject)
                root->addChild(j);

            weresubs = true;
        }

        if (!weresubs)
        {
            if (leftovers.empty())
                break;

            if (root->children.empty())
                throw Err("Labels used in empty program");

            throw Err("Program finishes with label (see macro definition)", root->children.back()->tok());
        }
        // this can be improved later (one extra loop)
        // when expanding macro we can detect that no new macro introduced
    } // while
}