]> git.mxchange.org Git - simgear.git/blob - simgear/scene/tgdb/ShaderGeometry.cxx
Make sure the boundingvolumes for the btg files are as high as possible
[simgear.git] / simgear / scene / tgdb / ShaderGeometry.cxx
1 /* -*-c++-*-
2  *
3  * Copyright (C) 2008 Stuart Buchanan
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License as
7  * published by the Free Software Foundation; either version 2 of the
8  * License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful, but
11  * WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
18  * MA 02110-1301, USA.
19  *
20  */
21
22 #include <osgDB/Registry>
23 #include <osgDB/Input>
24 #include <osgDB/ParameterOutput>
25
26 #include "ShaderGeometry.hxx"
27
28 #include <algorithm>
29
30 using namespace osg;
31 using namespace osgDB;
32
33 namespace simgear
34 {
35 void ShaderGeometry::addTree(const TreeBin::Tree& t)
36 {
37     if (!_posScaleArray.valid()) {
38         _posScaleArray = new Vec4Array();
39         _vertexAttribArray = new FloatArray();
40     }
41     _posScaleArray->push_back(Vec4(t.position.osg(), t.scale));
42     _vertexAttribArray->push_back((float)t.texture_index / varieties);
43     dirtyBound();
44 }
45
46 void ShaderGeometry::drawImplementation(osg::RenderInfo& renderInfo) const
47 {
48     State& state = *renderInfo.getState();
49     const Extensions* extensions = getExtensions(state.getContextID(), true);
50     Vec4Array::const_iterator citer = _posScaleArray->begin();
51     Vec4Array::const_iterator cend = _posScaleArray->end();
52     FloatArray::const_iterator viter = _vertexAttribArray->begin();
53     for (; citer != cend; ++citer, ++viter) {
54         const Vec4& color = *citer;
55         const float attrib = *viter;
56         glColor4fv(color.ptr());
57         extensions->glVertexAttrib1f(1, attrib);
58         _geometry->draw(renderInfo);
59     }
60 }
61
62 BoundingBox ShaderGeometry::computeBound() const
63 {
64     const BoundingBox& geom_box = _geometry->getBound();
65     BoundingBox bb;
66     const Vec4Array* posScales = _posScaleArray.get();
67     if (!posScales)
68         return bb;
69     size_t numPosScales = posScales->size();
70     for (Vec4Array::const_iterator iter = _posScaleArray->begin(),
71              e = _posScaleArray->end();
72          iter != e;
73          ++iter) {
74         const Vec4& posScale = *iter;
75         const float scale = posScale.w();
76         const Vec3 pos(posScale.x(), posScale.y(), posScale.z());
77         for (unsigned j = 0; j < 7; ++j)
78             bb.expandBy(geom_box.corner(j) * scale + pos);
79     }
80     return bb;
81 }
82
83 bool ShaderGeometry_readLocalData(Object& obj, Input& fr)
84 {
85     bool iteratorAdvanced = false;
86
87     ShaderGeometry& geom = static_cast<ShaderGeometry&>(obj);
88
89     if ((fr[0].matchWord("geometry"))) {
90         ++fr;
91         iteratorAdvanced = true;
92         osg::Geometry* drawable = dynamic_cast<osg::Geometry*>(fr.readDrawable());
93         if (drawable) {
94             geom._geometry = drawable;
95         }
96     }
97     int capacity = 0;
98     if (fr.matchSequence("posScale %i {")) {
99         int entry = fr[1].getNoNestedBrackets();
100         int capacity;
101         fr[1].getInt(capacity);
102         Vec4Array* posScale = new Vec4Array;
103         posScale->reserve(capacity);
104         fr += 3;
105         while (!fr.eof() && fr[0].getNoNestedBrackets() > entry) {
106             Vec4 v;
107             if (fr[0].getFloat(v.x()) && fr[1].getFloat(v.y())
108                 && fr[2].getFloat(v.z()) && fr[3].getFloat(v.w())) {
109                 fr += 4;
110                 posScale->push_back(v);
111             }
112             else ++fr;
113         }
114         ++fr;
115         geom._posScaleArray = posScale;
116     }
117     if (fr.matchSequence("variety %i {")) {
118         int entry = fr[1].getNoNestedBrackets();
119         int capacity;
120         fr[1].getInt(capacity);
121         FloatArray* variety = new FloatArray;
122         variety->reserve(capacity);
123         fr += 3;
124         while (!fr.eof() && fr[0].getNoNestedBrackets() > entry) {
125             float val;
126             if (fr[0].getFloat(val)) {
127                 ++fr;
128                 variety->push_back(val);
129             }
130             else ++fr;
131         }
132         ++fr;
133         geom._vertexAttribArray = variety;
134     }
135
136     return iteratorAdvanced;
137 }
138
139 bool ShaderGeometry_writeLocalData(const Object& obj, Output& fw)
140 {
141     const ShaderGeometry& geom = static_cast<const ShaderGeometry&>(obj);
142
143     fw.indent() << "geometry" << std::endl;
144     fw.writeObject(*geom._geometry);
145     if (geom._posScaleArray.valid()) {
146         fw.indent() << "posScale " << geom._posScaleArray->size() << " {\n";
147         fw.moveIn();
148         for (Vec4Array::const_iterator iter = geom._posScaleArray->begin();
149              iter != geom._posScaleArray->end();
150              ++iter) {
151             fw.indent() << iter->x() << " " << iter->y() << " " << iter->z() << " "
152                         << iter->w() << "\n";
153         }
154         fw.moveOut();
155         fw.indent() << "}\n";
156     }
157     if (geom._vertexAttribArray.valid()) {
158         fw.indent() << "variety" << geom._vertexAttribArray->size() << " {\n";
159         fw.moveIn();
160         for (FloatArray::const_iterator iter = geom._vertexAttribArray->begin();
161              iter != geom._vertexAttribArray->end();
162              ++iter) {
163             fw.indent() << *iter << "\n";
164         }
165         fw.moveOut();
166         fw.indent() << "}\n";
167     }
168     return true;
169 }
170
171 osgDB::RegisterDotOsgWrapperProxy shaderGeometryProxy
172 (
173     new ShaderGeometry,
174     "ShaderGeometry",
175     "Object Drawable ShaderGeometry",
176     &ShaderGeometry_readLocalData,
177     &ShaderGeometry_writeLocalData
178     );
179 }
180