1 /***************************************************************************
2                           editgraphobj.cpp  -  An editable graphics object
3                              -------------------
4     begin                : wo apr 16 2003
5     copyright            : (C) 2003 by CJP
6     email                : cornware-cjp@users.sourceforge.net
7  ***************************************************************************/
8 
9 /***************************************************************************
10  *                                                                         *
11  *   This program is free software; you can redistribute it and/or modify  *
12  *   it under the terms of the GNU General Public License as published by  *
13  *   the Free Software Foundation; either version 2 of the License, or     *
14  *   (at your option) any later version.                                   *
15  *                                                                         *
16  ***************************************************************************/
17 
18 #include <GL/gl.h>
19 #include <cstdio> //for sscanf
20 #include <cmath> //for fabs
21 
22 #include "load3ds.h"
23 #include "loadglt.h"
24 #include "loadlwo.h"
25 #include "loadobj.h"
26 #include "loadraw.h"
27 #include "glbfile.h"
28 
29 #include "editgraphobj.h"
30 #include "datafile.h"
31 
CEditGraphObj()32 CEditGraphObj::CEditGraphObj()
33 {
34 	m_ObjList = m_ObjListRef = 0;
35 	isRendered = false;
36 }
37 
~CEditGraphObj()38 CEditGraphObj::~CEditGraphObj()
39 {
40 	if(isRendered)
41 	{
42 		glDeleteLists(m_ObjList, 1);
43 		glDeleteLists(m_ObjListRef, 1);
44 	}
45 }
46 
loadGLBFile(CString filename)47 bool CEditGraphObj::loadGLBFile(CString filename)
48 {
49 	CGLBFile f;
50 	if(!f.load(filename)) return false;
51 
52 	clear();
53 	for(unsigned int p=0; p < f.m_Primitives.size(); p++)
54 	{
55 		m_Primitives.push_back(CPrimitive());
56 		CPrimitive &pr2 = m_Primitives.back();
57 		CGLBFile::SPrimitive &pr1 = f.m_Primitives[p];
58 
59 		pr2.m_Name = pr1.Name;
60 		pr2.m_Type = CPrimitive::VertexArray;
61 
62 		pr2.m_Material.LODs = "";
63 		if(pr1.material.LODs & 1) pr2.m_Material.LODs += '1';
64 		if(pr1.material.LODs & 2) pr2.m_Material.LODs += '2';
65 		if(pr1.material.LODs & 4) pr2.m_Material.LODs += '3';
66 		if(pr1.material.LODs & 8) pr2.m_Material.LODs += '4';
67 		if(pr1.material.LODs & 16) pr2.m_Material.LODs += 'c';
68 		if(pr1.material.LODs & 32) pr2.m_Material.LODs += 's';
69 		pr2.m_Material.texture = pr1.material.Texture;
70 		pr2.m_Material.modulationColor = pr1.material.ModulationColor;
71 		pr2.m_Material.replacementColor = pr1.material.ReplacementColor;
72 		pr2.m_Material.opacity = pr1.material.Opacity;
73 		pr2.m_Material.reflectance = pr1.material.Reflectance;
74 		pr2.m_Material.emissivity = pr1.material.Emissivity;
75 
76 		pr2.m_Animation.rotationEnabled = (pr1.animation.AnimationFlags & 0x1) != 0;
77 		pr2.m_Animation.rotationOrigin = pr1.animation.rotationOrigin;
78 		pr2.m_Animation.rotationVelocity = pr1.animation.rotationVelocity;
79 
80 		for(unsigned int v=0; v < pr1.vertex.size(); v++)
81 		{
82 			CVertex vt2;
83 			CGLBFile::SVertex &vt1 = pr1.vertex[v];
84 
85 			vt2.pos = vt1.pos;
86 			vt2.nor = vt1.nor;
87 			vt2.tex = vt1.tex;
88 
89 			pr2.m_Vertex.push_back(vt2);
90 		}
91 
92 		pr2.m_Index = pr1.index;
93 	}
94 
95 	return true;
96 }
97 
loadGLTFile(CString filename)98 bool CEditGraphObj::loadGLTFile(CString filename)
99 {
100 	return loadGLT(filename, *this);
101 }
102 
loadRAWFile(CString filename)103 bool CEditGraphObj::loadRAWFile(CString filename)
104 {
105 	return loadRAW(filename, *this);
106 }
107 
load3DSFile(CString filename)108 bool CEditGraphObj::load3DSFile(CString filename)
109 {
110 	return load3DS(filename, *this);
111 }
112 
loadLWOFile(CString filename)113 bool CEditGraphObj::loadLWOFile(CString filename)
114 {
115 	return loadLWO(filename, *this);
116 }
117 
loadOBJFile(CString filename)118 bool CEditGraphObj::loadOBJFile(CString filename)
119 {
120 	return loadOBJ(filename, *this);
121 }
122 
merge(const CEditGraphObj & obj,const CString & lods)123 void CEditGraphObj::merge(const CEditGraphObj &obj, const CString &lods)
124 {
125 	//merge 2 objects
126 	//if objects have equal names, then they are placed together
127 	//and the new one gets the suffix of the LODS
128 
129 	//calculate CG position
130 	CVector CG1, CG2;
131 	unsigned int num1 = 0, num2 = 0;
132 	for(unsigned int i=0; i < obj.m_Primitives.size(); i++)
133 		for(unsigned int j=0; j < obj.m_Primitives[i].m_Vertex.size(); j++)
134 		{
135 			CG2 += obj.m_Primitives[i].m_Vertex[j].pos;
136 			num2++;
137 		}
138 	CG2 /= num2;
139 
140 	for(unsigned int i=0; i < m_Primitives.size(); i++)
141 		for(unsigned int j=0; j < m_Primitives[i].m_Vertex.size(); j++)
142 		{
143 			CG1 += m_Primitives[i].m_Vertex[j].pos;
144 			num1++;
145 		}
146 	CG1 /= num1;
147 
148 	for(unsigned int i=0; i < obj.m_Primitives.size(); i++)
149 	{
150 		CPrimitive thePrimitive = obj.m_Primitives[i];
151 
152 		//Correct CG position
153 		thePrimitive.m_Material.LODs = lods;
154 		for(unsigned int j=0; j < thePrimitive.m_Vertex.size(); j++)
155 			thePrimitive.m_Vertex[j].pos += CG1 - CG2;
156 
157 		int match = -1;
158 		for(unsigned int j=0; j < m_Primitives.size(); j++)
159 			if(m_Primitives[j].m_Name == thePrimitive.m_Name)
160 				{match = j; break;}
161 
162 		if(match < 0) //no match: just add it to the end
163 		{
164 			m_Primitives.push_back(thePrimitive);
165 			continue;
166 		}
167 
168 		//there is a match
169 		thePrimitive.m_Name = thePrimitive.m_Name + "_" + lods;
170 
171 		//set the color
172 		for(unsigned int j=0; j < thePrimitive.m_Vertex.size(); j++)
173 		{
174 			thePrimitive.m_Vertex[j].col = m_Primitives[match].m_Vertex[0].col;
175 			thePrimitive.m_Vertex[j].opacity = m_Primitives[match].m_Vertex[0].opacity;
176 			thePrimitive.m_Vertex[j].reflectance = m_Primitives[match].m_Vertex[0].reflectance;
177 		}
178 
179 		m_Primitives.insert(m_Primitives.begin() + match, thePrimitive);
180 
181 	}
182 }
183 
clear()184 void CEditGraphObj::clear()
185 {
186 	m_Primitives.clear();
187 }
188 
saveGLTFile(const CString & filename)189 void CEditGraphObj::saveGLTFile(const CString &filename)
190 {
191 	CDataFile f(filename, true);
192 	f.writel("#CornWare UltimateStunts graphics file");
193 	f.writel("#created by the stunts3dedit editor");
194 	f.writel("");
195 	f.writel("Lod 1234c");
196 	f.writel("Normal 0,1,0");
197 	f.writel("Color 1,1,1");
198 	f.writel("Opacity 1");
199 	f.writel("Reflectance 0");
200 
201 	//State variables:
202 	CVertex state;
203 		state.pos = CVector(0,0,0);
204 		state.nor = CVector(0,1,0);
205 		state.col = CVector(1,1,1);
206 		state.opacity = 1.0;
207 		state.reflectance = 0.0;
208 		state.tex = CVector(0,0,0);
209 	int texid = -1;
210 	CString name = "default-name";
211 	CString LODs = "1234c";
212 
213 	for(unsigned int i=0; i<m_Primitives.size(); i++)
214 	{
215 		CPrimitive &pr = m_Primitives[i];
216 
217 		f.writel(""); //two empty lines
218 		f.writel("");
219 		if(!(pr.m_Name == name))
220 		{
221 			name = pr.m_Name;
222 			f.writel("#Tedit-name " + name);
223 		}
224 		if(!(pr.m_Material.LODs == LODs))
225 		{
226 			LODs = pr.m_Material.LODs;
227 			f.writel("Lod " + LODs);
228 
229 			//rewrite the entire state (set the current state totally invalid)
230 			//TODO: more efficient
231 			texid = -2;
232 			state.col = state.nor = state.tex = CVector(2,2,2);
233 			state.opacity = state.reflectance = 2;
234 		}
235 		if(!(pr.m_Material.texture == texid))
236 		{
237 			texid = pr.m_Material.texture;
238 			if(texid < 0)
239 				f.writel("Notex");
240 			else
241 				f.writel(CString("Texture ") + texid);
242 		}
243 
244 		f.writel("VertexArray");
245 		f.writel(CString("Color ") + pr.m_Material.modulationColor);
246 		f.writel(CString("Opacity ") + pr.m_Material.opacity);
247 		f.writel(CString("ReplacementColor ") + pr.m_Material.replacementColor);
248 		f.writel(CString("Reflectance ") + pr.m_Material.reflectance);
249 		f.writel(CString("Emissivity ") + pr.m_Material.emissivity);
250 
251 		if(pr.m_Animation.rotationEnabled)
252 		{
253 			f.writel(CString("RotationAnimation ") +
254 				pr.m_Animation.rotationOrigin + ";" +
255 				pr.m_Animation.rotationVelocity);
256 		}
257 
258 		for(unsigned int j=0; j<pr.m_Vertex.size(); j++)
259 		{
260 			CVertex &vt = pr.m_Vertex[j];
261 
262 			//normal
263 			if((vt.nor-state.nor).abs2() > 0.0001)
264 			{
265 				f.writel(CString("Normal ")+vt.nor.x+", "+vt.nor.y+", "+vt.nor.z);
266 				state.nor = vt.nor;
267 			}
268 
269 			//texcoord
270 			if((vt.tex-state.tex).abs2() > 0.000001)
271 			{
272 				f.writel(CString("TexCoord ")+vt.tex.x+", "+vt.tex.y);
273 				state.tex = vt.tex;
274 			}
275 
276 			//vertex
277 			f.writel(CString("Vertex ")+vt.pos.x+", "+vt.pos.y+", "+vt.pos.z);
278 		}
279 		for(unsigned int j=0; j<pr.m_Index.size(); j++)
280 			f.writel(CString("Index ") + pr.m_Index[j]);
281 
282 		f.writel("End");
283 	}
284 
285 }
286 
saveGLBFile(const CString & filename)287 void CEditGraphObj::saveGLBFile(const CString &filename)
288 {
289 	CGLBFile f;
290 
291 	for(unsigned int p=0; p < m_Primitives.size(); p++)
292 	{
293 		CPrimitive &pr1 = m_Primitives[p];
294 		f.m_Primitives.push_back(CGLBFile::SPrimitive());
295 		CGLBFile::SPrimitive &pr2 = f.m_Primitives.back();
296 
297 		pr2.Name = pr1.m_Name;
298 
299 		//Animation
300 		pr2.animation.AnimationFlags = 0;
301 		if(pr1.m_Animation.rotationEnabled) pr2.animation.AnimationFlags |= 0x1;
302 		pr2.animation.rotationOrigin   = pr1.m_Animation.rotationOrigin;
303 		pr2.animation.rotationVelocity = pr1.m_Animation.rotationVelocity;
304 
305 		//Material
306 		pr2.material.LODs = 0;
307 		if(pr1.m_Material.LODs.inStr('1') >= 0) pr2.material.LODs += 1;
308 		if(pr1.m_Material.LODs.inStr('2') >= 0) pr2.material.LODs += 2;
309 		if(pr1.m_Material.LODs.inStr('3') >= 0) pr2.material.LODs += 4;
310 		if(pr1.m_Material.LODs.inStr('4') >= 0) pr2.material.LODs += 8;
311 		if(pr1.m_Material.LODs.inStr('c') >= 0) pr2.material.LODs += 16;
312 		if(pr1.m_Material.LODs.inStr('s') >= 0) pr2.material.LODs += 32;
313 		pr2.material.Emissivity = pr1.m_Material.emissivity;
314 		pr2.material.ModulationColor = pr1.m_Material.modulationColor;
315 		pr2.material.Opacity = pr1.m_Material.opacity;
316 		pr2.material.Reflectance = pr1.m_Material.reflectance;
317 		pr2.material.ReplacementColor = pr1.m_Material.replacementColor;
318 		pr2.material.Texture = pr1.m_Material.texture;
319 
320 		//Vertices
321 		for(unsigned int v=0; v < pr1.m_Vertex.size(); v++)
322 		{
323 			CGLBFile::SVertex vt2;
324 			CVertex &vt1 = pr1.m_Vertex[v];
325 
326 			vt2.pos = vt1.pos;
327 			vt2.nor = vt1.nor;
328 			vt2.tex = vt1.tex;
329 
330 			pr2.vertex.push_back(vt2);
331 		}
332 
333 		//Indices
334 		pr2.index = pr1.m_Index;
335 	}
336 
337 	f.save(filename);
338 }
339 
convertToVertexArrays()340 void CEditGraphObj::convertToVertexArrays()
341 {
342 	for(unsigned int p=0; p < m_Primitives.size(); p++)
343 	{
344 		CPrimitive &pr = m_Primitives[p];
345 
346 		pr.m_Material.modulationColor = pr.m_Vertex[0].col;
347 		pr.m_Material.opacity = pr.m_Vertex[0].opacity;
348 		pr.m_Material.reflectance = pr.m_Vertex[0].reflectance;
349 		if(pr.m_Material.texture >= 0)
350 		{
351 			pr.m_Material.replacementColor = m_MatArray[pr.m_Material.texture]->getColor();
352 			pr.m_Material.replacementColor.x *= pr.m_Material.modulationColor.x;
353 			pr.m_Material.replacementColor.y *= pr.m_Material.modulationColor.y;
354 			pr.m_Material.replacementColor.z *= pr.m_Material.modulationColor.z;
355 		}
356 		else
357 			{pr.m_Material.replacementColor = pr.m_Material.modulationColor;}
358 		pr.m_Material.emissivity = 0;
359 
360 		unsigned int maxIndex = pr.m_Vertex.size() - 1;
361 		unsigned int writeIndex = 0;
362 		unsigned int readIndex = 0;
363 
364 		switch(pr.m_Type)
365 		{
366 		case CPrimitive::VertexArray:
367 			writeIndex = maxIndex+1;
368 			break;
369 
370 		case CPrimitive::Triangles:
371 			for(readIndex=0; readIndex <= maxIndex; readIndex++)
372 			{
373 				CVertex v = pr.m_Vertex[readIndex];
374 				pr.m_Index.push_back(findOrAdd(pr, v, writeIndex));
375 			}
376 			break;
377 
378 		case CPrimitive::Quads:
379 			for(readIndex=0; readIndex <= maxIndex; readIndex+= 4)
380 			{
381 				CVertex v1 = pr.m_Vertex[readIndex];
382 				CVertex v2 = pr.m_Vertex[readIndex+1];
383 				CVertex v3 = pr.m_Vertex[readIndex+2];
384 				CVertex v4 = pr.m_Vertex[readIndex+3];
385 
386 				unsigned int index1 = findOrAdd(pr, v1, writeIndex);
387 				unsigned int index2 = findOrAdd(pr, v2, writeIndex);
388 				unsigned int index3 = findOrAdd(pr, v3, writeIndex);
389 				unsigned int index4 = findOrAdd(pr, v4, writeIndex);
390 
391 				pr.m_Index.push_back(index1);
392 				pr.m_Index.push_back(index2);
393 				pr.m_Index.push_back(index3);
394 				pr.m_Index.push_back(index1);
395 				pr.m_Index.push_back(index3);
396 				pr.m_Index.push_back(index4);
397 			}
398 			break;
399 
400 		case CPrimitive::TriangleStrip:
401 		case CPrimitive::QuadStrip:
402 		{
403 			if(maxIndex < 2) break;
404 			unsigned int index1 = 0;
405 			unsigned int index2 = 1;
406 			writeIndex = 2;
407 			bool even = false;
408 			for(readIndex=2; readIndex <= maxIndex; readIndex++)
409 			{
410 				CVertex v3 = pr.m_Vertex[readIndex];
411 
412 				unsigned int index3 = findOrAdd(pr, v3, writeIndex);
413 
414 				if(even)
415 				{
416 					pr.m_Index.push_back(index3);
417 					pr.m_Index.push_back(index2);
418 					pr.m_Index.push_back(index1);
419 				}
420 				else
421 				{
422 					pr.m_Index.push_back(index1);
423 					pr.m_Index.push_back(index2);
424 					pr.m_Index.push_back(index3);
425 				}
426 
427 				index1 = index2;
428 				index2 = index3;
429 				even = !even;
430 			}
431 			break;
432 		}
433 
434 		case CPrimitive::Polygon:
435 		{
436 			if(maxIndex < 2) break;
437 			unsigned int index1 = 1;
438 			writeIndex = 2;
439 			for(readIndex=2; readIndex <= maxIndex; readIndex++)
440 			{
441 				CVertex v2 = pr.m_Vertex[readIndex];
442 
443 				unsigned int index2 = findOrAdd(pr, v2, writeIndex);
444 
445 				pr.m_Index.push_back(0);
446 				pr.m_Index.push_back(index1);
447 				pr.m_Index.push_back(index2);
448 
449 				index1 = index2;
450 			}
451 			break;
452 		}
453 
454 		}
455 
456 		pr.m_Vertex.resize(writeIndex);
457 		printf("Object %s reduced from %d to %d vertices\n",
458 			pr.m_Name.c_str(), maxIndex+1, writeIndex);
459 
460 		pr.m_Type = CPrimitive::VertexArray;
461 	}
462 }
463 
findOrAdd(CPrimitive & pr,const CVertex & v,unsigned int & writeIndex)464 unsigned int CEditGraphObj::findOrAdd(CPrimitive &pr, const CVertex &v, unsigned int &writeIndex)
465 {
466 	int found = -1;
467 	for(unsigned int i=0; i < writeIndex; i++)
468 		if(isEqual(pr.m_Vertex[i], v))
469 			{found = i; break;}
470 
471 	if(found < 0)
472 	{
473 		pr.m_Vertex[writeIndex] = v;
474 		writeIndex++;
475 		return writeIndex - 1;
476 	}
477 
478 	return (unsigned int)found;
479 }
480 
isEqual(const CVertex & v1,const CVertex & v2)481 bool CEditGraphObj::isEqual(const CVertex &v1, const CVertex &v2)
482 {
483 	return
484 		(v1.pos - v2.pos).abs() < 0.001 &&
485 		(v1.nor - v2.nor).abs() < 0.001 &&
486 		(v1.col - v2.col).abs() < 0.001 &&
487 		(v1.tex - v2.tex).abs() < 0.0001 &&
488 		fabs(v1.opacity - v2.opacity) < 0.01 &&
489 		fabs(v1.reflectance - v2.reflectance) < 0.01;
490 }
491 
render(const CString & visibleLODs)492 void CEditGraphObj::render(const CString &visibleLODs)
493 {
494 	//delete existing list
495 	if(isRendered)
496 	{
497 		printf("Deleting old model...\n");
498 		glDeleteLists(m_ObjList, 1);
499 		glDeleteLists(m_ObjListRef, 1);
500 	}
501 
502 	printf("Generating model...\n");
503 
504 	//Normal model
505 	m_ObjList = glGenLists(1);
506 	glNewList(m_ObjList, GL_COMPILE);
507 
508 	for(unsigned int i=0; i<m_Primitives.size(); i++)
509 	{
510 		CPrimitive &pr = m_Primitives[i];
511 
512 		CString LODs = pr.m_Material.LODs;
513 		bool doit = false;
514 		for(unsigned int j=0; j < LODs.length(); j++)
515 			if(visibleLODs.inStr( (LODs[j]) ) >= 0)
516 				{doit = true; break;}
517 		if(!doit) continue;
518 
519 		//Standard colors
520 		m_OpacityState = pr.m_Material.opacity;
521 		m_ColorState = pr.m_Material.modulationColor;
522 
523 		//Apply texture
524 		if(pr.m_Material.texture < 0)
525 		{ //no texture
526 			glDisable(GL_TEXTURE_2D);
527 		}
528 		else if(
529 			m_MatArray[pr.m_Material.texture]->getSizeX(1) <= 4 ||
530 			m_MatArray[pr.m_Material.texture]->getSizeY(1) <= 4)
531 		{ //too small texture
532 			glDisable(GL_TEXTURE_2D);
533 			m_ColorState.x *= pr.m_Material.replacementColor.x;
534 			m_ColorState.y *= pr.m_Material.replacementColor.y;
535 			m_ColorState.z *= pr.m_Material.replacementColor.z;
536 		}
537 		else
538 		{ //a good texture
539 			glEnable(GL_TEXTURE_2D);
540 			m_MatArray[pr.m_Material.texture]->draw(1);
541 		}
542 
543 		//Set the color
544 		setMaterialColor();
545 
546 		glBegin(GL_TRIANGLES);
547 		for(unsigned int k=0; k<pr.m_Index.size(); k++)
548 		{
549 			unsigned int j = pr.m_Index[k];
550 			CVertex &vt = pr.m_Vertex[j];
551 			CVector &nor = vt.nor;
552 			glNormal3f(nor.x, nor.y, nor.z);
553 			CVector &tex = vt.tex;
554 			glTexCoord2f(tex.x, tex.y);
555 			CVector &pos = vt.pos;
556 			glVertex3f(pos.x, pos.y, pos.z);
557 		}
558 		glEnd();
559 
560 		//Rotation axis
561 		if(pr.m_Animation.rotationEnabled)
562 		{
563 			CVector p1 = pr.m_Animation.rotationOrigin;
564 			CVector p2 = p1 + pr.m_Animation.rotationVelocity;
565 
566 			glDisable(GL_TEXTURE_2D);
567 			glDisable(GL_LIGHTING);
568 			glColor4f(0,1,1,1);
569 
570 			glBegin(GL_LINES);
571 			glVertex3f(p1.x, p1.y, p1.z);
572 			glVertex3f(p2.x, p2.y, p2.z);
573 			glEnd();
574 
575 			glColor4f(1,1,1,1);
576 			glEnable(GL_LIGHTING);
577 		}
578 	}
579 
580 	glEndList();
581 
582 	//Reflection model
583 	m_ObjListRef = glGenLists(1);
584 	glNewList(m_ObjListRef, GL_COMPILE);
585 
586 	m_ColorState = CVector(1,1,1);
587 	for(unsigned int i=0; i<m_Primitives.size(); i++)
588 	{
589 		CPrimitive &pr = m_Primitives[i];
590 		if(pr.m_Material.LODs.inStr('1') < 0) continue; //reflection model = LOD 1
591 
592 		if(pr.m_Type == CPrimitive::VertexArray)
593 		{
594 			m_OpacityState = pr.m_Material.reflectance;
595 			setMaterialColor();
596 
597 			glBegin(GL_TRIANGLES);
598 			for(unsigned int k=0; k<pr.m_Index.size(); k++)
599 			{
600 				unsigned int j = pr.m_Index[k];
601 				CVertex &vt = pr.m_Vertex[j];
602 				CVector &nor = vt.nor;
603 				glNormal3f(nor.x, nor.y, nor.z);
604 				CVector &pos = vt.pos;
605 				glVertex3f(pos.x, pos.y, pos.z);
606 			}
607 			glEnd();
608 		}
609 		else
610 		{
611 			glBegin(pr.m_Type);
612 			for(unsigned int j=0; j<pr.m_Vertex.size(); j++)
613 			{
614 				CVertex &vt = pr.m_Vertex[j];
615 				CVector &nor = vt.nor;
616 				glNormal3f(nor.x, nor.y, nor.z);
617 				m_OpacityState = vt.reflectance;
618 				setMaterialColor();
619 				CVector &pos = vt.pos;
620 				glVertex3f(pos.x, pos.y, pos.z);
621 			}
622 			glEnd();
623 		}
624 	}
625 
626 	glEndList();
627 
628 
629 	isRendered = true;
630 }
631 
draw() const632 void CEditGraphObj::draw() const
633 {
634 	glCallList(m_ObjList);
635 }
636 
drawRef() const637 void CEditGraphObj::drawRef() const
638 {
639 	glCallList(m_ObjListRef);
640 }
641 
setMaterialColor()642 void CEditGraphObj::setMaterialColor()
643 {
644 	float kleur[] = {m_ColorState.x, m_ColorState.y, m_ColorState.z, m_OpacityState};
645 	glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, kleur);
646 }
647