diff options
Diffstat (limited to 'libraries/irrlicht-1.8.1/source/Irrlicht/CSphereSceneNode.cpp')
-rw-r--r-- | libraries/irrlicht-1.8.1/source/Irrlicht/CSphereSceneNode.cpp | 199 |
1 files changed, 199 insertions, 0 deletions
diff --git a/libraries/irrlicht-1.8.1/source/Irrlicht/CSphereSceneNode.cpp b/libraries/irrlicht-1.8.1/source/Irrlicht/CSphereSceneNode.cpp new file mode 100644 index 0000000..00b6528 --- /dev/null +++ b/libraries/irrlicht-1.8.1/source/Irrlicht/CSphereSceneNode.cpp | |||
@@ -0,0 +1,199 @@ | |||
1 | // Copyright (C) 2002-2012 Nikolaus Gebhardt | ||
2 | // This file is part of the "Irrlicht Engine". | ||
3 | // For conditions of distribution and use, see copyright notice in irrlicht.h | ||
4 | |||
5 | #include "CSphereSceneNode.h" | ||
6 | #include "IVideoDriver.h" | ||
7 | #include "ISceneManager.h" | ||
8 | #include "S3DVertex.h" | ||
9 | #include "os.h" | ||
10 | #include "CShadowVolumeSceneNode.h" | ||
11 | |||
12 | namespace irr | ||
13 | { | ||
14 | namespace scene | ||
15 | { | ||
16 | |||
17 | //! constructor | ||
18 | CSphereSceneNode::CSphereSceneNode(f32 radius, u32 polyCountX, u32 polyCountY, ISceneNode* parent, ISceneManager* mgr, s32 id, | ||
19 | const core::vector3df& position, const core::vector3df& rotation, const core::vector3df& scale) | ||
20 | : IMeshSceneNode(parent, mgr, id, position, rotation, scale), Mesh(0), Shadow(0), | ||
21 | Radius(radius), PolyCountX(polyCountX), PolyCountY(polyCountY) | ||
22 | { | ||
23 | #ifdef _DEBUG | ||
24 | setDebugName("CSphereSceneNode"); | ||
25 | #endif | ||
26 | |||
27 | Mesh = SceneManager->getGeometryCreator()->createSphereMesh(radius, polyCountX, polyCountY); | ||
28 | } | ||
29 | |||
30 | |||
31 | |||
32 | //! destructor | ||
33 | CSphereSceneNode::~CSphereSceneNode() | ||
34 | { | ||
35 | if (Shadow) | ||
36 | Shadow->drop(); | ||
37 | if (Mesh) | ||
38 | Mesh->drop(); | ||
39 | } | ||
40 | |||
41 | |||
42 | //! renders the node. | ||
43 | void CSphereSceneNode::render() | ||
44 | { | ||
45 | video::IVideoDriver* driver = SceneManager->getVideoDriver(); | ||
46 | |||
47 | if (Mesh && driver) | ||
48 | { | ||
49 | driver->setMaterial(Mesh->getMeshBuffer(0)->getMaterial()); | ||
50 | driver->setTransform(video::ETS_WORLD, AbsoluteTransformation); | ||
51 | if (Shadow) | ||
52 | Shadow->updateShadowVolumes(); | ||
53 | |||
54 | driver->drawMeshBuffer(Mesh->getMeshBuffer(0)); | ||
55 | if ( DebugDataVisible & scene::EDS_BBOX ) | ||
56 | { | ||
57 | video::SMaterial m; | ||
58 | m.Lighting = false; | ||
59 | driver->setMaterial(m); | ||
60 | driver->draw3DBox(Mesh->getMeshBuffer(0)->getBoundingBox(), video::SColor(255,255,255,255)); | ||
61 | } | ||
62 | } | ||
63 | } | ||
64 | |||
65 | |||
66 | //! Removes a child from this scene node. | ||
67 | //! Implemented here, to be able to remove the shadow properly, if there is one, | ||
68 | //! or to remove attached childs. | ||
69 | bool CSphereSceneNode::removeChild(ISceneNode* child) | ||
70 | { | ||
71 | if (child && Shadow == child) | ||
72 | { | ||
73 | Shadow->drop(); | ||
74 | Shadow = 0; | ||
75 | } | ||
76 | |||
77 | return ISceneNode::removeChild(child); | ||
78 | } | ||
79 | |||
80 | |||
81 | //! Creates shadow volume scene node as child of this node | ||
82 | //! and returns a pointer to it. | ||
83 | IShadowVolumeSceneNode* CSphereSceneNode::addShadowVolumeSceneNode( | ||
84 | const IMesh* shadowMesh, s32 id, bool zfailmethod, f32 infinity) | ||
85 | { | ||
86 | if (!SceneManager->getVideoDriver()->queryFeature(video::EVDF_STENCIL_BUFFER)) | ||
87 | return 0; | ||
88 | |||
89 | if (!shadowMesh) | ||
90 | shadowMesh = Mesh; // if null is given, use the mesh of node | ||
91 | |||
92 | if (Shadow) | ||
93 | Shadow->drop(); | ||
94 | |||
95 | Shadow = new CShadowVolumeSceneNode(shadowMesh, this, SceneManager, id, zfailmethod, infinity); | ||
96 | return Shadow; | ||
97 | } | ||
98 | |||
99 | |||
100 | //! returns the axis aligned bounding box of this node | ||
101 | const core::aabbox3d<f32>& CSphereSceneNode::getBoundingBox() const | ||
102 | { | ||
103 | return Mesh ? Mesh->getBoundingBox() : Box; | ||
104 | } | ||
105 | |||
106 | |||
107 | void CSphereSceneNode::OnRegisterSceneNode() | ||
108 | { | ||
109 | if (IsVisible) | ||
110 | SceneManager->registerNodeForRendering(this); | ||
111 | |||
112 | ISceneNode::OnRegisterSceneNode(); | ||
113 | } | ||
114 | |||
115 | |||
116 | //! returns the material based on the zero based index i. To get the amount | ||
117 | //! of materials used by this scene node, use getMaterialCount(). | ||
118 | //! This function is needed for inserting the node into the scene hirachy on a | ||
119 | //! optimal position for minimizing renderstate changes, but can also be used | ||
120 | //! to directly modify the material of a scene node. | ||
121 | video::SMaterial& CSphereSceneNode::getMaterial(u32 i) | ||
122 | { | ||
123 | if (i>0 || !Mesh) | ||
124 | return ISceneNode::getMaterial(i); | ||
125 | else | ||
126 | return Mesh->getMeshBuffer(i)->getMaterial(); | ||
127 | } | ||
128 | |||
129 | |||
130 | //! returns amount of materials used by this scene node. | ||
131 | u32 CSphereSceneNode::getMaterialCount() const | ||
132 | { | ||
133 | return 1; | ||
134 | } | ||
135 | |||
136 | |||
137 | //! Writes attributes of the scene node. | ||
138 | void CSphereSceneNode::serializeAttributes(io::IAttributes* out, io::SAttributeReadWriteOptions* options) const | ||
139 | { | ||
140 | ISceneNode::serializeAttributes(out, options); | ||
141 | |||
142 | out->addFloat("Radius", Radius); | ||
143 | out->addInt("PolyCountX", PolyCountX); | ||
144 | out->addInt("PolyCountY", PolyCountY); | ||
145 | } | ||
146 | |||
147 | |||
148 | //! Reads attributes of the scene node. | ||
149 | void CSphereSceneNode::deserializeAttributes(io::IAttributes* in, io::SAttributeReadWriteOptions* options) | ||
150 | { | ||
151 | f32 oldRadius = Radius; | ||
152 | u32 oldPolyCountX = PolyCountX; | ||
153 | u32 oldPolyCountY = PolyCountY; | ||
154 | |||
155 | Radius = in->getAttributeAsFloat("Radius"); | ||
156 | PolyCountX = in->getAttributeAsInt("PolyCountX"); | ||
157 | PolyCountY = in->getAttributeAsInt("PolyCountY"); | ||
158 | // legacy values read for compatibility with older versions | ||
159 | u32 polyCount = in->getAttributeAsInt("PolyCount"); | ||
160 | if (PolyCountX ==0 && PolyCountY == 0) | ||
161 | PolyCountX = PolyCountY = polyCount; | ||
162 | |||
163 | Radius = core::max_(Radius, 0.0001f); | ||
164 | |||
165 | if ( !core::equals(Radius, oldRadius) || PolyCountX != oldPolyCountX || PolyCountY != oldPolyCountY) | ||
166 | { | ||
167 | if (Mesh) | ||
168 | Mesh->drop(); | ||
169 | Mesh = SceneManager->getGeometryCreator()->createSphereMesh(Radius, PolyCountX, PolyCountY); | ||
170 | } | ||
171 | |||
172 | ISceneNode::deserializeAttributes(in, options); | ||
173 | } | ||
174 | |||
175 | //! Creates a clone of this scene node and its children. | ||
176 | ISceneNode* CSphereSceneNode::clone(ISceneNode* newParent, ISceneManager* newManager) | ||
177 | { | ||
178 | if (!newParent) | ||
179 | newParent = Parent; | ||
180 | if (!newManager) | ||
181 | newManager = SceneManager; | ||
182 | |||
183 | CSphereSceneNode* nb = new CSphereSceneNode(Radius, PolyCountX, PolyCountY, newParent, | ||
184 | newManager, ID, RelativeTranslation); | ||
185 | |||
186 | nb->cloneMembers(this, newManager); | ||
187 | nb->getMaterial(0) = Mesh->getMeshBuffer(0)->getMaterial(); | ||
188 | nb->Shadow = Shadow; | ||
189 | if ( nb->Shadow ) | ||
190 | nb->Shadow->grab(); | ||
191 | |||
192 | if ( newParent ) | ||
193 | nb->drop(); | ||
194 | return nb; | ||
195 | } | ||
196 | |||
197 | } // end namespace scene | ||
198 | } // end namespace irr | ||
199 | |||