00001 /* 00002 File: SceneLang.cc 00003 00004 Function: See header file 00005 00006 Author(s): Andrew Willmott 00007 00008 Copyright: (c) 1995-2000, Andrew Willmott 00009 00010 Notes: 00011 00012 */ 00013 00014 00015 #include "gcl/SceneLang.h" 00016 #include "gcl/SLContext.h" 00017 #include "gcl/Readers.h" 00018 00019 00020 // --- Current library & scene-parsing context -------------------------------- 00021 00022 #ifdef UNFINISHED 00023 class SLC 00024 { 00025 static SLContext *slContext = new SLContext(aNumAttributes); 00026 static SLLibrary *slLibrary = 0; 00027 static scGroup *slCurrentGroupPtr; 00028 }; 00029 #endif 00030 00031 static SLContext *slContext = new SLContext(aNumAttributes); 00032 static SLLibrary *slLibrary = 0; 00033 static scGroup *slCurrentGroupPtr; 00034 00035 // --- Scene command definitions ---------------------------------------------- 00036 00037 Void slInit() 00038 { 00039 slSetLibrary(new SLLibrary); 00040 } 00041 00042 scObject *slCurrent() 00043 { 00044 return(slCurrentGroupPtr->Last()); 00045 } 00046 00047 scScenePtr slCurrentGroup() 00048 { 00049 return(slCurrentGroupPtr); 00050 } 00051 00052 scScenePtr slBeginObject(const Char *name) 00053 { 00054 if (slLibrary == 0) 00055 { 00056 cerr << "GCL Error in slBeginObject: slInit() was not called." << endl; 00057 exit(1); 00058 } 00059 00060 scScenePtr newGroup = GroupCast(Clone(slLibrary->Member("group"))); 00061 00062 newGroup->SetName(name); 00063 00064 if (slCurrentGroupPtr) 00065 slCurrentGroupPtr->Add(newGroup); 00066 00067 slCurrentGroupPtr = newGroup; 00068 slContext->Push(); 00069 00070 return(newGroup); 00071 } 00072 00073 Void slEndObject() 00074 { 00075 slCurrentGroupPtr = slCurrentGroupPtr->parent; 00076 slContext->Pop(); 00077 } 00078 00079 00080 // --- Attribute routines ----------------------------------------------------- 00081 00082 00083 Void slPointList() 00084 { 00085 scPoints *points = new scPoints; 00086 00087 points->AddToContext(slContext); 00088 slCurrentGroupPtr->Add(points); 00089 } 00090 00091 Int slPoint(const Point &p) 00092 { 00093 scPoints *points = SL_GET(Points); 00094 00095 if (!points) 00096 { 00097 slPointList(); 00098 points = (scPoints*) slCurrent(); 00099 } 00100 00101 points->Append(p); 00102 00103 return(points->NumItems() - 1); 00104 } 00105 00106 Void slPoints(const PointList &pl) 00107 { 00108 scPoints *points = new scPoints(pl); 00109 00110 slCurrentGroupPtr->Add(points); 00111 points->AddToContext(slContext); 00112 } 00113 00114 Void slColourList() 00115 { 00116 scColours *colours = new scColours; 00117 00118 colours->AddToContext(slContext); 00119 slCurrentGroupPtr->Add(colours); 00120 } 00121 00122 Int slColour(const Colour &c) 00123 // XXX this is overloaded -- have slColour as vertex colour, and 00124 // define different colour type as object colours (slDiffColour?) 00125 { 00126 scColours *colours; 00127 00128 if (colours = SL_GET(Colours)) 00129 { 00130 colours->Append(c); 00131 return(colours->NumItems() - 1); 00132 } 00133 else 00134 { 00135 scColour *colour = new scColour(c); 00136 00137 slCurrentGroupPtr->Add(colour); 00138 colour->AddToContext(slContext); 00139 return(-1); 00140 } 00141 } 00142 00143 Void slNormalList() 00144 { 00145 scNormals *normals = new scNormals; 00146 00147 normals->AddToContext(slContext); 00148 slCurrentGroupPtr->Add(normals); 00149 } 00150 00151 Int slNormal(const Vector &p) 00152 { 00153 scNormals *normals = SL_GET(Normals); 00154 00155 if (!normals) 00156 { 00157 slNormalList(); 00158 normals = (scNormals*) slCurrent(); 00159 } 00160 00161 normals->Append(p); 00162 00163 return(normals->NumItems() - 1); 00164 } 00165 00166 Void slCoordList() 00167 { 00168 scCoords *coords = new scCoords; 00169 00170 coords->AddToContext(slContext); 00171 slCurrentGroupPtr->Add(coords); 00172 } 00173 00174 Int slCoord(const Coord &c) 00175 { 00176 scCoords *coords = SL_GET(Coords); 00177 00178 if (!coords) 00179 { 00180 slCoordList(); 00181 coords = (scCoords*) slCurrent(); 00182 } 00183 00184 coords->Append(c); 00185 00186 return(coords->NumItems() - 1); 00187 } 00188 00189 Void slCoords(const CoordList &cl) 00190 { 00191 scCoords *coords = new scCoords(cl); 00192 00193 slCurrentGroupPtr->Add(coords); 00194 coords->AddToContext(slContext); 00195 } 00196 00197 // --- Index types ------------------------------------------------------- 00198 00199 // Generic 00200 00201 Void slIndexList(scAttributeID id) 00202 { 00203 scIndexes *indexes = new scIndexes(id); 00204 00205 indexes->AddToContext(slContext); 00206 slCurrentGroupPtr->Add(indexes); 00207 } 00208 00209 Void slIndex(scAttributeID id, Int i) 00210 { 00211 Assert(i >= 0, "(slIndex) negative index!"); 00212 00213 scIndexes *indexes = (scIndexes*) slContext->Get(id); 00214 00215 if (!indexes) 00216 { 00217 slIndexList(id); 00218 indexes = (scIndexes*) slCurrent(); 00219 } 00220 00221 indexes->Append(i); 00222 } 00223 00224 Void slIndexes(scAttributeID id, const IndexList &il) 00225 { 00226 scIndexes *indexes = new scIndexes(id, il); 00227 00228 slCurrentGroupPtr->Add(indexes); 00229 indexes->AddToContext(slContext); 00230 } 00231 00232 // Specific 00233 00234 Void slPointIndexList() { slIndexList(aPointIndexes); } 00235 Void slColourIndexList() { slIndexList(aColourIndexes); } 00236 Void slNormalIndexList() { slIndexList(aNormalIndexes); } 00237 Void slCoordIndexList() { slIndexList(aCoordIndexes); } 00238 00239 Void slPointIndex(Int i) { slIndex(aPointIndexes, i); } 00240 Void slColourIndex(Int i) { slIndex(aColourIndexes, i); } 00241 Void slNormalIndex(Int i) { slIndex(aNormalIndexes, i); } 00242 Void slCoordIndex(Int i) { slIndex(aCoordIndexes, i); } 00243 00244 Void slPointIndexes(const IndexList &il) { slIndexes(aPointIndexes, il); } 00245 Void slColourIndexes(const IndexList &il) { slIndexes(aColourIndexes, il); } 00246 Void slNormalIndexes(const IndexList &il) { slIndexes(aNormalIndexes, il); } 00247 Void slCoordIndexes(const IndexList &il) { slIndexes(aCoordIndexes, il); } 00248 00249 // ---------------------------------------------------------------------------- 00250 00251 Void slTexture(StrConst filename) 00252 { 00253 scTexture *texture = new scTexture; 00254 00255 texture->Load(filename); 00256 00257 slCurrentGroupPtr->Add(texture); 00258 texture->AddToContext(slContext); 00259 } 00260 00261 Void slCamera() 00262 { 00263 scCamera *camera = new scCamera; 00264 00265 camera->AddToContext(slContext); 00266 slCurrentGroupPtr->Add(camera); 00267 } 00268 00269 Void slTransform(const Transform &t) 00270 { 00271 scTransform *transform = new scTransform(t); 00272 00273 slCurrentGroupPtr->Add(transform); 00274 transform->AddToContext(slContext); 00275 } 00276 00277 Void slEmittance(const Colour &c) 00278 { 00279 scEmittance *emit = new scEmittance(c); 00280 00281 slCurrentGroupPtr->Add(emit); 00282 emit->AddToContext(slContext); 00283 } 00284 00285 Void slPoly() 00286 { 00287 scPrimitive *poly; 00288 00289 poly = Clone(slLibrary->Member("poly")); 00290 00291 slCurrentGroupPtr->Add(poly); 00292 } 00293 00294 Void slBeginFaces() 00295 { 00296 scIndexes *indexes = SL_GET(PointIndexes); 00297 scIndexes *faceIndexes = new scIndexes(aFaceIndexes); 00298 00299 if (!indexes) 00300 { 00301 slPointIndexList(); 00302 indexes = (scIndexes*) slCurrent(); 00303 } 00304 00305 faceIndexes->AddToContext(slContext); 00306 slCurrentGroupPtr->Add(faceIndexes); 00307 faceIndexes->Append(indexes->NumItems()); 00308 } 00309 00310 Void slFace() 00311 { 00312 scIndexes *faceIdxs = SL_GET(FaceIndexes); 00313 scIndexes *idxs = SL_GET(PointIndexes); 00314 00315 if (!faceIdxs) 00316 _Warning("slFace() without an slBeginFaces()"); 00317 else 00318 faceIdxs->Append(idxs->NumItems()); 00319 } 00320 00321 Void slEndFaces() 00322 { 00323 scIndexes *faceIdxs = SL_GET(FaceIndexes); 00324 00325 if (!faceIdxs) 00326 _Warning("slFace() without an slBeginFaces()"); 00327 else if (faceIdxs->NumItems() > 1) 00328 slPoly(); 00329 // XXX else remove empty face list. 00330 } 00331 00332 // --- Generic ---------------------------------------------------------------- 00333 00334 Void slApply(const Transform &t) 00335 { 00336 slCurrent()->Apply(t); 00337 } 00338 00339 Bool slObjectExists(const Char *name) 00340 { 00341 if (slLibrary) 00342 return(slLibrary->MemberExists(name)); 00343 else 00344 return(false); 00345 } 00346 00347 scPrimitive *slObject(const Char *name) 00348 { 00349 scPrimitive *newObj = Clone(slLibrary->Member(name)); 00350 00351 slCurrentGroupPtr->Add(newObj); 00352 00353 return(newObj); 00354 } 00355 00356 scPrimitive *slObject(scPrimitive *object) 00357 { 00358 slCurrentGroupPtr->Add(object); 00359 return(object); 00360 } 00361 00362 scPrimitive *slObjectFile(StrConst filename) 00363 { 00364 scScenePtr scenePtr; 00365 FileName sceneFile; 00366 00367 sceneFile.SetPath(SubstituteEnvVars(filename)); 00368 scenePtr = SceneReader::Load(sceneFile); 00369 00370 if (scenePtr) 00371 slCurrentGroupPtr->Add(scenePtr); 00372 00373 return(scenePtr); 00374 } 00375 00376 Void slBeginObject(scScenePtr object) 00377 { 00378 if (slCurrentGroupPtr) 00379 slCurrentGroupPtr->Add(object); 00380 00381 slCurrentGroupPtr = object; 00382 slContext->Push(); 00383 } 00384 00385 Void slAttribute(scAttribute *attrPtr) 00386 { 00387 slCurrentGroupPtr->Add(attrPtr); 00388 attrPtr->AddToContext(slContext); 00389 } 00390 00391 Void slEndAttribute(Int attr) 00392 { 00393 slCurrentGroupPtr->Add(new scClearAttr(attr)); 00394 } 00395 00396 Void slMeshType(RenderStyle renStyle) 00397 { 00398 scMeshType *sm = new scMeshType; 00399 00400 sm->itsType = renStyle; 00401 slCurrentGroupPtr->Add(sm); 00402 } 00403 00404 SLContext *slGetContext() 00405 { 00406 return(slContext); 00407 } 00408 00409 // --- Library routines ------------------------------------------------------- 00410 00411 00412 Void slSetLibrary(SLLibrary *library) 00413 { 00414 delete slLibrary; 00415 00416 slLibrary = library; 00417 slLibrary->Create(); 00418 } 00419 00420 SLLibrary *slSwapLibrary(SLLibrary *newLib) 00421 { 00422 SLLibrary *tl = slLibrary; 00423 00424 slLibrary = newLib; 00425 return(tl); 00426 } 00427 00428 Void slAddToLibrary(scGroup *newGroup) 00429 { 00430 slLibrary->AddMember(newGroup); 00431 } 00432 00433 SLLibrary *slGetLibrary() 00434 { 00435 return(slLibrary); 00436 }