root/OpenSceneGraph/trunk/src/osgSim/LineOfSight.cpp @ 13041

Revision 13041, 5.4 kB (checked in by robert, 3 years ago)

Ran script to remove trailing spaces and tabs

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2006 Robert Osfield
2 *
3 * This library is open source and may be redistributed and/or modified under
4 * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
5 * (at your option) any later version.  The full license is in LICENSE file
6 * included with this distribution, and on the openscenegraph.org website.
7 *
8 * This library is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 * OpenSceneGraph Public License for more details.
12*/
13
14#include <osgSim/LineOfSight>
15
16#include <osg/Notify>
17#include <osgDB/ReadFile>
18#include <osgUtil/LineSegmentIntersector>
19
20using namespace osgSim;
21
22DatabaseCacheReadCallback::DatabaseCacheReadCallback()
23{
24    _maxNumFilesToCache = 2000;
25}
26
27void DatabaseCacheReadCallback::clearDatabaseCache()
28{
29    OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_mutex);
30    _filenameSceneMap.clear();
31}
32
33void DatabaseCacheReadCallback::pruneUnusedDatabaseCache()
34{
35}
36
37osg::Node* DatabaseCacheReadCallback::readNodeFile(const std::string& filename)
38{
39    // first check to see if file is already loaded.
40    {
41        OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_mutex);
42
43        FileNameSceneMap::iterator itr = _filenameSceneMap.find(filename);
44        if (itr != _filenameSceneMap.end())
45        {
46            OSG_INFO<<"Getting from cache "<<filename<<std::endl;
47
48            return itr->second.get();
49        }
50    }
51
52    // now load the file.
53    osg::ref_ptr<osg::Node> node = osgDB::readNodeFile(filename);
54
55    // insert into the cache.
56    if (node.valid())
57    {
58        OpenThreads::ScopedLock<OpenThreads::Mutex> lock(_mutex);
59
60        if (_filenameSceneMap.size() < _maxNumFilesToCache)
61        {
62            OSG_INFO<<"Inserting into cache "<<filename<<std::endl;
63
64            _filenameSceneMap[filename] = node;
65        }
66        else
67        {
68            // for time being implement a crude search for a candidate to chuck out from the cache.
69            for(FileNameSceneMap::iterator itr = _filenameSceneMap.begin();
70                itr != _filenameSceneMap.end();
71                ++itr)
72            {
73                if (itr->second->referenceCount()==1)
74                {
75                    OSG_NOTICE<<"Erasing "<<itr->first<<std::endl;
76                    // found a node which is only referenced in the cache so we can discard it
77                    // and know that the actual memory will be released.
78                    _filenameSceneMap.erase(itr);
79                    break;
80                }
81            }
82            OSG_INFO<<"And the replacing with "<<filename<<std::endl;
83            _filenameSceneMap[filename] = node;
84        }
85    }
86
87    return node.release();
88}
89
90LineOfSight::LineOfSight()
91{
92    setDatabaseCacheReadCallback(new DatabaseCacheReadCallback);
93}
94
95void LineOfSight::clear()
96{
97    _LOSList.clear();
98}
99
100unsigned int LineOfSight::addLOS(const osg::Vec3d& start, const osg::Vec3d& end)
101{
102    unsigned int index = _LOSList.size();
103    _LOSList.push_back(LOS(start,end));
104    return index;
105}
106
107void LineOfSight::computeIntersections(osg::Node* scene, osg::Node::NodeMask traversalMask)
108{
109    osg::ref_ptr<osgUtil::IntersectorGroup> intersectorGroup = new osgUtil::IntersectorGroup();
110
111    for(LOSList::iterator itr = _LOSList.begin();
112        itr != _LOSList.end();
113        ++itr)
114    {
115        osg::ref_ptr<osgUtil::LineSegmentIntersector> intersector = new osgUtil::LineSegmentIntersector(itr->_start, itr->_end);
116        intersectorGroup->addIntersector( intersector.get() );
117    }
118
119    _intersectionVisitor.reset();
120    _intersectionVisitor.setTraversalMask(traversalMask);
121    _intersectionVisitor.setIntersector( intersectorGroup.get() );
122
123    scene->accept(_intersectionVisitor);
124
125    unsigned int index = 0;
126    osgUtil::IntersectorGroup::Intersectors& intersectors = intersectorGroup->getIntersectors();
127    for(osgUtil::IntersectorGroup::Intersectors::iterator intersector_itr = intersectors.begin();
128        intersector_itr != intersectors.end();
129        ++intersector_itr, ++index)
130    {
131        osgUtil::LineSegmentIntersector* lsi = dynamic_cast<osgUtil::LineSegmentIntersector*>(intersector_itr->get());
132        if (lsi)
133        {
134            Intersections& intersectionsLOS = _LOSList[index]._intersections;
135            _LOSList[index]._intersections.clear();
136
137            osgUtil::LineSegmentIntersector::Intersections& intersections = lsi->getIntersections();
138
139            for(osgUtil::LineSegmentIntersector::Intersections::iterator itr = intersections.begin();
140                itr != intersections.end();
141                ++itr)
142            {
143                const osgUtil::LineSegmentIntersector::Intersection& intersection = *itr;
144                if (intersection.matrix.valid()) intersectionsLOS.push_back( intersection.localIntersectionPoint * (*intersection.matrix) );
145                else intersectionsLOS.push_back( intersection.localIntersectionPoint  );
146            }
147        }
148    }
149
150}
151
152LineOfSight::Intersections LineOfSight::computeIntersections(osg::Node* scene, const osg::Vec3d& start, const osg::Vec3d& end, osg::Node::NodeMask traversalMask)
153{
154    LineOfSight los;
155    unsigned int index = los.addLOS(start,end);
156    los.computeIntersections(scene, traversalMask);
157    return los.getIntersections(index);
158}
159
160void LineOfSight::setDatabaseCacheReadCallback(DatabaseCacheReadCallback* dcrc)
161{
162    _dcrc = dcrc;
163    _intersectionVisitor.setReadCallback(dcrc);
164}
Note: See TracBrowser for help on using the browser.