2
0

LevelEditor.py 127 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429
  1. from PandaObject import *
  2. from PieMenu import *
  3. from OnscreenText import *
  4. from whrandom import *
  5. from Tkinter import *
  6. from DirectGeometry import *
  7. from SceneGraphExplorer import *
  8. from tkSimpleDialog import askstring
  9. from tkFileDialog import *
  10. import Pmw
  11. import Dial
  12. import Floater
  13. import EntryScale
  14. import VectorWidgets
  15. import string
  16. class LevelEditor(NodePath, PandaObject):
  17. def __init__(self,direct,parent = None):
  18. # Initialize superclass
  19. NodePath.__init__(self)
  20. self.assign(hidden.attachNewNode( NamedNode('LevelEditor')))
  21. # Record handle to direct session
  22. self.direct = direct
  23. # Make sure direct is running
  24. self.direct.enable()
  25. self.direct.widget.disableHandles(['x-ring', 'x-disc',
  26. 'y-ring', 'y-disc',
  27. 'z-post'])
  28. # Create level editor dictionaries
  29. # This dictionary stores information about new objects added
  30. # to the level
  31. self.levelDictionary = {}
  32. # This dictionary stores information about module hooks,
  33. # grouped by level
  34. self.hooksDictionary = {}
  35. # This dictionary stores information about the various
  36. # pie menus in use
  37. self.pieMenuDictionary = {}
  38. # This dictionary stores all the different color palettes
  39. self.colorPaletteDictionary = {}
  40. # This dictionary stores info about current and possible
  41. # object attributes
  42. self.attributeDictionary = {}
  43. # This dictionary stores pleasing style combinations
  44. self.styleDictionary = {}
  45. # This dictionary stores pointers to the various maps
  46. self.mapDictionary = {}
  47. self.activeMap = None
  48. # DNAStorage instance for storing level DNA info
  49. self.dnaStore = DNAStorage()
  50. loadDNAFile(self.dnaStore, 'dna/storage.dna',
  51. getDefaultCoordinateSystem())
  52. self.dnaOutputDir = 'ToontownCentral'
  53. self.dnaOutputFile = 'toontown_working.dna'
  54. # Top level DNA Data Object
  55. self.levelObjectsDNA = DNAData('LevelObjects')
  56. # Create top level node
  57. self.levelObjects = self.attachNewNode(NamedNode('LevelObjects'))
  58. # Create a top level group
  59. self.createTopLevelGroup()
  60. # Set used to iterate over module categories
  61. self.categorySet = []
  62. self.selectedLevelObject = None
  63. self.targetDNAObject = None
  64. self.activeMenu = None
  65. # Get a handle to the grid
  66. self.grid = self.direct.grid
  67. self.showGrid(0)
  68. self.levelMap = hidden.attachNewNode(NamedNode('level-map'))
  69. map = loader.loadModel('level_editor/toontown_central_layout')
  70. map.getBottomArc().setTransition(TransparencyTransition(1))
  71. map.setColor(Vec4(1,1,1,.4))
  72. self.mapDictionary['toontownCentral'] = map
  73. map = loader.loadModel('level_editor/donalds_dock_layout')
  74. map.getBottomArc().setTransition(TransparencyTransition(1))
  75. map.setColor(Vec4(1,1,1,.4))
  76. self.mapDictionary['donaldsDock'] = map
  77. map = loader.loadModel('level_editor/minnies_melody_land_layout')
  78. map.getBottomArc().setTransition(TransparencyTransition(1))
  79. map.setColor(Vec4(1,1,1,.4))
  80. self.mapDictionary['minniesMelodyLand'] = map
  81. map = loader.loadModel('level_editor/the_burrrgh_layout')
  82. map.getBottomArc().setTransition(TransparencyTransition(1))
  83. map.setColor(Vec4(1,1,1,.4))
  84. self.mapDictionary['theBurrrgh'] = map
  85. self.hitPt = Point3(0)
  86. self.offset = Point3(0)
  87. self.crankOrigin = Point3(0)
  88. self.crankDir = Vec3(0)
  89. self.hprSnap = 1
  90. self.snapAngle = 15.0
  91. self.lastAngle = 0.0
  92. # Create Level Editor Panel and pie menus
  93. # Initialize styles
  94. self.initializeStyleDictionary()
  95. # Initialize pie Menus (this depends on the style dictionary)
  96. self.initializePieMenus()
  97. self.panel = LevelEditorPanel(self, parent)
  98. base.cam.node().setNear(5.0)
  99. base.cam.node().setFar(10000)
  100. self.direct.camera.setPos(0,-10,10)
  101. # Default is to use the toontown central color palette
  102. self.editToontownCentral()
  103. self.enable()
  104. def initializeAttributeDictionary(self):
  105. # Retrieve lists of available attributes from DNAStorage object
  106. # Cornices
  107. attributeList = self.getCatalogCodesSuffix('cornice', '_ur')
  108. # Make the first one a null texture
  109. attributeList[:0] = [None]
  110. self.attributeDictionary['corniceTextures'] = attributeList
  111. self.attributeDictionary['corniceTexture'] = attributeList[1]
  112. self.attributeDictionary['corniceOrienation'] = '_ur'
  113. # Doors
  114. attributeList = self.getCatalogCodesSuffix('door', '_ur')
  115. self.attributeDictionary['doorTextures'] = attributeList
  116. self.attributeDictionary['doorTexture'] = attributeList[1]
  117. self.attributeDictionary['doorOrienation'] = '_ur'
  118. # FlatBuildings
  119. self.attributeDictionary['buildingHeight'] = 20.0
  120. # Props
  121. attributeList = self.getCatalogCodes('prop')
  122. self.attributeDictionary['propTypes'] = attributeList
  123. self.attributeDictionary['propType'] = attributeList[1]
  124. # Walls
  125. attributeList = self.getCatalogCodesSuffix('wall', '_ur')
  126. self.attributeDictionary['wallTextures'] = attributeList
  127. self.attributeDictionary['wallTexture'] = attributeList[1]
  128. self.attributeDictionary['wallOrienation'] = '_ur'
  129. self.attributeDictionary['wallWidth'] = 15.0
  130. # Windows
  131. attributeList = self.getCatalogCodesSuffix('window', '_ur')
  132. self.attributeDictionary['windowTextures'] = attributeList
  133. self.attributeDictionary['windowTexture'] = attributeList[1]
  134. self.attributeDictionary['windowOrienation'] = '_ur'
  135. self.attributeDictionary['numWindows'] = 0
  136. def getActiveColor(self):
  137. return self.attributeDictionary['activeColor']
  138. def setActiveColor(self, color):
  139. self.attributeDictionary['activeColor'] = color
  140. def getBuildingHeight(self):
  141. return self.attributeDictionary['buildingHeight']
  142. def setBuildingHeight(self, height):
  143. self.attributeDictionary['buildingHeight'] = height
  144. def getCategorySet(self):
  145. return self.categorySet
  146. def getCorniceColor(self):
  147. return self.attributeDictionary['corniceColor']
  148. def getCorniceColors(self):
  149. return self.attributeDictionary['corniceColors']
  150. def getCorniceTexture(self):
  151. return self.attributeDictionary['corniceTexture']
  152. def setCorniceTexture(self, dnaString):
  153. self.attributeDictionary['corniceTexture'] = dnaString
  154. def getCorniceTextures(self):
  155. return self.attributeDictionary['corniceTextures']
  156. def getDnaStore(self):
  157. return self.dnaStore
  158. def getDoorColor(self):
  159. return self.attributeDictionary['doorColor']
  160. def getDoorColors(self):
  161. return self.attributeDictionary['doorColors']
  162. def getDoorTexture(self):
  163. return self.attributeDictionary['doorTexture']
  164. def setDoorTexture(self,dnaString):
  165. self.attributeDictionary['doorTexture'] = dnaString
  166. def getDoorTextures(self):
  167. return self.attributeDictionary['doorTextures']
  168. def getGrid(self):
  169. return self.grid
  170. def getGroupNum(self):
  171. return self.groupNum
  172. def setGroupNum(self,num):
  173. self.groupNum = num
  174. def setGroupParentToSelected(self):
  175. if self.direct.selected.last:
  176. self.setGroupParent(self.direct.selected.last)
  177. def setGroupParent(self,nodePath):
  178. parentDNA = self.getDNAGroup(nodePath)
  179. if parentDNA:
  180. self.groupParent = nodePath
  181. self.groupParentDNA = parentDNA
  182. def getHooksDictionary(self):
  183. return self.hooksDictionary
  184. def getLevelDictionary(self):
  185. return self.levelDictionary
  186. def getLevelMap(self):
  187. return self.levelMap
  188. def getLevelObjects(self):
  189. return self.levelObjects
  190. def getLevelObjectsDNA(self):
  191. return self.levelObjectsDNA
  192. def getNumWindows(self):
  193. return self.attributeDictionary.get('numWindows', 0)
  194. def setNumWindows(self, numWindows):
  195. self.attributeDictionary['numWindows'] = numWindows
  196. def printWallStyle(self):
  197. if self.selectedLevelObject:
  198. dnaObject = self.selectedLevelObject['DNA']
  199. objectClass = dnaObject.__class__.getClassType()
  200. if objectClass.eq(DNAFlatBuilding.getClassType()):
  201. self.printWallStyleFor(dnaObject)
  202. def printWallStyleFor(self, DNAFlatBuilding):
  203. wall = self.getLastWall(DNAFlatBuilding)
  204. cornice = self.getCornice(DNAFlatBuilding)
  205. self.printWallStyleWith(wall, cornice)
  206. def printWallStyleWith(self, wall, cornice):
  207. if wall:
  208. print 'self.addStyle(styleCount = styleCount + 1)'
  209. print 'wallTexture: ', self.getDNAString(wall)
  210. print 'wallColor: #(', wall.getColor(), ')'
  211. window = self.getWindow(wall,0)
  212. if window & (window.getWindowCount() > 0):
  213. print 'windowTexture: ', self.getDNAString(window)
  214. print 'windowColor: #(', window.getColor(), ')'
  215. else:
  216. print 'windowTexture: None'
  217. print 'windowColor: None'
  218. if cornice:
  219. print 'corniceTexture: ', self.getDNAString(cornice)
  220. print 'corniceColor: #(', cornice.getColor(), ')'
  221. else:
  222. print'corniceTexture: None'
  223. print'corniceColor: None'
  224. def printWallStyleForBldgWall(self, aDNAFlatBuilding, wallNum):
  225. if (aDNAFlatBuilding.getClassType().eq(DNAFlatBuilding.getClassType())):
  226. wall = self.getWall(aDNAFlatBuilding, wallNum)
  227. cornice = self.getCornice(aDNAFlatBuilding)
  228. self.printWallStyleWith(wall,cornice)
  229. def getPropType(self):
  230. return self.attributeDictionary['propType']
  231. def setPropType(self,dnaString):
  232. self.attributeDictionary['propType'] = dnaString
  233. def getPropTypes(self):
  234. return self.attributeDictionary['propTypes']
  235. def getSelectedLevelObject(self):
  236. return self.selectedLevelObject
  237. def getSnapAngle(self):
  238. return self.grid.getSnapAngle()
  239. def setSnapAngle(self, aFloat):
  240. self.grid.setSnapAngle(aFloat)
  241. def getWallColor(self):
  242. return self.attributeDictionary['wallColor']
  243. def setWallColor(self,aColor):
  244. self.attributeDictionary['wallColor'] = aColor
  245. def getWallColors(self):
  246. return self.attributeDictionary['wallColors']
  247. def getWallMenu(self):
  248. return wallMenu
  249. def getWallTexture(self):
  250. return self.attributeDictionary['wallTexture']
  251. def setWallTexture(self, texture):
  252. self.attributeDictionary['wallTexture'] = texture
  253. def getWallTextureDNA(self, dnaString):
  254. self.attributeDictionary['wallTexture'] = dnaString
  255. def getWallTextures(self):
  256. return self.attributeDictionary['wallTextures']
  257. def getWallWidth(self):
  258. return self.attributeDictionary['wallWidth']
  259. def setWallWidthVal(self,aFloat):
  260. self.attributeDictionary['wallWidth'] = aFloat
  261. def setWallWidthString(self, width):
  262. if width == 'fiveFt':
  263. self.setWallWidthVal(5.0)
  264. elif width == 'tenFt':
  265. self.setWallWidthVal(10.0)
  266. elif width == 'fifteenFt':
  267. self.setWallWidthVal(10.0)
  268. elif width == 'twentyFt':
  269. self.setWallWidthVal(10.0)
  270. elif width == 'twentyFiveFt':
  271. self.setWallWidthVal(10.0)
  272. def getWindowColor(self):
  273. return self.attributeDictionary['windowColor']
  274. def getWindowColors(self):
  275. return self.attributeDictionary['windowColors']
  276. def getWindowTexture(self):
  277. return self.attributeDictionary['windowTexture']
  278. def setWindowTexture(self,dnaString):
  279. self.attributeDictionary['windowTexture'] = dnaString
  280. def getWindowTextures(self):
  281. return self.attributeDictionary['windowTextures']
  282. def destroy(self):
  283. self.disable()
  284. self.removeNode()
  285. def disable(self):
  286. self.direct.deselectAll()
  287. self.reparentTo(hidden)
  288. self.hide()
  289. self.grid.ignore('insert')
  290. self.ignore('selectedNodePath')
  291. self.ignore('preRemoveNodePath')
  292. self.ignore('toggleMapViz')
  293. self.ignore('reparentNodePath')
  294. self.ignore('createNewLevelGroup')
  295. self.ignore('setNodePathName')
  296. self.ignore('manipulateObjectCleanup')
  297. self.ignore('SGESelectNodePath')
  298. self.ignore('SGEIsolateNodePath')
  299. self.ignore('SGEToggle VizNodePath')
  300. self.ignore('SGESet ParentNodePath')
  301. self.ignore('SGEAdd GroupNodePath')
  302. self.ignore('showAll')
  303. self.ignore('p')
  304. self.disableManipulation()
  305. def disableManipulation(self):
  306. # Disable handling of mouse events
  307. self.ignore('handleMouse3')
  308. self.ignore('handleMouse3Up')
  309. def editToontownCentral(self):
  310. self.levelMap.setPos(0.0,0.0,0.0)
  311. self.showMap('toontownCentral')
  312. self.useToontownCentralColors()
  313. self.styleDictionary = (
  314. self.attributeDictionary['toontownCentralStyleDictionary'])
  315. self.pieMenuDictionary['styleMenu'] = (
  316. self.pieMenuDictionary['toontownCentralStyleMenu'])
  317. self.attributeDictionary['streetTexture'] = 'street_street_tex'
  318. self.attributeDictionary['sidewalkTexture'] = 'street_sidewalk_tex'
  319. self.dnaOutputDir = 'ToontownCentral'
  320. self.dnaOutputFile = 'toontown_central_working.dna'
  321. self.panel.editMenu.selectitem('Toontown Central')
  322. def editDonaldsDock(self):
  323. self.levelMap.setPos(0.0,0.0,0.0)
  324. self.showMap('donaldsDock')
  325. self.useDonaldsDockColors()
  326. self.styleDictionary = (
  327. self.attributeDictionary['donaldsDockStyleDictionary'])
  328. self.pieMenuDictionary['styleMenu'] = (
  329. self.pieMenuDictionary['donaldsDockStyleMenu'])
  330. self.attributeDictionary['streetTexture'] = 'street_street_dock_tex'
  331. self.attributeDictionary['sidewalkTexture'] = (
  332. 'street_sidewalk_dock_tex')
  333. self.dnaOutputDir = 'DonaldsDock'
  334. self.dnaOutputFile = 'donalds_dock_working.dna'
  335. self.panel.editMenu.selectitem('Donalds Dock')
  336. def editMinniesMelodyLand(self):
  337. self.levelMap.setPos(0.0,0.0,0.0)
  338. self.showMap('minniesMelodyLand')
  339. self.useMinniesMelodyLandColors()
  340. self.styleDictionary = (
  341. self.attributeDictionary['minniesMelodyLandStyleDictionary'])
  342. self.pieMenuDictionary['styleMenu'] = (
  343. self.pieMenuDictionary['minniesMelodyLandStyleMenu'])
  344. self.attributeDictionary['streetTexture'] = 'street_street_dock_tex'
  345. self.attributeDictionary['sidewalkTexture'] = (
  346. 'street_sidewalk_dock_tex')
  347. self.dnaOutputDir = 'MinniesMelodyLand'
  348. self.dnaOutputFile = 'minnies_melody_land_working.dna'
  349. self.panel.editMenu.selectitem('Minnies Melody Land')
  350. def editTheBurrrgh(self):
  351. self.levelMap.setPos(0.0,0.0,0.0)
  352. self.showMap('theBurrrgh')
  353. self.useTheBurrrghColors()
  354. self.styleDictionary = (
  355. self.attributeDictionary['theBurrrghStyleDictionary'])
  356. self.pieMenuDictionary['styleMenu'] = (
  357. self.pieMenuDictionary['theBurrrghStyleMenu'])
  358. self.attributeDictionary['streetTexture'] = 'street_street_dock_tex'
  359. self.attributeDictionary['sidewalkTexture'] = (
  360. 'street_sidewalk_dock_tex')
  361. self.dnaOutputDir = 'TheBurrrgh'
  362. self.dnaOutputFile = 'the_burrrgh_working.dna'
  363. self.panel.editMenu.selectitem('The Burrrgh')
  364. def showMap(self, mapName):
  365. if self.activeMap:
  366. self.activeMap.reparentTo(hidden)
  367. self.activeMap = self.mapDictionary[mapName]
  368. self.activeMap.reparentTo(self.levelMap)
  369. def enable(self):
  370. self.reparentTo(render)
  371. self.show()
  372. self.accept('selectedNodePath', self.selectDNARoot)
  373. self.accept('preRemoveNodePath', self.preRemoveNodePath)
  374. self.accept('toggleMapViz', self.toggleMapViz)
  375. self.accept('reparentNodePath', self.reparentNodePath)
  376. self.accept('createNewLevelGroup', self.createNewLevelGroup)
  377. self.accept('setNodePathName', self.setNodePathName)
  378. self.accept('manipulateObjectCleanup', self.updateSelectedPose)
  379. self.accept('SGESelectNodePath', self.selectNodePath)
  380. #self.accept('SGESelectNodePath', self.flashNodePath)
  381. self.accept('SGEFlashNodePath', self.flashNodePath)
  382. self.accept('SGEIsolateNodePath', self.isolateNodePath)
  383. self.accept('SGEToggle VizNodePath', self.toggleNodePathViz)
  384. self.accept('SGESet ParentNodePath', self.setGroupParent)
  385. self.accept('SGEAdd GroupNodePath', self.addGroupToSelected)
  386. self.accept('showAll', self.showAll)
  387. self.accept('p',self.plantSelectedNodePath)
  388. self.enableManipulation()
  389. def enableManipulation(self):
  390. # Enable interactive placement of a nodePath
  391. # Turn off camera control
  392. base.disableMouse()
  393. # Handle mouse events for pie menus
  394. self.accept('handleMouse3',self.levelHandleMouse3)
  395. self.accept('handleMouse3Up',self.levelHandleMouse3Up)
  396. def useDriveMode(self):
  397. pos = base.camera.getPos()
  398. pos.setZ(4.0)
  399. hpr = base.camera.getHpr()
  400. hpr.set(hpr[0], 0.0, 0.0)
  401. t = base.camera.lerpPosHpr(pos, hpr, 1.0, blendType = 'easeInOut',
  402. task = 'manipulateCamera')
  403. # Note, if this dies an unatural death, this could screw things up
  404. t.uponDeath = self.switchToDriveMode
  405. def switchToDriveMode(self,state):
  406. self.direct.minimumConfiguration()
  407. self.disableManipulation()
  408. base.useDrive()
  409. # Make sure we're where we want to be
  410. pos = base.camera.getPos()
  411. pos.setZ(4.0)
  412. hpr = base.camera.getHpr()
  413. hpr.set(hpr[0], 0.0, 0.0)
  414. # Fine tune the drive mode
  415. base.mouseInterface.getBottomNode().setPos(pos)
  416. base.mouseInterface.getBottomNode().setHpr(hpr)
  417. base.mouseInterface.getBottomNode().setForwardSpeed(20.0)
  418. base.mouseInterface.getBottomNode().setReverseSpeed(20.0)
  419. def useDirectFly(self):
  420. base.disableMouse()
  421. self.enableManipulation()
  422. self.direct.enable()
  423. def useToontownCentralColors(self):
  424. self.attributeDictionary['wallColors'] = (
  425. self.colorPaletteDictionary['toontownCentralWallColors'])
  426. self.attributeDictionary['wallColor'] = (
  427. self.attributeDictionary['wallColors'][1])
  428. self.pieMenuDictionary['wallColorMenu'] = (
  429. self.pieMenuDictionary['toontownCentralWallColors'])
  430. self.attributeDictionary['windowColors'] = (
  431. self.colorPaletteDictionary['toontownCentralWindowColors'])
  432. self.attributeDictionary['windowColor'] = (
  433. self.attributeDictionary['windowColors'][1])
  434. self.pieMenuDictionary['windowColorMenu'] = (
  435. self.pieMenuDictionary['toontownCentralWindowColors'])
  436. self.attributeDictionary['doorColors'] = (
  437. self.colorPaletteDictionary['toontownCentralDoorColors'])
  438. self.attributeDictionary['doorColor'] = (
  439. self.attributeDictionary['doorColors'][1])
  440. self.pieMenuDictionary['doorColorMenu'] = (
  441. self.pieMenuDictionary['toontownCentralDoorColors'])
  442. self.attributeDictionary['corniceColors'] = (
  443. self.colorPaletteDictionary['toontownCentralCorniceColors'])
  444. self.attributeDictionary['corniceColor'] = (
  445. self.attributeDictionary['corniceColors'][1])
  446. self.pieMenuDictionary['corniceColorMenu'] = (
  447. self.pieMenuDictionary['toontownCentralCorniceColors'])
  448. def useDonaldsDockColors(self):
  449. self.attributeDictionary['wallColors'] = (
  450. self.colorPaletteDictionary['donaldsDockWallColors'])
  451. self.attributeDictionary['wallColor'] = (
  452. self.attributeDictionary['wallColors'][1])
  453. self.pieMenuDictionary['wallColorMenu'] = (
  454. self.pieMenuDictionary['donaldsDockWallColors'])
  455. self.attributeDictionary['windowColors'] = (
  456. self.colorPaletteDictionary['donaldsDockWindowColors'])
  457. self.attributeDictionary['windowColor'] = (
  458. self.attributeDictionary['windowColors'][1])
  459. self.pieMenuDictionary['windowColorMenu'] = (
  460. self.pieMenuDictionary['donaldsDockWindowColors'])
  461. self.attributeDictionary['doorColors'] = (
  462. self.colorPaletteDictionary['donaldsDockDoorColors'])
  463. self.attributeDictionary['doorColor'] = (
  464. self.attributeDictionary['doorColors'][1])
  465. self.pieMenuDictionary['doorColorMenu'] = (
  466. self.pieMenuDictionary['donaldsDockDoorColors'])
  467. self.attributeDictionary['corniceColors'] = (
  468. self.colorPaletteDictionary['donaldsDockCorniceColors'])
  469. self.attributeDictionary['corniceColor'] = (
  470. self.attributeDictionary['corniceColors'][1])
  471. self.pieMenuDictionary['corniceColorMenu'] = (
  472. self.pieMenuDictionary['donaldsDockCorniceColors'])
  473. def useTheBurrrghColors(self):
  474. self.attributeDictionary['wallColors'] = (
  475. self.colorPaletteDictionary['theBurrrghWallColors'])
  476. self.attributeDictionary['wallColor'] = (
  477. self.attributeDictionary['wallColors'][1])
  478. self.pieMenuDictionary['wallColorMenu'] = (
  479. self.pieMenuDictionary['theBurrrghWallColors'])
  480. self.attributeDictionary['windowColors'] = (
  481. self.colorPaletteDictionary['theBurrrghWindowColors'])
  482. self.attributeDictionary['windowColor'] = (
  483. self.attributeDictionary['windowColors'][1])
  484. self.pieMenuDictionary['windowColorMenu'] = (
  485. self.pieMenuDictionary['theBurrrghWindowColors'])
  486. self.attributeDictionary['doorColors'] = (
  487. self.colorPaletteDictionary['theBurrrghDoorColors'])
  488. self.attributeDictionary['doorColor'] = (
  489. self.attributeDictionary['doorColors'][1])
  490. self.pieMenuDictionary['doorColorMenu'] = (
  491. self.pieMenuDictionary['theBurrrghDoorColors'])
  492. self.attributeDictionary['corniceColors'] = (
  493. self.colorPaletteDictionary['theBurrrghCorniceColors'])
  494. self.attributeDictionary['corniceColor'] = (
  495. self.attributeDictionary['corniceColors'][1])
  496. self.pieMenuDictionary['corniceColorMenu'] = (
  497. self.pieMenuDictionary['theBurrrghCorniceColors'])
  498. def useMinniesMelodyLandColors(self):
  499. self.attributeDictionary['wallColors'] = (
  500. self.colorPaletteDictionary['minniesMelodyLandWallColors'])
  501. self.attributeDictionary['wallColor'] = (
  502. self.attributeDictionary['wallColors'][1])
  503. self.pieMenuDictionary['wallColorMenu'] = (
  504. self.pieMenuDictionary['minniesMelodyLandWallColors'])
  505. self.attributeDictionary['windowColors'] = (
  506. self.colorPaletteDictionary['minniesMelodyLandWindowColors'])
  507. self.attributeDictionary['windowColor'] = (
  508. self.attributeDictionary['windowColors'][1])
  509. self.pieMenuDictionary['windowColorMenu'] = (
  510. self.pieMenuDictionary['minniesMelodyLandWindowColors'])
  511. self.attributeDictionary['doorColors'] = (
  512. self.colorPaletteDictionary['minniesMelodyLandDoorColors'])
  513. self.attributeDictionary['doorColor'] = (
  514. self.attributeDictionary['doorColors'][1])
  515. self.pieMenuDictionary['doorColorMenu'] = (
  516. self.pieMenuDictionary['minniesMelodyLandDoorColors'])
  517. self.attributeDictionary['corniceColors'] = (
  518. self.colorPaletteDictionary['minniesMelodyLandCorniceColors'])
  519. self.attributeDictionary['corniceColor'] = (
  520. self.attributeDictionary['corniceColors'][1])
  521. self.pieMenuDictionary['corniceColorMenu'] = (
  522. self.pieMenuDictionary['minniesMelodyLandCorniceColors'])
  523. def addCollisionSphere(self):
  524. sphere = self.vizRegion.attachNewNode(NamedNode('vizSphere'))
  525. instance = self.vizSphere.instanceTo(sphere)
  526. instance.setScale(20.0 * math.sqrt(2))
  527. if (self.vizRegion.getNumChildren() > 1):
  528. sphere.setPos(vizRegion.getChild(vizRegion.getNumChildren() - 2),
  529. 40.0,0.0,0.0)
  530. else:
  531. sphere.setPos(0,0,0)
  532. self.selectNodePath(sphere)
  533. def addVizRegion(self):
  534. self.vizRegionCount = self.vizRegionCount + 1
  535. self.vizRegion = self.vizObjects.attachNewNode(
  536. NamedNode('vizRegion' + `self.vizRegionCount`))
  537. self.addCollisionSphere()
  538. # Start with region selected
  539. self.selectNodePath(vizRegion)
  540. def setHprSnap(self,flag):
  541. self.hprSnap = flag
  542. def isolateSelectedNodePath(self):
  543. if self.direct.selected.last:
  544. self.isolateNodePath(self.direct.selected.last)
  545. def isolateNodePath(self,aNodePath):
  546. # First show everything in level
  547. self.levelObjects.showAllDescendants()
  548. render.hideCollisionSolids()
  549. aNodePath.hideSiblings()
  550. def selectDNARoot(self, aNodePath):
  551. # If this isn't a root object see if one exists above it
  552. if (aNodePath.getName()[-8:] != '_DNARoot'):
  553. dnaRoot = self.getDNARoot(aNodePath)
  554. # Is this a DNA object?
  555. if dnaRoot:
  556. # Yes! Select root
  557. self.direct.select(dnaRoot)
  558. def getDNARoot(self, aNodePath):
  559. if not aNodePath.hasParent():
  560. return 0
  561. name = aNodePath.getName()
  562. if (name[-8:] == '_DNARoot'):
  563. return aNodePath
  564. else:
  565. return self.getDNARoot(aNodePath.getParent())
  566. def updateSelectedPose(self):
  567. # Move grid to line up with object
  568. for selectedNode in self.direct.selected:
  569. if self.levelDictionary.has_key(selectedNode.id()):
  570. # First snap to grid
  571. pos = selectedNode.getPos(self.grid)
  572. snapPos = self.grid.computeSnapPoint(pos)
  573. selectedNode.setPos(self.grid, snapPos[0], snapPos[1], 0)
  574. # Angle snap
  575. self.lastAngle = self.grid.computeSnapAngle(
  576. selectedNode.getH(self.grid))
  577. selectedNode.setH(self.grid, self.lastAngle)
  578. # Update DNA
  579. self.updateDNAPosHpr(selectedNode)
  580. # If this node is the last selected reposition grid
  581. if selectedNode == self.direct.selected.last:
  582. # Position grid for placing next object
  583. self.autoPositionGrid()
  584. def levelHandleMouse3(self):
  585. # If nothing selected, just return
  586. if not self.direct.selected.last:
  587. return
  588. # Otherwise, find its dictionary entry
  589. self.selectedLevelObject = (
  590. self.getLevelObject(self.direct.selected.last))
  591. # If not None, determine interaction type
  592. if self.selectedLevelObject:
  593. selectedObjectDNA = self.selectedLevelObject['DNA']
  594. # Default target/menu
  595. target = None
  596. menuType = None
  597. # Interaction type depends on selected object's class
  598. objClass = selectedObjectDNA.__class__.getClassType()
  599. if objClass.eq(DNAFlatBuilding.getClassType()):
  600. # Where are we hitting the building?
  601. hitPt = self.getWallIntersectionPoint()
  602. if hitPt:
  603. xPt = hitPt[0]
  604. zPt = hitPt[2]
  605. # Which wall are we pointing at (if any)
  606. wallNum = self.getWallNum(selectedObjectDNA, zPt)
  607. # How wide is the selected wall?
  608. wallWidth = selectedObjectDNA.getWidth()
  609. # Menu mode depends on where we are pointing
  610. if (zPt > self.getWallHeights(selectedObjectDNA)[-1:][0]):
  611. menuMode = 'cornice'
  612. else:
  613. if (xPt < 0.0):
  614. menuMode = 'window'
  615. elif (xPt > wallWidth):
  616. menuMode = 'misc'
  617. elif ((xPt >= 0.0) & (xPt <= wallWidth)):
  618. menuMode = 'wall'
  619. if menuMode == 'wall':
  620. if wallNum != -1:
  621. selectedWall = (
  622. self.getWall(selectedObjectDNA, wallNum))
  623. # Default is wall type menu
  624. menuType = 'style'
  625. target = selectedWall
  626. # If shift, switch wall texture
  627. if self.direct.fShift:
  628. menuType = 'wall'
  629. # If alt, switch to wall orientation menu
  630. if self.direct.fAlt:
  631. menuType = 'orientation'
  632. # If control, switch to wall color menu
  633. if self.direct.fControl:
  634. menuType = 'wallColor'
  635. else:
  636. target = None
  637. elif menuMode == 'window':
  638. if wallNum != -1:
  639. selectedWall = (
  640. self.getWall(selectedObjectDNA, wallNum))
  641. # Default is window type menu
  642. menuType = 'window'
  643. target = self.getWindow(selectedWall,0)
  644. # If alt, switch to window orientation menu
  645. if self.direct.fAlt:
  646. menuType = 'upOrientation'
  647. if self.direct.fShift:
  648. menuType = 'numWindows'
  649. target = selectedWall
  650. if self.direct.fControl:
  651. menuType = 'windowColor'
  652. elif menuMode == 'cornice':
  653. menuType = 'cornice'
  654. target = self.getCornice(selectedObjectDNA)
  655. if self.direct.fAlt:
  656. menuType = 'upOrientation'
  657. if self.direct.fControl:
  658. menuType = 'corniceColor'
  659. elif menuMode == 'misc':
  660. menuType = 'wallWidth'
  661. target = selectedObjectDNA
  662. else:
  663. target = None
  664. elif objClass.eq(DNALandmarkBuilding.getClassType()):
  665. menuType = 'door'
  666. target = self.getDoor(selectedObjectDNA)
  667. if self.direct.fAlt:
  668. menuType = 'upOrientation'
  669. if self.direct.fControl:
  670. menuType = 'doorColor'
  671. elif objClass.eq(DNAProp.getClassType()):
  672. menuType = 'propType'
  673. target = selectedObjectDNA
  674. if self.direct.fControl:
  675. menuType = 'propColor'
  676. # Now spawn apropriate menu task
  677. if ((target != None) | (menuType == 'cornice')):
  678. self.spawnMenuTask(menuType, target)
  679. def levelHandleMouse3Up(self):
  680. if self.activeMenu:
  681. self.activeMenu.removePieMenuTask()
  682. def flashNodePath(self, aNodePath):
  683. taskMgr.removeTasksNamed('flashNodePath')
  684. t = Task.Task(self.flashNodePathTask)
  685. t.aNodePath = aNodePath
  686. t.initState = t.hidden = aNodePath.isHidden()
  687. t.flashCount = 0
  688. t.frameCount = 0
  689. t.uponDeath = self.preSelectDone
  690. taskMgr.spawnTaskNamed(t, 'flashNodePath')
  691. def flashNodePathTask(self, state):
  692. aNodePath = state.aNodePath
  693. initState = state.initState
  694. hidden = state.hidden
  695. flashCount = state.flashCount
  696. frameCount = state.frameCount
  697. if (flashCount < 4):
  698. if (frameCount % 3) == 0:
  699. if hidden:
  700. aNodePath.show()
  701. else:
  702. aNodePath.hide()
  703. state.hidden = not state.hidden
  704. state.flashCount = flashCount + 1
  705. state.frameCount = frameCount + 1
  706. return Task.cont
  707. else:
  708. return Task.done
  709. def preSelectDone(self,state):
  710. if state.initState:
  711. state.aNodePath.hide()
  712. else:
  713. state.aNodePath.show()
  714. def showAll(self):
  715. self.levelObjects.showAllDescendants()
  716. render.hideCollisionSolids()
  717. def showGrid(self,flag):
  718. if flag:
  719. self.grid.enable()
  720. else:
  721. self.grid.disable()
  722. def spawnMenuTask(self, menu, aDNAObject):
  723. # Record the starting window code and targetDNAObject
  724. # This will be used by pieMenu action selector
  725. self.targetDNAObject = aDNAObject
  726. # Update panel's color if appropriate
  727. if aDNAObject:
  728. targetClass = self.targetDNAObject.__class__.getClassType()
  729. if ((targetClass.eq(DNAWall.getClassType())) |
  730. (targetClass.eq(DNAWindows.getClassType())) |
  731. (targetClass.eq(DNACornice.getClassType()))):
  732. self.panel.setCurrentColor(self.targetDNAObject.getColor())
  733. # What kind of menu is it?
  734. if menu == 'wall':
  735. self.activeMenu = self.pieMenuDictionary['wallMenu']
  736. state = self.getDNAString(aDNAObject)
  737. elif menu == 'window':
  738. self.activeMenu = self.pieMenuDictionary['windowMenu']
  739. state = self.getDNAString(aDNAObject)
  740. elif menu == 'orientation':
  741. self.activeMenu = self.pieMenuDictionary['orientationMenu']
  742. dnaString = self.getDNAString(aDNAObject)
  743. state = dnaString[-3:]
  744. elif menu == 'upOrientation':
  745. self.activeMenu = self.pieMenuDictionary['upOrientationMenu']
  746. if aDNAObject:
  747. dnaString = self.getDNAString(aDNAObject)
  748. state = dnaString[-3:]
  749. else:
  750. state = None
  751. elif menu == 'numWindows':
  752. self.activeMenu = self.pieMenuDictionary['numWindowsMenu']
  753. state = self.getWindow(aDNAObject, 0).getWindowCount()
  754. elif menu == 'cornice':
  755. self.activeMenu = self.pieMenuDictionary['corniceMenu']
  756. if aDNAObject:
  757. state = self.getDNAString(aDNAObject)
  758. else:
  759. state = None
  760. elif menu == 'door':
  761. self.activeMenu = self.pieMenuDictionary['doorMenu']
  762. state = self.getDNAString(aDNAObject)
  763. elif menu == 'wallWidth':
  764. self.activeMenu = self.pieMenuDictionary['wallWidthMenu']
  765. state = aDNAObject.getWidth()
  766. elif menu == 'wallColor':
  767. self.activeMenu = self.pieMenuDictionary['wallColorMenu']
  768. self.activeColors = self.getWallColors()
  769. state = aDNAObject.getColor()
  770. elif menu == 'windowColor':
  771. self.activeMenu = self.pieMenuDictionary['windowColorMenu']
  772. self.activeColors = self.getWindowColors()
  773. state = aDNAObject.getColor()
  774. elif menu == 'doorColor':
  775. self.activeMenu = self.pieMenuDictionary['doorColorMenu']
  776. self.activeColors = self.getDoorColors()
  777. state = aDNAObject.getColor()
  778. elif menu == 'corniceColor':
  779. self.activeMenu = self.pieMenuDictionary['corniceColorMenu']
  780. self.activeColors = self.getCorniceColors()
  781. state = aDNAObject.getColor()
  782. elif menu == 'propColor':
  783. self.activeMenu = self.pieMenuDictionary['wallColorMenu']
  784. self.activeColors = self.getWallColors()
  785. state = aDNAObject.getColor()
  786. elif menu == 'propType':
  787. self.activeMenu = self.pieMenuDictionary['propTypesMenu']
  788. state = self.getDNAString(aDNAObject)
  789. elif menu == 'style':
  790. self.activeMenu = self.pieMenuDictionary['styleMenu']
  791. state = 1
  792. # Store initial state in case you need to restore it on menu cancel
  793. self.activeMenu.setInitialState(state)
  794. # Spawn the menu task
  795. self.activeMenu.spawnPieMenuTask()
  796. def toggleMapViz(self, flag):
  797. if flag:
  798. self.levelMap.reparentTo(self)
  799. else:
  800. self.levelMap.reparentTo(hidden)
  801. def toggleNodePathViz(self, aNodePath):
  802. # First kill the flashing task
  803. taskMgr.removeTasksNamed('flashNodePath')
  804. if aNodePath.isHidden():
  805. aNodePath.show()
  806. else:
  807. aNodePath.hide()
  808. def setXyzSnap(self, flag):
  809. self.grid.setXyzSnap(flag)
  810. if flag:
  811. self.autoPositionGrid()
  812. def addStyle(self, dictionary, key, wallTexture, wallColor, windowTexture,
  813. windowColor, corniceTexture, corniceColor):
  814. style = {}
  815. style['wallTexture'] = wallTexture
  816. color = VBase4(wallColor)
  817. style['wallColor'] = color
  818. style['windowTexture'] = windowTexture
  819. color = VBase4(windowColor)
  820. style['windowColor'] = color
  821. style['corniceTexture'] = corniceTexture
  822. color = None
  823. if corniceColor:
  824. color = VBase4(corniceColor)
  825. style['corniceColor'] = color
  826. dictionary[key] = style
  827. def createColorMenu(self, menuName, colorArray):
  828. # Create the new one
  829. numberNodes = []
  830. # Add in common grey scale colors
  831. adjustedColorArray = (
  832. [VBase4(1,1,1,1)] +
  833. colorArray +
  834. [VBase4(0.75, 0.75, 0.75, 1.0 ),
  835. VBase4(0.5, 0.5, 0.5, 1.0),
  836. VBase4(0.25, 0.25, 0.25, 1.0)]
  837. )
  838. for i in range(len(adjustedColorArray)):
  839. node = OnscreenText(' ', 0.0, 0.0)
  840. numberNodes.append(node)
  841. node.setColor(adjustedColorArray[i])
  842. numItems = len(numberNodes)
  843. # Attach it to hidden for now
  844. newColorMenu = hidden.attachNewNode(NamedNode(menuName + 'Menu'))
  845. # Attach the color chips to the new menu and adjust sizes
  846. radius = 0.7
  847. angle = deg2Rad(360.0/float(numItems))
  848. for i in range (numItems):
  849. # Get the node
  850. node = numberNodes[i]
  851. node.setScale(node.getScale() * 2.0)
  852. # Reposition it
  853. node.setXY(radius * math.cos(i * angle),
  854. (radius *
  855. (self.direct.chan.width /
  856. float(self.direct.chan.height)) *
  857. math.sin(i * angle)))
  858. # Add it to the wallColorMenu
  859. node.reparentTo(newColorMenu)
  860. # Scale the whole shebang down by 0.5
  861. newColorMenu.setScale(0.5)
  862. # Store menu and colors in appropriate dictionarys
  863. self.pieMenuDictionary[menuName] = (
  864. PieMenu(self.direct, newColorMenu, self.updateColorIndex))
  865. self.colorPaletteDictionary[menuName] = adjustedColorArray
  866. def createColorMenusFromFile(self, prefix):
  867. dict = self.createColorDictionaryFromFile(
  868. 'level_editor/' + prefix + 'Colors.txt')
  869. self.colorPaletteDictionary[prefix + 'Colors'] = dict
  870. self.createColorMenu(prefix + 'WallColors', dict['wallColors'])
  871. self.createColorMenu(prefix + 'WindowColors', dict['windowColors'])
  872. self.createColorMenu(prefix + 'DoorColors', dict['doorColors'])
  873. self.createColorMenu(prefix + 'CorniceColors', dict['corniceColors'])
  874. def createColorDictionaryFromFile(self, filename):
  875. print 'Loading Color Palettes from: ' + filename
  876. f = Filename(filename)
  877. f.resolveFilename(getModelPath())
  878. f = open(f.toOsSpecific(), 'r')
  879. rawData = f.readlines()
  880. f.close()
  881. dict = {}
  882. wallColors = []
  883. windowColors = []
  884. doorColors = []
  885. corniceColors = []
  886. for line in rawData:
  887. l = string.strip(line)
  888. if l:
  889. if l[:4] == 'wall':
  890. wallColors.append(eval(l[11:]))
  891. elif l[:4] == 'wind':
  892. windowColors.append(eval(l[13:]))
  893. elif l[:4] == 'door':
  894. doorColors.append(eval(l[11:]))
  895. elif l[:4] == 'corn':
  896. corniceColors.append(eval(l[14:]))
  897. dict['wallColors'] = wallColors
  898. dict['windowColors'] = windowColors
  899. dict['doorColors'] = doorColors
  900. dict['corniceColors'] = corniceColors
  901. return dict
  902. def printColorDictionary(self, dict):
  903. for color in dict['wallColors']:
  904. print ('wallColor: Vec4(%.2f, %.2f, %.2f, 1.0)' %
  905. (color[0], color[1], color[2]))
  906. for color in dict['windowColors']:
  907. print ('windowColor: Vec4(%.2f, %.2f, %.2f, 1.0)' %
  908. (color[0], color[1], color[2]))
  909. for color in dict['doorColors']:
  910. print ('doorColor: Vec4(%.2f, %.2f, %.2f, 1.0)' %
  911. (color[0], color[1], color[2]))
  912. for color in dict['corniceColors']:
  913. print ('corniceColor: Vec4(%.2f, %.2f, %.2f, 1.0)' %
  914. (color[0], color[1], color[2]))
  915. def createColorMenus(self):
  916. self.createColorMenusFromFile('toontownCentral')
  917. self.createColorMenusFromFile('donaldsDock')
  918. self.createColorMenusFromFile('theBurrrgh')
  919. self.createColorMenusFromFile('minniesMelodyLand')
  920. # Use the toontown color set
  921. self.useToontownCentralColors()
  922. def createCorniceMenu(self):
  923. # Get the currently available window options
  924. numItems = len(self.getCorniceTextures())
  925. newCorniceMenu = hidden.attachNewNode(NamedNode('corniceMenu'))
  926. # Attach an empty node for first item
  927. newCorniceMenu.attachNewNode(NamedNode('no cornice'))
  928. angle = deg2Rad(360.0/numItems)
  929. # Note: start at 2 to skip first item (none)
  930. for i in range(1, numItems):
  931. # Get the node
  932. node = self.dnaStore.findNode(self.getCorniceTextures()[i])
  933. # Add it to the window menu
  934. path = node.instanceTo(newCorniceMenu)
  935. # Place menu nodes in a circle, offset each in X and Z
  936. # by half node width/height (.5 * path scale)
  937. path.setPos(0.75 * math.cos(i * angle),
  938. 0.0,
  939. (0.75 *
  940. (self.direct.chan.width /
  941. float(self.direct.chan.height)) *
  942. math.sin(i * angle)))
  943. path.setScale(0.5)
  944. # Scale the whole shebang down by 0.5
  945. newCorniceMenu.setScale(0.5)
  946. return newCorniceMenu
  947. def createDoorMenu(self):
  948. # Get the currently available door options
  949. numItems = len(self.getDoorTextures())
  950. newDoorMenu = hidden.attachNewNode(NamedNode('doorMenu'))
  951. angle = deg2Rad(360.0/float(numItems))
  952. for i in range(numItems):
  953. # Get the node
  954. node = self.dnaStore.findNode(self.getDoorTextures()[i])
  955. # Add it to the door menu
  956. path = node.instanceTo(newDoorMenu)
  957. # Place menu nodes in a circle, offset each in X and Z
  958. # by half node width/height (.5 * path scale)
  959. path.setPos(0.75 * math.cos(i * angle) - 0.025,
  960. 0.0,
  961. ((0.75 *
  962. (self.direct.chan.width/
  963. float(self.direct.chan.height)) *
  964. math.sin(i * angle)) - 0.025))
  965. path.setScale(0.05)
  966. # Scale the whole shebang down by 0.5
  967. newDoorMenu.setScale(0.5)
  968. return newDoorMenu
  969. def createNumWindowsMenu(self):
  970. numberNodes = []
  971. for i in range(4):
  972. node = OnscreenText(`i`, 0.0, 0.0)
  973. numberNodes.append(node)
  974. numItems = len(numberNodes)
  975. newNumWindowsMenu = hidden.attachNewNode(NamedNode('numWindowsMenu'))
  976. radius = 0.7
  977. angle = deg2Rad(360.0/numItems)
  978. for i in range(numItems):
  979. # Get the node
  980. node = numberNodes[i]
  981. node.setScale(node.getScale() * 4.0)
  982. # Reposition it
  983. node.setXY(radius * math.cos(i * angle),
  984. (radius *
  985. (self.direct.chan.width/
  986. float(self.direct.chan.height)) *
  987. math.sin(i * angle)))
  988. # Add it to the numWindowsMenu
  989. node.reparentTo(newNumWindowsMenu)
  990. # Scale the whole shebang down by 0.5
  991. newNumWindowsMenu.setScale(0.5)
  992. return newNumWindowsMenu
  993. def createOrientationMenu(self):
  994. newOrientationMenu = hidden.attachNewNode(NamedNode('orientationMenu'))
  995. radius = 0.5
  996. node = OnscreenText('UR',radius,radius)
  997. node.setScale(node.getScale() * 3.0)
  998. node.reparentTo(newOrientationMenu)
  999. node = OnscreenText('UL',-radius,radius)
  1000. node.setScale(node.getScale() * 3.0)
  1001. node.reparentTo(newOrientationMenu)
  1002. node = OnscreenText('DL',-radius, -radius)
  1003. node.setScale(node.getScale() * 3.0)
  1004. node.reparentTo(newOrientationMenu)
  1005. node = OnscreenText('DR',radius,-radius)
  1006. node.setScale(node.getScale() * 3.0)
  1007. node.reparentTo(newOrientationMenu)
  1008. # Scale the whole shebang down by radius
  1009. newOrientationMenu.setScale(radius)
  1010. return newOrientationMenu
  1011. def createPropTypesMenu(self):
  1012. numItems = len(self.getPropTypes())
  1013. propNodes = []
  1014. for i in range (numItems):
  1015. node = OnscreenText(self.getPropTypes()[i],0,0)
  1016. propNodes.append(node)
  1017. newPropTypeMenu = hidden.attachNewNode(NamedNode('propTypeMenu'))
  1018. radius = 0.7
  1019. angle = deg2Rad(360.0/numItems)
  1020. for i in range (numItems):
  1021. # Get the node
  1022. node = propNodes[i]
  1023. node.setScale(node.getScale())
  1024. # Reposition it
  1025. node.setXY(radius * math.cos(i * angle),
  1026. (radius *
  1027. (self.direct.chan.width/
  1028. float(self.direct.chan.height)) *
  1029. math.sin(i * angle)))
  1030. # Add it to the propTypeMenu
  1031. node.reparentTo(newPropTypeMenu)
  1032. # Scale the whole shebang down by 0.5
  1033. newPropTypeMenu.setScale(0.5)
  1034. return newPropTypeMenu
  1035. def createStyleSample(self, style, num):
  1036. # Create a wall
  1037. wall = DNAWall('wall')
  1038. wall.setCode(self.dnaStore.findCode(style['wallTexture']))
  1039. wall.setColor(style['wallColor'])
  1040. wall.setHeight(10.0)
  1041. # Add its windows
  1042. windows = DNAWindows('windows')
  1043. windows.setWindowCount(2)
  1044. windows.setCode(self.dnaStore.findCode(style['windowTexture']))
  1045. windows.setColor(style['windowColor'])
  1046. wall.add(windows)
  1047. # And a cornice if necessary
  1048. corniceTexture = style['corniceTexture']
  1049. if corniceTexture:
  1050. cornice = DNACornice('cornice')
  1051. cornice.setCode(self.getDNACode(corniceTexture))
  1052. cornice.setColor(style['corniceColor'])
  1053. wall.add(cornice)
  1054. # The final building
  1055. bldg = DNAFlatBuilding('style' + `num`)
  1056. bldg.add(wall)
  1057. bldg.setWidth(12.0)
  1058. return bldg.traverse(hidden, self.dnaStore)
  1059. def createStyleMenuWith(self, dictionary):
  1060. numItems = len(dictionary)
  1061. newStyleMenu = hidden.attachNewNode(NamedNode('styleMenu'))
  1062. radius = 0.7
  1063. angle = deg2Rad(360.0/numItems)
  1064. for i in range(numItems):
  1065. # Get the node
  1066. node = self.createStyleSample(dictionary[i], i)
  1067. node.setScale(0.03)
  1068. # Reposition it
  1069. node.setPos(radius * math.cos(i * angle),
  1070. 0.0,
  1071. (radius *
  1072. (self.direct.chan.width/
  1073. float(self.direct.chan.height)) *
  1074. math.sin(i * angle)))
  1075. # Add it to the styleMenu
  1076. node.reparentTo(newStyleMenu)
  1077. # Scale the whole shebang down by 0.5
  1078. newStyleMenu.setScale(0.5)
  1079. return newStyleMenu
  1080. def createUpOrientationMenu(self):
  1081. newUpOrientationMenu = (
  1082. hidden.attachNewNode(NamedNode('upOrientationMenu')))
  1083. radius = 0.5
  1084. node = OnscreenText('UR',radius, radius)
  1085. node.setScale(node.getScale() * 3.0)
  1086. node.reparentTo(newUpOrientationMenu)
  1087. node = OnscreenText('UL',-radius, radius)
  1088. node.setScale(node.getScale() * 3.0)
  1089. node.reparentTo(newUpOrientationMenu)
  1090. node = newUpOrientationMenu.attachNewNode(NamedNode('hiddenNode'))
  1091. node.setScale(node.getScale() * 3.0)
  1092. node = newUpOrientationMenu.attachNewNode(NamedNode('hiddenNode'))
  1093. node.setScale(node.getScale() * 3.0)
  1094. # Scale the whole shebang down by radius
  1095. newUpOrientationMenu.setScale(radius)
  1096. return newUpOrientationMenu
  1097. def createWallMenu(self):
  1098. numItems = len(self.getWallTextures())
  1099. newWallMenu = hidden.attachNewNode(NamedNode('wallMenu'))
  1100. angle = deg2Rad(360.0/numItems)
  1101. for i in range(numItems):
  1102. node = self.dnaStore.findNode(self.getWallTextures()[i])
  1103. path = node.instanceTo(newWallMenu)
  1104. # Place menu nodes in a circle, offset each in X and Z by
  1105. # half node width/height (.5 * path scale)
  1106. path.setPos(0.75 * math.cos(i * angle) - 0.15,
  1107. 0.0,
  1108. (0.75 *
  1109. (self.direct.chan.width/
  1110. float(self.direct.chan.height)) *
  1111. math.sin(i * angle) - 0.15))
  1112. path.setScale(0.25)
  1113. # Scale the whole shebang down by 0.5
  1114. newWallMenu.setScale(0.5)
  1115. return newWallMenu
  1116. def createWallWidthMenu(self):
  1117. numberNodes = []
  1118. self.wallWidths = [5, 10, 15, 15.607, 20, 20.706, 25]
  1119. widthsAsText = ['5', '10', '15', '15.6', '20', '20.7', '25']
  1120. for width in widthsAsText:
  1121. node = OnscreenText(width,0,0)
  1122. numberNodes.append(node)
  1123. numItems = len(numberNodes)
  1124. newWallWidthMenu = hidden.attachNewNode(NamedNode('wallWidthMenu'))
  1125. radius = 0.7
  1126. angle = deg2Rad(360.0/numItems)
  1127. for i in range(numItems):
  1128. # Get the node
  1129. node = numberNodes[i]
  1130. node.setScale(node.getScale()* 4.0)
  1131. # Reposition it
  1132. node.setXY(radius * math.cos(i * angle),
  1133. (radius *
  1134. (self.direct.chan.width/
  1135. float(self.direct.chan.height)) *
  1136. math.sin(i * angle)))
  1137. # Add it to the wallWidthMenu
  1138. node.reparentTo(newWallWidthMenu)
  1139. # Scale the whole shebang down by 0.5
  1140. newWallWidthMenu.setScale(0.5)
  1141. return newWallWidthMenu
  1142. def createWindowMenu(self):
  1143. # Get the currently available window options
  1144. numItems = len(self.getWindowTextures())
  1145. newWindowMenu = hidden.attachNewNode(NamedNode('windowMenu'))
  1146. angle = deg2Rad(360.0/numItems)
  1147. for i in range(numItems):
  1148. # Get the node
  1149. node = self.dnaStore.findNode(self.getWindowTextures()[i])
  1150. # Add it to the window menu
  1151. path = node.instanceTo(newWindowMenu)
  1152. # Place menu nodes in a circle, offset each in X and Z by
  1153. # half node width/height (.5 * path scale)
  1154. path.setPos(0.75 * math.cos(i * angle) - 0.05,
  1155. 0.0,
  1156. (0.75 *
  1157. (self.direct.chan.width/
  1158. float(self.direct.chan.height)) *
  1159. math.sin(i * angle) - 0.05))
  1160. path.setScale(0.1)
  1161. # Scale the whole shebang down by 0.5
  1162. newWindowMenu.setScale(0.5)
  1163. return newWindowMenu
  1164. def createStyleDictionaryFromFile(self, filename):
  1165. print 'Loading style from: ' + filename
  1166. styleData = self.getStyleData(filename)
  1167. styleDictionary = {}
  1168. styleCount = 0
  1169. while styleData:
  1170. style, styleData = self.getStyleFromStyleData(styleData)
  1171. styleDictionary[styleCount] = style
  1172. styleCount = styleCount + 1
  1173. return styleDictionary
  1174. def getStyleData(self, filename):
  1175. f = Filename(filename)
  1176. f.resolveFilename(getModelPath())
  1177. f = open(f.toOsSpecific(), 'r')
  1178. rawData = f.readlines()
  1179. f.close()
  1180. styleData = []
  1181. for line in rawData:
  1182. l = string.strip(line)
  1183. if l:
  1184. styleData.append(l)
  1185. return styleData
  1186. def getStyleFromStyleData(self, styleData):
  1187. style = {}
  1188. # Wall
  1189. style['wallTexture'] = string.strip(styleData[0][12:])
  1190. style['wallColor'] = eval(styleData[1][10:])
  1191. # Window Texture
  1192. texture = string.strip(styleData[2][14:])
  1193. if texture == 'None':
  1194. style['windowTexture'] = None
  1195. else:
  1196. style['windowTexture'] = texture
  1197. # Window Color
  1198. color = string.strip(styleData[3][12:])
  1199. if color == 'None':
  1200. style['windowColor'] = None
  1201. else:
  1202. style['windowColor'] = eval(color,globals())
  1203. # Cornice Texture
  1204. texture = string.strip(styleData[4][15:])
  1205. if texture == 'None':
  1206. style['corniceTexture'] = None
  1207. else:
  1208. style['corniceTexture'] = texture
  1209. # Cornice Color
  1210. color = string.strip(styleData[5][13:])
  1211. if color == 'None':
  1212. style['corniceColor'] = None
  1213. else:
  1214. style['corniceColor'] = eval(color,globals())
  1215. # Result
  1216. return style, styleData[6:]
  1217. def initializePieMenus(self):
  1218. # Clear out any old menus just in case
  1219. for key in self.pieMenuDictionary.keys():
  1220. oldMenu = self.pieMenuDictionary[key]
  1221. oldMenu.reparentTo(hidden)
  1222. oldMenu.removeNode()
  1223. # Get list of available attributes
  1224. self.initializeAttributeDictionary()
  1225. # Create pop-up pie menus
  1226. self.pieMenuDictionary['wallMenu'] = (
  1227. PieMenu(self.direct, self.createWallMenu(),
  1228. self.updateWallTextureNum))
  1229. self.pieMenuDictionary['windowMenu'] = (
  1230. PieMenu(self.direct, self.createWindowMenu(),
  1231. self.updateWindowTextureNum))
  1232. menu = PieMenu(self.direct, self.createOrientationMenu(),
  1233. self.updateOrientationNum)
  1234. # Clear angle offset on this menu
  1235. menu.setItemOffset(0.0)
  1236. self.pieMenuDictionary['orientationMenu'] = menu
  1237. menu = PieMenu(self.direct, self.createUpOrientationMenu(),
  1238. self.updateOrientationNum)
  1239. # Clear angle offset on this menu
  1240. menu.setItemOffset(0.0)
  1241. self.pieMenuDictionary['upOrientationMenu'] = menu
  1242. self.pieMenuDictionary['numWindowsMenu'] = (
  1243. PieMenu(self.direct, self.createNumWindowsMenu(),
  1244. self.updateNumWindows))
  1245. self.pieMenuDictionary['corniceMenu'] = (
  1246. PieMenu(self.direct,self.createCorniceMenu(),
  1247. self.updateCorniceTextureNum))
  1248. self.pieMenuDictionary['doorMenu'] = (
  1249. PieMenu(self.direct,self.createDoorMenu(),
  1250. self.updateDoorTextureNum))
  1251. self.pieMenuDictionary['wallWidthMenu'] = (
  1252. PieMenu(self.direct,self.createWallWidthMenu(),
  1253. self.updateWallWidthSF))
  1254. self.pieMenuDictionary['propTypesMenu'] = (
  1255. PieMenu(self.direct,self.createPropTypesMenu(),
  1256. self.updatePropNum))
  1257. self.pieMenuDictionary['toontownCentralStyleMenu'] = (
  1258. PieMenu(self.direct,self.createStyleMenuWith(
  1259. self.attributeDictionary['toontownCentralStyleDictionary']),
  1260. self.updateWallStyleNum))
  1261. self.pieMenuDictionary['donaldsDockStyleMenu'] = (
  1262. PieMenu(self.direct,self.createStyleMenuWith(
  1263. self.attributeDictionary['donaldsDockStyleDictionary']),
  1264. self.updateWallStyleNum))
  1265. self.pieMenuDictionary['theBurrrghStyleMenu'] = (
  1266. PieMenu(self.direct,self.createStyleMenuWith(
  1267. self.attributeDictionary['theBurrrghStyleDictionary']),
  1268. self.updateWallStyleNum))
  1269. self.pieMenuDictionary['minniesMelodyLandStyleMenu'] = (
  1270. PieMenu(self.direct,self.createStyleMenuWith(
  1271. self.attributeDictionary['minniesMelodyLandStyleDictionary']),
  1272. self.updateWallStyleNum))
  1273. self.pieMenuDictionary['styleMenu'] = (
  1274. self.pieMenuDictionary['toontownCentralStyleMenu'])
  1275. # Create several differnt color palette menus
  1276. self.createColorMenus()
  1277. def initializeStyleDictionary(self):
  1278. # Create a dictionary for toontownCentral
  1279. dictionary = self.createStyleDictionaryFromFile(
  1280. 'level_editor/toontownCentralStyles.txt')
  1281. # Store this dictionary in the self.attributeDictionary
  1282. self.attributeDictionary['toontownCentralStyleDictionary'] = dictionary
  1283. # Create a dictionary for donaldsDock
  1284. dictionary = self.createStyleDictionaryFromFile(
  1285. 'level_editor/donaldsDockStyles.txt')
  1286. # Store this dictionary in the self.attributeDictionary
  1287. self.attributeDictionary['donaldsDockStyleDictionary'] = dictionary
  1288. # Create a dictionary for theBurrrgh
  1289. dictionary = self.createStyleDictionaryFromFile(
  1290. 'level_editor/theBurrrghStyles.txt')
  1291. # Store this dictionary in the self.attributeDictionary
  1292. self.attributeDictionary['theBurrrghStyleDictionary'] = dictionary
  1293. # Create a dictionary for minniesMelodyLand
  1294. dictionary = self.createStyleDictionaryFromFile(
  1295. 'level_editor/minniesMelodyLandStyles.txt')
  1296. # Store this dictionary in the self.attributeDictionary
  1297. self.attributeDictionary['minniesMelodyLandStyleDictionary'] = (
  1298. dictionary)
  1299. # Record active style dictionary
  1300. self.styleDictionary = (
  1301. self.attributeDictionary['toontownCentralStyleDictionary'])
  1302. def initializeTheBurrrghStyleDictionary(self):
  1303. dictionary = {}
  1304. styleCount = 0
  1305. self.addStyle(dictionary, styleCount,
  1306. 'wall_md_blank_ur',
  1307. Vec4(0.417323, 0.15711, 0.15711, 1.0),
  1308. 'window_sm_square_ur',
  1309. Vec4(0.874016, 0.654655, 0.329041, 1.0),
  1310. 'cornice_marble_ur',
  1311. Vec4(0.76378, 0.572086, 0.287541, 1.0))
  1312. styleCount = styleCount + 1
  1313. self.addStyle(dictionary, styleCount,
  1314. 'wall_sm_wood_ur',
  1315. Vec4(0.874016, 0.610097, 0.610097, 1.0),
  1316. 'window_sm_shuttered_ur',
  1317. Vec4(0.874016, 0.548402, 0.329041, 1.0),
  1318. None,
  1319. None)
  1320. styleCount = styleCount + 1
  1321. self.addStyle(dictionary, styleCount,
  1322. 'wall_sm_wood_ur',
  1323. Vec4(0.913386, 0.540868, 0.540868, 1.0),
  1324. 'window_porthole_ur',
  1325. Vec4(0.0778138, 0.472441, 0.314961, 1.0),
  1326. 'cornice_horizontal_ur',
  1327. Vec4(1.0, 0.501961, 0.376471, 1.0))
  1328. styleCount = styleCount + 1
  1329. self.addStyle(dictionary, styleCount,
  1330. 'wall_sm_wood_ur',
  1331. Vec4(0.913386, 0.540868, 0.540868, 1.0),
  1332. 'window_porthole_ur',
  1333. Vec4(0.0778138, 0.472441, 0.314961, 1.0),
  1334. 'cornice_shingles_ur',
  1335. Vec4(0.732283, 0.511163, 0.511163, 1.0))
  1336. styleCount = styleCount + 1
  1337. self.addStyle(dictionary, styleCount,
  1338. 'wall_md_blank_ur',
  1339. Vec4(0.384314, 0.305635, 0.187618, 1.0),
  1340. 'window_sm_round_ur',
  1341. Vec4(0.779528, 0.489115, 0.293469, 1.0),
  1342. 'cornice_dental_ur',
  1343. Vec4(0.574803, 0.38771, 0.340374, 1.0))
  1344. styleCount = styleCount + 1
  1345. self.addStyle(dictionary, styleCount,
  1346. 'wall_bricks_dr',
  1347. Vec4(0.629921, 0.471823, 0.237147, 1.0),
  1348. 'window_sm_shuttered_ur',
  1349. Vec4(1.0, 0.627451, 0.376471, 1.0),
  1350. None,
  1351. None)
  1352. styleCount = styleCount + 1
  1353. self.addStyle(dictionary, styleCount,
  1354. 'wall_md_board_ur',
  1355. Vec4(0.929134, 0.153034, 0.153034, 1.0),
  1356. 'window_porthole_ur',
  1357. Vec4(0.0, 0.532747, 0.317894, 1.0),
  1358. 'cornice_shingles_ur',
  1359. Vec4(0.944882, 0.715146, 0.659565, 1.0))
  1360. styleCount = styleCount + 1
  1361. self.addStyle(dictionary, styleCount,
  1362. 'wall_lg_brick_ur',
  1363. Vec4(0.166003, 0.440945, 0.276671, 1.0),
  1364. 'window_md_curtains_ur',
  1365. Vec4(0.17258, 0.637795, 0.450208, 1.0),
  1366. None,
  1367. None)
  1368. styleCount = styleCount + 1
  1369. self.addStyle(dictionary, styleCount,
  1370. 'wall_md_board_ur',
  1371. Vec4(0.929134, 0.153034, 0.153034, 1.0),
  1372. 'window_porthole_ur',
  1373. Vec4(0.0, 0.532747, 0.317894, 1.0),
  1374. None,
  1375. None)
  1376. # Store this dictionary in the self.attributeDictionary
  1377. self.attributeDictionary['theBurrrghStyleDictionary'] = dictionary
  1378. def initializeMinniesMelodyLandStyleDictionary(self):
  1379. dictionary = {}
  1380. styleCount = 0
  1381. self.addStyle(dictionary, styleCount,
  1382. 'wall_md_blank_ur',
  1383. Vec4(0.417323, 0.15711, 0.15711, 1.0),
  1384. 'window_sm_square_ur',
  1385. Vec4(0.874016, 0.654655, 0.329041, 1.0),
  1386. 'cornice_marble_ur',
  1387. Vec4(0.76378, 0.572086, 0.287541, 1.0))
  1388. styleCount = styleCount + 1
  1389. self.addStyle(dictionary, styleCount,
  1390. 'wall_sm_wood_ur',
  1391. Vec4(0.874016, 0.610097, 0.610097, 1.0),
  1392. 'window_sm_shuttered_ur',
  1393. Vec4(0.874016, 0.548402, 0.329041, 1.0),
  1394. None,
  1395. None)
  1396. styleCount = styleCount + 1
  1397. self.addStyle(dictionary, styleCount,
  1398. 'wall_sm_wood_ur',
  1399. Vec4(0.913386, 0.540868, 0.540868, 1.0),
  1400. 'window_porthole_ur',
  1401. Vec4(0.0778138, 0.472441, 0.314961, 1.0),
  1402. 'cornice_horizontal_ur',
  1403. Vec4(1.0, 0.501961, 0.376471, 1.0))
  1404. styleCount = styleCount + 1
  1405. self.addStyle(dictionary, styleCount,
  1406. 'wall_sm_wood_ur',
  1407. Vec4(0.913386, 0.540868, 0.540868, 1.0),
  1408. 'window_porthole_ur',
  1409. Vec4(0.0778138, 0.472441, 0.314961, 1.0),
  1410. 'cornice_shingles_ur',
  1411. Vec4(0.732283, 0.511163, 0.511163, 1.0))
  1412. styleCount = styleCount + 1
  1413. self.addStyle(dictionary, styleCount,
  1414. 'wall_md_blank_ur',
  1415. Vec4(0.384314, 0.305635, 0.187618, 1.0),
  1416. 'window_sm_round_ur',
  1417. Vec4(0.779528, 0.489115, 0.293469, 1.0),
  1418. 'cornice_dental_ur',
  1419. Vec4(0.574803, 0.38771, 0.340374, 1.0))
  1420. styleCount = styleCount + 1
  1421. self.addStyle(dictionary, styleCount,
  1422. 'wall_bricks_dr',
  1423. Vec4(0.629921, 0.471823, 0.237147, 1.0),
  1424. 'window_sm_shuttered_ur',
  1425. Vec4(1.0, 0.627451, 0.376471, 1.0),
  1426. None,
  1427. None)
  1428. styleCount = styleCount + 1
  1429. self.addStyle(dictionary, styleCount,
  1430. 'wall_md_board_ur',
  1431. Vec4(0.929134, 0.153034, 0.153034, 1.0),
  1432. 'window_porthole_ur',
  1433. Vec4(0.0, 0.532747, 0.317894, 1.0),
  1434. 'cornice_shingles_ur',
  1435. Vec4(0.944882, 0.715146, 0.659565, 1.0))
  1436. styleCount = styleCount + 1
  1437. self.addStyle(dictionary, styleCount,
  1438. 'wall_lg_brick_ur',
  1439. Vec4(0.166003, 0.440945, 0.276671, 1.0),
  1440. 'window_md_curtains_ur',
  1441. Vec4(0.17258, 0.637795, 0.450208, 1.0),
  1442. None,
  1443. None)
  1444. styleCount = styleCount + 1
  1445. self.addStyle(dictionary, styleCount,
  1446. 'wall_md_board_ur',
  1447. Vec4(0.929134, 0.153034, 0.153034, 1.0),
  1448. 'window_porthole_ur',
  1449. Vec4(0.0, 0.532747, 0.317894, 1.0),
  1450. None,
  1451. None)
  1452. # Store this dictionary in the self.attributeDictionary
  1453. self.attributeDictionary['minniesMelodyLandStyleDictionary'] = dictionary
  1454. def addDNAGroup(self,dnaGroup):
  1455. # Add hook to allow placement of a new dna Group of this type
  1456. # by simply hitting the space bar
  1457. # First clear out old hooks just to be safe
  1458. self.ignore('insert')
  1459. # Now add new hook
  1460. self.accept('insert', self.initNewDNAGroupWithParent,
  1461. [dnaGroup, self.groupParent])
  1462. # Now add the first copy of this Group
  1463. self.initDNAGroupWithParent(dnaGroup,self.groupParent)
  1464. def addDNAGroupType(self, dnaGroup, type):
  1465. # Add hook to allow placement of a new dna Group of this type
  1466. # by simply hitting the space bar
  1467. # First clear out old hooks just to be safe
  1468. self.ignore('insert')
  1469. # Now add new hook
  1470. self.accept('insert',
  1471. self.addFlatBuilding,
  1472. [type])
  1473. # First clear out old hooks just to be safe
  1474. self.ignore('space')
  1475. self.accept('space',
  1476. initNewDNAGroupWithParentType,
  1477. [dnaGroup, self.groupParent, type])
  1478. # Now add the first copy of this Group
  1479. self.initDNAGroupWithParentType(dnaGroup, self.groupParent, type)
  1480. def addDNAGroupTypeMethod(self, dnaGroup, type, method):
  1481. # Add hook to allow placement of a new dna Group of this type
  1482. # by simply hitting the space bar
  1483. # First clear out old hooks just to be safe
  1484. self.ignore('insert')
  1485. # Now add new hooks
  1486. # Insert key generates random version
  1487. self.accept('insert', method, [type])
  1488. # Space bar creates a copy
  1489. self.ignore('space')
  1490. self.accept('space', self.initNewDNAGroupWithParentType,
  1491. [dnaGroup, self.groupParent, type])
  1492. # Now add the first copy of this Group
  1493. self.initDNAGroupWithParentType(dnaGroup, self.groupParent, type)
  1494. def addFlatBuilding(self, buildingType):
  1495. # Create new building
  1496. newDNAFlatBuilding = DNAFlatBuilding(buildingType + '_DNARoot')
  1497. # Select walls
  1498. if buildingType == 'random20':
  1499. selectedType = self.selectBuildingType('twenty')
  1500. elif buildingType == 'random30':
  1501. selectedType = self.selectBuildingType('thirty')
  1502. else:
  1503. selectedType = buildingType
  1504. if selectedType == 'toonTenTen':
  1505. self.setBuildingHeight(20.0)
  1506. newDNAFlatBuilding.add(self.createWall(10.0))
  1507. newDNAFlatBuilding.add(self.createWall(10.0))
  1508. elif selectedType == 'toonTwenty':
  1509. self.setBuildingHeight(20.0)
  1510. newDNAFlatBuilding.add(self.createWall(20.0))
  1511. elif selectedType == 'toonTenTwenty':
  1512. self.setBuildingHeight(30.0)
  1513. newDNAFlatBuilding.add(self.createWall(10.0))
  1514. newDNAFlatBuilding.add(self.createWall(20.0))
  1515. elif selectedType == 'toonTwentyTen':
  1516. self.setBuildingHeight(30.0)
  1517. newDNAFlatBuilding.add(self.createWall(20.0))
  1518. newDNAFlatBuilding.add(self.createWall(10.0))
  1519. elif selectedType == 'toonTenTenTen':
  1520. self.setBuildingHeight(30.0)
  1521. newDNAFlatBuilding.add(self.createWall(10.0))
  1522. newDNAFlatBuilding.add(self.createWall(10.0))
  1523. newDNAFlatBuilding.add(self.createWall(10.0))
  1524. elif selectedType == 'toonTenTwenty':
  1525. newDNAFlatBuilding.add(self.createWall(10.0))
  1526. newDNAFlatBuilding.add(self.createWall(20.0))
  1527. elif selectedType == 'toonTwentyTen':
  1528. newDNAFlatBuilding.add(self.createWall(20.0))
  1529. newDNAFlatBuilding.add(self.createWall(10.0))
  1530. elif selectedType == 'toonThirty':
  1531. newDNAFlatBuilding.add(self.createWall(30.0))
  1532. # Pick a style for this building
  1533. self.setRandomBuildingStyle(newDNAFlatBuilding)
  1534. # Initialize its position and hpr
  1535. newDNAFlatBuilding.setPos(VBase3(0))
  1536. newDNAFlatBuilding.setHpr(VBase3(0))
  1537. # Now place new building in the world
  1538. self.addDNAGroupTypeMethod(newDNAFlatBuilding,buildingType,
  1539. self.addFlatBuilding)
  1540. def addLandmark(self, landmarkType):
  1541. newDNALandmarkBuilding = DNALandmarkBuilding(landmarkType + '_DNARoot')
  1542. newDNALandmarkBuilding.setCode(self.getDNACode(landmarkType))
  1543. newDNALandmarkBuilding.setPos(VBase3(0))
  1544. newDNALandmarkBuilding.setHpr(VBase3(0))
  1545. newDNADoor = self.createDoor(self.getDoorTexture())
  1546. newDNALandmarkBuilding.add(newDNADoor)
  1547. # Now place new building in the world
  1548. self.addDNAGroup(newDNALandmarkBuilding)
  1549. def addObject(self, aNodePath, dnaGroup):
  1550. # Add specified node path to the scene dictionary
  1551. objectDictionary = {}
  1552. objectDictionary['nodePath'] = aNodePath
  1553. objectDictionary['DNA'] = dnaGroup
  1554. self.levelDictionary[aNodePath.id()] = objectDictionary
  1555. return objectDictionary
  1556. def addProp(self, newPropType):
  1557. newDNAProp = DNAProp(newPropType + '_DNARoot')
  1558. newDNAProp.setCode(self.getDNACode(newPropType))
  1559. newDNAProp.setPos(VBase3(0))
  1560. newDNAProp.setHpr(VBase3(0))
  1561. # Now place new building in the world
  1562. self.addDNAGroup(newDNAProp)
  1563. self.setPropType(newPropType)
  1564. def addStreetModule(self, streetType):
  1565. newDNAStreet = DNAStreet(streetType + '_DNARoot')
  1566. newDNAStreet.setCode(self.getDNACode(streetType))
  1567. newDNAStreet.setPos(VBase3(0))
  1568. newDNAStreet.setHpr(VBase3(0))
  1569. newDNAStreet.setStreetTexture(
  1570. self.getDNACode(self.attributeDictionary['streetTexture']))
  1571. newDNAStreet.setSidewalkTexture(
  1572. self.getDNACode(self.attributeDictionary['sidewalkTexture']))
  1573. # Now place new building in the world
  1574. self.addDNAGroup(newDNAStreet)
  1575. def addWall(self, dnaString, height):
  1576. # Create the DNA for this wall
  1577. newDNAWall = self.createWallWithDNA(dnaString, height)
  1578. # Pick a default window
  1579. newDNAWindows = DNAWindows()
  1580. self.setWindowTexture(self.getRandomWindowTexture())
  1581. newDNAWindows.setCode(self.getDNACode(self.getWindowTexture()))
  1582. newDNAWindows.setWindowCount(self.getRandomNumWindows(height))
  1583. colors = self.getWallColors()
  1584. newDNAWindows.setColor(colors[randint(0,len(colors) - 1)])
  1585. newDNAWall.add(newDNAWindows)
  1586. return newDNAWall
  1587. def createCornice(self,dnaString):
  1588. newDNACornice = DNACornice()
  1589. newDNACornice.setCode(self.getDNACode(dnaString))
  1590. colors = self.getCorniceColors()
  1591. newDNACornice.setColor(colors[randint(0,len(colors) - 1)])
  1592. return newDNACornice
  1593. def createDoor(self, dnaString):
  1594. newDNADoor = DNADoor()
  1595. newDNADoor.setCode(self.getDNACode(dnaString))
  1596. colors = self.getDoorColors()
  1597. newDNADoor.setColor(colors[randint(0,len(colors) - 1)])
  1598. return newDNADoor
  1599. def addGroupToSelected(self, aNodePath):
  1600. self.setGroupParent(aNodePath)
  1601. self.createNewLevelGroup()
  1602. def createNewLevelGroup(self):
  1603. newGroupParentDNA = DNAGroup('group=' + `self.groupNum`)
  1604. # Add it to the level objects
  1605. self.groupParentDNA.add(newGroupParentDNA)
  1606. # Make the new one be the current one
  1607. self.groupParentDNA = newGroupParentDNA
  1608. newGroupParent = self.groupParentDNA.traverse(
  1609. self.groupParent, self.dnaStore)
  1610. self.groupParent = newGroupParent
  1611. self.groupNum = self.groupNum + 1
  1612. # Add it to the level dictionary
  1613. self.addObject(self.groupParent, self.groupParentDNA)
  1614. def createTopLevelGroup(self):
  1615. # Create a new top level group
  1616. self.groupParentDNA = DNAGroup('rootNode')
  1617. self.groupNum = 0
  1618. # Add it to the level objects
  1619. self.levelObjectsDNA.add(self.groupParentDNA)
  1620. self.groupParent = self.groupParentDNA.traverse(
  1621. self.levelObjects, self.dnaStore)
  1622. # Add it to the level dictionary
  1623. self.addObject(self.groupParent, self.groupParentDNA)
  1624. def createWall(self, height):
  1625. return self.createWallWithDNA(self.getWallTexture(), height)
  1626. def createWallWithDNA(self, dnaString, height):
  1627. # Create a new DNAWall using default attributes
  1628. # Create the DNA for this wall
  1629. newDNAWall = DNAWall()
  1630. newDNAWall.setCode(self.getDNACode(dnaString))
  1631. newDNAWall.setHeight(height)
  1632. newDNAWall.setColor(self.getWallColor())
  1633. # Pick a default window
  1634. newDNAWindows = DNAWindows()
  1635. newDNAWindows.setCode(self.getDNACode(self.getWindowTexture()))
  1636. newDNAWindows.setWindowCount(1)
  1637. newDNAWindows.setColor(self.getWindowColor())
  1638. newDNAWall.add(newDNAWindows)
  1639. return newDNAWall
  1640. def createWindows(self, numWindows):
  1641. newDNAWindows = DNAWindows()
  1642. newDNAWindows.setCode(self.getDNACode(self.getWindowTexture()))
  1643. newDNAWindows.setWindowCount(numWindows)
  1644. newDNAWindows.setColor(self.getWindowColor())
  1645. return newDNAWindows
  1646. def getCatalogCode(self, category, i):
  1647. return self.dnaStore.getCatalogCode(category, i)
  1648. def getCatalogCodes(self, category):
  1649. numCodes = self.dnaStore.getNumCatalogCodes(category)
  1650. codes = []
  1651. for i in range(numCodes):
  1652. codes.append(self.dnaStore.getCatalogCode(category, i))
  1653. return codes
  1654. def getCatalogCodesSuffix(self, category, suffix):
  1655. codes = self.getCatalogCodes(category)
  1656. orientedCodes = []
  1657. for code in codes:
  1658. if code[-3:] == suffix:
  1659. orientedCodes.append(code)
  1660. return orientedCodes
  1661. def getCornice(self, aDNAFlatBuilding):
  1662. lastWall = self.getLastWall(aDNAFlatBuilding)
  1663. if lastWall:
  1664. for i in range(lastWall.getNumChildren()):
  1665. child = lastWall.at(i)
  1666. if child.__class__.getClassType().eq(DNACornice.getClassType()):
  1667. return child
  1668. # Not found
  1669. return None
  1670. def getDNACode(self, dnaString):
  1671. dnaCode = self.dnaStore.findCode(dnaString)
  1672. if dnaCode == 0:
  1673. print 'getDNACode Error!'
  1674. return dnaCode
  1675. def getDNAGroup(self, aNodePath):
  1676. dict = self.getLevelObject(aNodePath)
  1677. if dict:
  1678. return dict['DNA']
  1679. else:
  1680. return None
  1681. def getDNAString(self, aDNAObject):
  1682. return (self.dnaStore.findStringFromCode(aDNAObject.getCode()))
  1683. def getDoor(self, aDNAGroup):
  1684. for i in range(aDNAGroup.getNumChildren()):
  1685. child = aDNAGroup.at(i)
  1686. if child.__class__.getClassType().eq(DNADoor.getClassType()):
  1687. return child
  1688. # Not found
  1689. return None
  1690. def getLastWall(self, aDNAFlatBuilding):
  1691. lastWall = None
  1692. for i in range(aDNAFlatBuilding.getNumChildren()):
  1693. child = aDNAFlatBuilding.at(i)
  1694. if child.__class__.getClassType().eq(DNAWall.getClassType()):
  1695. lastWall = child
  1696. return lastWall
  1697. def getLevelObject(self, aNodePath):
  1698. # Given a node path, find the corresponding level object
  1699. # in the levelDictionary, if none exists, return 0
  1700. return self.levelDictionary.get(aNodePath.id(), None)
  1701. def getRandomCorniceTexture(self):
  1702. chance = 100 * random()
  1703. if (chance < 20):
  1704. textures = self.getCorniceTextures()
  1705. len = len(textures)
  1706. index = randint(0,len)
  1707. return textures[index]
  1708. else:
  1709. return None
  1710. def rounded(self,val):
  1711. return int(round(val))
  1712. def getRandomNumWindows(self, height):
  1713. h = self.rounded(height)
  1714. if h == 10:
  1715. # Only return 0 25% of the time
  1716. if self.rounded(self.getWallWidth()) == 5:
  1717. return randint(1,3)
  1718. else:
  1719. return randint(0,3)
  1720. elif h == 20:
  1721. if self.rounded(self.getWallWidth()) == 5:
  1722. return randint(1,3)
  1723. else:
  1724. return randint(0,4)
  1725. elif h == 30:
  1726. if self.rounded(self.getWallWidth()) == 5:
  1727. return randint(1,3)
  1728. else:
  1729. return randint(0,4)
  1730. def getRandomDictionaryEntry(self,dict):
  1731. numKeys = len(dict)
  1732. if numKeys > 0:
  1733. keys = dict.keys()
  1734. key = keys[randint(0,numKeys - 1)]
  1735. return dict[key]
  1736. else:
  1737. return None
  1738. def getRandomStyle(self):
  1739. return self.getRandomDictionaryEntry(self.styleDictionary)
  1740. def getRandomWallTexture(self):
  1741. return self.getWallTextures()[
  1742. randint(0, len(self.getWallTextures()) - 1)]
  1743. def getRandomWallWidth(self):
  1744. chance = randint(0,100)
  1745. if chance <= 15:
  1746. return 5.0
  1747. elif (chance > 15) & (chance <= 30):
  1748. return 10.0
  1749. elif (chance > 30) & (chance <= 65):
  1750. return 15.0
  1751. elif (chance > 65) & (chance <= 85):
  1752. return 20.0
  1753. elif (chance > 85):
  1754. return 25.0
  1755. def getRandomWindowTexture(self):
  1756. wt = self.getWindowTextures()
  1757. return wt[randint(9, len(wt) -1 )]
  1758. def getWall(self, aDNAGroup, wallNum):
  1759. wallCount = 0
  1760. for i in range(aDNAGroup.getNumChildren()):
  1761. child = aDNAGroup.at(i)
  1762. if child.__class__.getClassType().eq(DNAWall.getClassType()):
  1763. if wallCount == wallNum:
  1764. return child
  1765. wallCount = wallCount + 1
  1766. # Not found
  1767. return None
  1768. def getWallHeights(self, aDNAFlatBuilding):
  1769. heightList = []
  1770. heightTotal = 0.0
  1771. # Compute wall heights
  1772. for i in range(aDNAFlatBuilding.getNumChildren()):
  1773. child = aDNAFlatBuilding.at(i)
  1774. if child.__class__.getClassType().eq(DNAWall.getClassType()):
  1775. heightTotal = heightTotal + child.getHeight()
  1776. heightList.append(heightTotal)
  1777. return heightList
  1778. def getWallNum(self, aDNAFlatBuilding, zPt):
  1779. if zPt < 0:
  1780. return -1
  1781. heightList = self.getWallHeights(aDNAFlatBuilding)
  1782. wallNum = 0
  1783. for height in heightList:
  1784. if zPt < height:
  1785. return wallNum
  1786. wallNum = wallNum + 1
  1787. return -1
  1788. def getWindow(self, aDNAGroup, windowNum):
  1789. windowCount = 0
  1790. for i in range(aDNAGroup.getNumChildren()):
  1791. child = aDNAGroup.at(i)
  1792. if child.__class__.getClassType().eq(DNAWindows.getClassType()):
  1793. if windowCount == windowNum:
  1794. return child
  1795. windowCount = windowCount + 1
  1796. # Not found
  1797. return None
  1798. def initDNAGroupWithParent(self, dnaGroup, parent):
  1799. # Create the geometry
  1800. # If it is a flat building, update building DNA to current wall width
  1801. if (dnaGroup.__class__.getClassType().eq(DNAFlatBuilding.getClassType())):
  1802. dnaGroup.setWidth(self.getWallWidth())
  1803. newNodePath = dnaGroup.traverse(parent,self.dnaStore)
  1804. #newNodePath.node().setName(newNodePath.node().getName() + '_DNARoot')
  1805. # Add it to the level dictionary
  1806. self.addObject(newNodePath, dnaGroup)
  1807. # Add it to the top level DNA Group
  1808. self.groupParentDNA.add(dnaGroup)
  1809. # Place the new node path at the current grid origin
  1810. newNodePath.setPos(self.grid,0,0,0)
  1811. # Initialize angle to match last object
  1812. newNodePath.setH(self.grid, self.lastAngle)
  1813. # Select the instance
  1814. self.selectNodePath(newNodePath)
  1815. # Now move the grid to get ready for the next group
  1816. self.autoPositionGrid()
  1817. # Update dictionary
  1818. dnaGroup.setPos(newNodePath.getPos())
  1819. dnaGroup.setHpr(newNodePath.getHpr())
  1820. def initDNAGroupWithParentType(self, dnaGroup, parent, type):
  1821. # Create the geometry
  1822. # If it is a flat building, update building DNA to current wall width
  1823. if dnaGroup.__class__.getClassType().eq(DNAFlatBuilding.getClassType()):
  1824. dnaGroup.setWidth(self.getWallWidth())
  1825. newNodePath = dnaGroup.traverse(parent, self.dnaStore)
  1826. #newNodePath.node().setName(newNodePath.node().getName() + '_DNARoot')
  1827. # Add it to the level dictionary
  1828. self.addObject(newNodePath, dnaGroup)
  1829. # Add it to the top level DNA Group
  1830. self.groupParentDNA.add(dnaGroup)
  1831. # Place the new node path at the current grid origin
  1832. newNodePath.setPos(self.grid,0,0,0)
  1833. # Initialize angle to match last object
  1834. newNodePath.setH(self.grid, self.lastAngle)
  1835. # Select the instance
  1836. self.selectNodePath(newNodePath)
  1837. # Now move the grid to get ready for the next group
  1838. self.autoPositionGrid()
  1839. # Update dictionary
  1840. dnaGroup.setPos(newNodePath.getPos())
  1841. dnaGroup.setHpr(newNodePath.getHpr())
  1842. def initNewDNAGroupWithParent(self, dnaGroup, rootNode):
  1843. # Reflect currently selected prop type
  1844. if dnaGroup.__class__.getClassType().eq(DNAProp.getClassType()):
  1845. self.updatePropType(dnaGroup,self.getPropType())
  1846. # Create a new copy of dnaGroup's class
  1847. # Extract group's class using __class__
  1848. # Call that class's constructor passing in dnaGroup to make a copy
  1849. self.initDNAGroupWithParent(dnaGroup.__class__(dnaGroup), self.groupParent)
  1850. # Initialize
  1851. if dnaGroup.__class__.getClassType().eq(DNAProp.getClassType()):
  1852. objectType = self.getDNAString(dnaGroup)
  1853. if objectType != 'prop_sphere':
  1854. # Update props placement to reflect current mouse position
  1855. # Where is the mouse relative to the grid?
  1856. hitPt = self.getGridIntersectionPoint()
  1857. self.direct.selected.last.setPos(self.grid, self.hitPt)
  1858. dnaGroup.setPos(self.direct.selected.last.getPos())
  1859. def initNewDNAGroupWithParentType(self, dnaGroup, rootNode, type):
  1860. # Create a new dna Group of the same type a dnaGroup
  1861. newDNAGroup = dnaGroup.__class__(dnaGroup)
  1862. if dnaGroup.__class__.getClassType().eq(DNAProp.getClassType()):
  1863. self.updatePropType(newDNAGroup,self.getPropType())
  1864. self.initDNAGroupWithParentType(newDNAGroup, self.groupParent, type)
  1865. def loadSpecifiedDNAFile(self):
  1866. f = Filename('/alpha/DIRECT/LevelEditor/DNAFiles')
  1867. path = os.path.join(f.toOsSpecific(), self.dnaOutputDir)
  1868. #f = Filename('dna')
  1869. #f.resolveFilename(getModelPath())
  1870. #path = f.toOsSpecific()
  1871. if not os.path.isdir(path):
  1872. print 'LevelEditor Warning: Invalid default DNA directory!'
  1873. print 'Using: C:\\'
  1874. path = 'C:\\'
  1875. dnaFilename = askopenfilename(
  1876. defaultextension = '.dna',
  1877. filetypes = (('DNA Files', '*.dna'),('All files', '*')),
  1878. initialdir = path,
  1879. title = 'Load DNA File',
  1880. parent = self.panel.component('hull'))
  1881. if dnaFilename:
  1882. self.loadDNAFromFile(dnaFilename)
  1883. def saveToSpecifiedDNAFile(self):
  1884. f = Filename('/alpha/DIRECT/LevelEditor/DNAFiles')
  1885. path = os.path.join(f.toOsSpecific(), self.dnaOutputDir)
  1886. if not os.path.isdir(path):
  1887. print 'LevelEditor Warning: Invalid DNA save directory!'
  1888. print 'Using: C:\\'
  1889. path = 'C:\\'
  1890. dnaFilename = asksaveasfilename(
  1891. defaultextension = '.dna',
  1892. filetypes = (('DNA Files', '*.dna'),('All files', '*')),
  1893. initialdir = path,
  1894. title = 'Save DNA File as',
  1895. parent = self.panel.component('hull'))
  1896. if dnaFilename:
  1897. self.outputDNA(dnaFilename)
  1898. def loadDNAFromFile(self, filename):
  1899. # Out with the old, in with the new
  1900. self.resetLevel()
  1901. # Get rid of default group and root node
  1902. self.preRemoveNodePath(self.groupParent)
  1903. self.removeNodePath(self.groupParent)
  1904. # Clear self.dnaStore
  1905. self.dnaStore.resetDNAGroups()
  1906. # Reset DNA VIS Groups
  1907. self.dnaStore.resetDNAVisGroups()
  1908. # Now load in new file
  1909. self.groupParent = loadDNAFile(self.dnaStore, filename,
  1910. getDefaultCoordinateSystem())
  1911. # Make sure the topmost level object gets put under level objects dna
  1912. self.groupParentDNA = self.dnaStore.findDNAGroup(
  1913. self.groupParent.getBottomArc())
  1914. self.levelObjectsDNA.add(self.groupParentDNA)
  1915. # No level objects node found, just add the whole thing
  1916. self.groupParent.reparentTo(self.levelObjects)
  1917. if 0:
  1918. newLevelObjects = nodePath.find('**/LevelObjects')
  1919. if newLevelObjects.isEmpty():
  1920. # No level objects node found, just add the whole thing
  1921. nodePath.reparentTo(self.levelObjects)
  1922. else:
  1923. # There is a LevelObjects node, add its children
  1924. # Before reparenting children, try to set groupNum to
  1925. # something reasonable
  1926. self.groupNum = newLevelObjects.getNumChildren()
  1927. # Go ahead and get rid of the default parent
  1928. # (since there is probably one in the dnafile
  1929. self.preRemoveNodePath(self.groupParent)
  1930. self.removeNodePath(self.groupParent)
  1931. # Now add the children from the DNA File
  1932. children = newLevelObjects.getChildren()
  1933. for i in range(children.getNumPaths()):
  1934. children.getPath(i).reparentTo(self.levelObjects)
  1935. # Now create a new top level group with next group number
  1936. self.createTopLevelGroup()
  1937. # Add these objects to the levelDictionary
  1938. numPaths = self.dnaStore.getNumNodeRelations()
  1939. for pathNum in range(numPaths):
  1940. relation = self.dnaStore.getNodeRelationAt(pathNum)
  1941. if relation:
  1942. if (relation.getChild() and relation.getParent()):
  1943. newNodePath = NodePath(relation)
  1944. group = self.dnaStore.findDNAGroup(relation)
  1945. if newNodePath.isSingleton():
  1946. print 'Singleton!!'
  1947. else:
  1948. self.addObject(newNodePath, group)
  1949. else:
  1950. print'blah'
  1951. self.createNewLevelGroup()
  1952. def outputDNADefaultFile(self):
  1953. f = Filename('/alpha/DIRECT/LevelEditor/DNAFiles')
  1954. file = os.path.join(f.toOsSpecific(), self.dnaOutputDir,
  1955. self.dnaOutputFile)
  1956. self.outputDNA(file)
  1957. def outputDNA(self,filename):
  1958. print 'Saving DNA to: ', filename
  1959. self.levelObjectsDNA.writeDna(Filename(filename),
  1960. Notify.out(),self.dnaStore)
  1961. def preRemoveNodePath(self, aNodePath):
  1962. # Remove nodePath's DNA from its parent
  1963. dnaGroup = self.getDNAGroup(aNodePath)
  1964. if dnaGroup:
  1965. parentDNAGroup = self.getDNAGroup((aNodePath.getParent()))
  1966. if parentDNAGroup:
  1967. parentDNAGroup.remove(dnaGroup)
  1968. def printVizRegions(self):
  1969. if self.direct.selected.last:
  1970. self.printVizRegionsOf(self.direct.selected.last)
  1971. def printVizRegionsOf(self, aNodePath):
  1972. # Print out commands to create viz regions
  1973. print 'To Be Supplied'
  1974. def removeCornices(self, aDNAGroup):
  1975. while self.removeDNAObjectOfClass(
  1976. DNACornice,self.getLastWall(aDNAGroup)):
  1977. pass
  1978. def removeDNAObjectOfClass(self, objectClass, aDNAGroup):
  1979. # Remove the first object of that type you come across
  1980. for i in range(aDNAGroup.getNumChildren()):
  1981. child = aDNAGroup.at(i)
  1982. if child.__class__.getClassType().eq(objectClass.getClassType()):
  1983. aDNAGroup.remove(child)
  1984. return 1
  1985. # None found
  1986. return 0
  1987. def removeNodePath(self, aNodePath):
  1988. # Remove specified node path from the scene dictionary
  1989. nodePathHandle = aNodePath.id()
  1990. del(self.levelDictionary[nodePathHandle])
  1991. # Get rid of its visible representation
  1992. aNodePath.removeNode()
  1993. def removeWindows(self, aDNAGroup):
  1994. while self.removeDNAObjectOfClass(DNAWindows, aDNAGroup):
  1995. pass
  1996. def reparentNodePath(self, aNodePath):
  1997. selectedDNAObject = self.getDNAGroup(aNodePath)
  1998. if not selectedDNAObject:
  1999. return 0
  2000. parent = aNodePath.getParent()
  2001. if not parent:
  2002. return 0
  2003. parentDNAObject = self.getDNAGroup(parent)
  2004. if not parentDNAObject:
  2005. return 0
  2006. if self.groupParent & self.groupParentDNA:
  2007. # Everybody seems happy, move it
  2008. aNodePath.reparentTo(self.groupParent)
  2009. parentDNAObject.remove(selectedDNAObject)
  2010. self.groupParentDNA.add(selectedDNAObject)
  2011. return 1
  2012. def reparentSelectedNodePath(self):
  2013. selectedNodePath = self.direct.selected.last
  2014. if not selectedNodePath:
  2015. return 0
  2016. return self.reparentNodePath(selectedNodePath)
  2017. def replaceLevelObject(self, levelObject):
  2018. # Get the DNA for this object
  2019. dnaGroup = levelObject['DNA']
  2020. # Get to current node path and its parent
  2021. oldNodePath = levelObject['nodePath']
  2022. parent = oldNodePath.getParent()
  2023. # Traverse the dna to create the new node path
  2024. newNodePath = dnaGroup.traverse(parent, self.dnaStore)
  2025. #newNodePath.node().setName(newNodePath.node().getName() + '_DNARoot')
  2026. self.selectNodePath(newNodePath)
  2027. # Add it to the levelObjects dictionary
  2028. self.selectedLevelObject = self.addObject(newNodePath, dnaGroup)
  2029. # Now get rid of the old level object
  2030. self.removeNodePath(oldNodePath)
  2031. def replaceLevelObjectNodePath(self, levelObject):
  2032. # Get and reuse the DNA for this object
  2033. dnaGroup = levelObject['DNA']
  2034. # Get to current node path and its parent
  2035. oldNodePath = levelObject['nodePath']
  2036. parent = oldNodePath.getParent()
  2037. # Traverse the dna to create the new node path
  2038. newNodePath = dnaGroup.traverse(parent, self.dnaStore)
  2039. #newNodePath.node().setName(newNodePath.node().getName() + '_DNARoot')
  2040. self.selectNodePath(newNodePath)
  2041. # Add it to the levelObjects dictionary
  2042. self.selectedLevelObject = self.addObject(newNodePath, dnaGroup)
  2043. # Now get rid of the old level object
  2044. self.removeNodePath(oldNodePath)
  2045. def selectBuildingType(self, heightType):
  2046. chance = randint(0,100)
  2047. if heightType == 'twenty':
  2048. if chance <= 65:
  2049. return 'toonTenTen'
  2050. else:
  2051. return 'toonTwenty'
  2052. else:
  2053. if chance <= 40:
  2054. return 'toonTenTwenty'
  2055. elif (chance > 40) & (chance <= 70):
  2056. return 'toonTwentyTen'
  2057. elif (chance > 70) & (chance <= 90):
  2058. return 'toonTenTenTen'
  2059. else:
  2060. return 'toonThirty'
  2061. def setGroupName(self, aNodePath, aName):
  2062. aDNAGroup = self.getDNAGroup(aNodePath)
  2063. if aDNAGroup:
  2064. aNodePath.setName(aName)
  2065. aDNAGroup.setName(aName)
  2066. def setNodePathName(self, aNodePath, aName):
  2067. levelObject = self.getLevelObject(aNodePath)
  2068. if levelObject:
  2069. levelObjectDNA = levelObject['DNA']
  2070. aNodePath.setName(aName)
  2071. levelObjectDNA.setName(aName)
  2072. self.replaceLevelObject(levelObject)
  2073. def setRandomBuildingStyle(self, aDNAFlatBuilding):
  2074. self.setWallWidthVal(self.getRandomWallWidth())
  2075. aDNAFlatBuilding.setWidth(self.getWallWidth())
  2076. style = self.getRandomStyle()
  2077. for i in range(aDNAFlatBuilding.getNumChildren()):
  2078. # Set style of each child
  2079. child = aDNAFlatBuilding.at(i)
  2080. if child.__class__.getClassType().eq(DNAWall.getClassType()):
  2081. if randint(0,100) < 40:
  2082. style = self.getRandomStyle()
  2083. self.setWallStyle(child, style)
  2084. # Using the style of the last wall:
  2085. if not style['corniceTexture']:
  2086. self.removeCornices(aDNAFlatBuilding)
  2087. else:
  2088. aDNACornice = self.getCornice(aDNAFlatBuilding)
  2089. if not aDNACornice:
  2090. aDNACornice = DNACornice()
  2091. aDNACornice.setCode(
  2092. self.dnaStore.findCode(style['corniceTexture']))
  2093. aDNACornice.setColor(style['corniceColor'])
  2094. lastWall = self.getLastWall(aDNAFlatBuilding)
  2095. lastWall.add(aDNACornice)
  2096. def setRandomNumWindows(self, aDNAWall, numWindows):
  2097. window = self.getWindow(aDNAWall, 0)
  2098. window.setWindowCount(numWindows)
  2099. def setWallStyle(self, aDNAWall, style):
  2100. aDNAWall.setCode(self.dnaStore.findCode(style['wallTexture']))
  2101. aDNAWall.setColor(style['wallColor'])
  2102. aDNAWindows = self.getWindow(aDNAWall, 0)
  2103. # If the wall has windows:
  2104. if aDNAWindows:
  2105. aDNAWindows.setWindowCount(
  2106. self.getRandomNumWindows(aDNAWall.getHeight()))
  2107. aDNAWindows.setCode(self.dnaStore.findCode(style['windowTexture']))
  2108. aDNAWindows.setColor(style['windowColor'])
  2109. def setWallStyleNum(self, aDNAWall, styleNum):
  2110. # What about cornices
  2111. self.setWallStyle(aDNAWall, self.styleDictionary[styleNum])
  2112. def updateColorIndex(self, colorIndex):
  2113. if colorIndex < 0:
  2114. self.updateObjColor(
  2115. self.targetDNAObject,self.activeMenu.getInitialState())
  2116. else:
  2117. self.updateObjColor(
  2118. self.targetDNAObject,self.activeColors[colorIndex])
  2119. def updateObjColor(self, aDNAObject, color):
  2120. aDNAObject.setColor(color)
  2121. # Replace object in levelObjects dictionary and scene graph
  2122. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2123. self.setActiveColor(color)
  2124. def updateCorniceTextureNum(self, corniceNumber):
  2125. self.updateObjCorniceTexture(self.targetDNAObject, corniceNumber)
  2126. def updateObjCorniceTexture(self, aDNACornice, corniceTextureNumber):
  2127. # Which wall texture was picked by the user?
  2128. if (corniceTextureNumber < 0):
  2129. dnaString = self.activeMenu.getInitialState()
  2130. else:
  2131. dnaString = self.getCorniceTextures()[corniceTextureNumber]
  2132. # Now update the texture on the cornice with that texture
  2133. self.updateCorniceTextureDNA(aDNACornice, dnaString)
  2134. def updateCorniceTextureDNA(self, aDNACornice, dnaString):
  2135. # Get the currently selected DNA Group
  2136. aDNAGroup = self.selectedLevelObject['DNA']
  2137. if dnaString == None:
  2138. # Remove any existing cornices
  2139. self.removeCornices(aDNAGroup)
  2140. # Clear out target DNA Object
  2141. self.targetDNAObject = None
  2142. else:
  2143. # Change the cornice type
  2144. if aDNACornice:
  2145. # Change existing one
  2146. aDNACornice.setCode(self.dnaStore.findCode(dnaString))
  2147. else:
  2148. lastWall = self.getLastWall(aDNAGroup)
  2149. if lastWall:
  2150. # No cornice exists, add a new one
  2151. newDNACornice = self.createCornice(dnaString)
  2152. lastWall.add(newDNACornice)
  2153. # Update target DNA Object
  2154. self.targetDNAObject = newDNACornice
  2155. # Replace object in levelObjects dictionary and scene graph
  2156. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2157. self.setCorniceTexture(dnaString)
  2158. def updateDNAPosHpr(self, aNodePath):
  2159. if aNodePath:
  2160. dnaGroup = self.getDNAGroup(aNodePath)
  2161. if dnaGroup:
  2162. groupClass = dnaGroup.__class__.getClassType()
  2163. if not(groupClass.eq(DNAGroup.getClassType())):
  2164. dnaGroup.setPos(aNodePath.getPos())
  2165. dnaGroup.setHpr(aNodePath.getHpr())
  2166. if (groupClass.eq(DNAProp.getClassType())):
  2167. dnaGroup.setScale(aNodePath.getScale())
  2168. def updateDoorTextureNum(self, doorTextureNumber):
  2169. self.updateObjDoorTexture(self.targetDNAObject, doorTextureNumber)
  2170. def updateObjDoorTexture(self, aDNADoor, doorTextureNumber):
  2171. # Which door texture was picked by the user?
  2172. if doorTextureNumber < 0:
  2173. dnaString = self.activeMenu.getInitialState()
  2174. else:
  2175. dnaString = self.getDoorTextures()[doorTextureNumber]
  2176. # Now update the texture on the door with that texture
  2177. self.updateDoorTextureDNA(aDNADoor, dnaString)
  2178. def updateDoorTextureDNA(self, aDNADoor ,dnaString):
  2179. aDNADoor.setCode(self.dnaStore.findCode(dnaString))
  2180. # Replace object in levelObjects dictionary and scene graph
  2181. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2182. self.setDoorTexture(dnaString)
  2183. def updateNumWindows(self, numWindows):
  2184. if numWindows < 0:
  2185. self.updateObjNumWindows(self.targetDNAObject,
  2186. self.activeMenu.getInitialState())
  2187. else:
  2188. self.updateObjNumWindows(self.targetDNAObject,numWindows)
  2189. def updateObjNumWindows(self, aDNAWall, numWindows):
  2190. # remove any existing windows
  2191. self.removeWindows(aDNAWall)
  2192. # Add the newly specified number of windows
  2193. newDNAWindows = self.createWindows(numWindows)
  2194. aDNAWall.add(newDNAWindows)
  2195. # Replace object in levelObjects dictionary and scene graph
  2196. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2197. self.setNumWindows(numWindows)
  2198. def updateOrientationNum(self, orientationNumber):
  2199. remappedOrientationNumber = orientationNumber
  2200. # Remap lower menu values for Door's and Cornices'
  2201. # (only have upper orientations)
  2202. targetClass = self.targetDNAObject.__class__.getClassType()
  2203. if (targetClass.eq(DNADoor.getClassType()) |
  2204. targetClass.eq(DNAWindows.getClassType()) |
  2205. targetClass.eq(DNACornice.getClassType())):
  2206. if (orientationNumber == 2):
  2207. remappedOrientationNumber = 1
  2208. elif (orientationNumber == 3):
  2209. remappedOrientationNumber = 0
  2210. self.updateOrientation(self.targetDNAObject, remappedOrientationNumber)
  2211. def updateOrientation(self, aDNAObject, orientationNumber):
  2212. if self.activeMenu.getInitialState() == None:
  2213. return None
  2214. currString = self.getDNAString(aDNAObject)
  2215. # Strip off current suffix
  2216. newString = currString[:-3]
  2217. if orientationNumber == 0:
  2218. dnaString = newString + '_ur'
  2219. elif orientationNumber == 1:
  2220. dnaString = newString + '_ul'
  2221. elif orientationNumber == 2:
  2222. dnaString = newString + '_dl'
  2223. elif orientationNumber == 3:
  2224. dnaString = newString + '_dr'
  2225. else:
  2226. dnaString = self.activeMenu.getInitialState()
  2227. if dnaString != currString:
  2228. objClass = aDNAObject.__class__.getClassType()
  2229. if objClass.eq(DNAWall.getClassType()):
  2230. self.updateWallTextureDNA(aDNAObject, dnaString)
  2231. elif objClass.eq(DNACornice.getClassType()):
  2232. self.updateCorniceTextureDNA(aDNAObject, dnaString)
  2233. elif objClass.eq(DNADoor.getClassType()):
  2234. self.updateDoorTextureDNA(aDNAObject, dnaString)
  2235. elif objClass.eq(DNAWindows.getClassType()):
  2236. self.updateWindowTextureDNA(aDNAObject, dnaString)
  2237. def updatePropNum(self,propNumber):
  2238. self.updatePropType(self.targetDNAObject, propNumber)
  2239. def updatePropType(self, aDNAProp, propNumber):
  2240. # Which propType was picked by the user?
  2241. if (propNumber < 0):
  2242. dnaString = self.activeMenu.getInitialState()
  2243. else:
  2244. dnaString = self.getPropTypes()[propNumber]
  2245. # Now update the texture on the wall with that texture
  2246. self.updatePropDNA(aDNAProp,dnaString)
  2247. def updatePropDNA(self, aDNAProp, dnaString):
  2248. aDNAProp.setCode(self.dnaStore.findCode(dnaString))
  2249. # Replace object in levelObjects dictionary and scene graph
  2250. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2251. self.setPropType(dnaString)
  2252. def updateRandomNumWindows(self, aDNAFlatBuilding):
  2253. for i in range(aDNAFlatBuilding.getNumChildren()):
  2254. child = aDNAFlatBuilding.at(i)
  2255. if child.__class__.getClassType().eq(DNAWall.getClassType()):
  2256. self.setRandomNumWindows(
  2257. child,
  2258. self.getRandomNumWindows(child.getHeight()))
  2259. def updateWallColor(self, aDNAWall, color):
  2260. aDNAWall.setColor(color)
  2261. # Replace object in levelObjects dictionary and scene graph
  2262. self.replaceLevelObject(self.selectedLevelObject)
  2263. def updateWallOrientationNum(self, wallOrientationNumber):
  2264. self.updateWallOrientation(self.targetDNAObject, wallOrientationNumber)
  2265. def updateWallOrientation(self, aDNAWall, wallOrientationNumber):
  2266. currString = self.getDNAString(aDNAWall)
  2267. # Strip off current suffix
  2268. newString = currString[:-3]
  2269. if wallOrientationNumber == 0:
  2270. dnaString = newString + '_ur'
  2271. elif wallOrientationNumber == 1:
  2272. dnaString = newString + '_ul'
  2273. elif wallOrientationNumber == 2:
  2274. dnaString = newString + '_dr'
  2275. elif wallOrientationNumber == 3:
  2276. dnaString = newString + '_dl'
  2277. else:
  2278. dnaString = self.activeMenu.getInitialState()
  2279. if dnaString != currString:
  2280. self.updateWallTextureDNA(aDNAWall, dnaString)
  2281. def updateWallStyleNum(self, styleNum):
  2282. if styleNum < 0:
  2283. self.setWallStyleNum(self.targetDNAObject, 0)
  2284. else:
  2285. self.setWallStyleNum(self.targetDNAObject, styleNum)
  2286. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2287. def updateWallTextureNum(self, wallTextureNumber):
  2288. self.updateObjWallTextureNum(self.targetDNAObject, wallTextureNumber)
  2289. def updateObjWallTextureNum(self, aDNAWall, wallTextureNumber):
  2290. # Which wall texture was picked by the user?
  2291. if wallTextureNumber < 0:
  2292. dnaString = self.activeMenu.getInitialState()
  2293. else:
  2294. dnaString = self.getWallTextures()[wallTextureNumber]
  2295. # Now update the texture on the wall with that texture
  2296. self.updateWallTextureDNA(aDNAWall, dnaString)
  2297. def updateWallTextureDNA(self, aDNAWall, dnaString):
  2298. aDNAWall.setCode(self.dnaStore.findCode(dnaString))
  2299. # Replace object in levelObjects dictionary and scene graph
  2300. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2301. self.setWallTexture(dnaString)
  2302. def updateWallWidthSF(self, scaleFactor):
  2303. if (scaleFactor < 0):
  2304. self.updateWallWidth(self.targetDNAObject,
  2305. (self.activeMenu.getInitialState()))
  2306. else:
  2307. self.updateWallWidth(self.targetDNAObject,
  2308. self.wallWidths[scaleFactor])
  2309. def updateSelectedWallWidth(self, width):
  2310. if self.targetDNAObject:
  2311. if self.targetDNAObject.__class__.getClassType().eq(
  2312. DNAFlatBuilding.getClassType()):
  2313. self.updateWallWidth(self.targetDNAObject,width)
  2314. def updateWallWidth(self, aDNAWall, width):
  2315. aDNAWall.setWidth(width)
  2316. # Replace object in levelObjects dictionary and scene graph
  2317. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2318. self.setWallWidthVal(width)
  2319. self.autoPositionGrid()
  2320. def updateWindowTextureNum(self, windowTextureNumber):
  2321. self.updateObjWindowTexture(self.targetDNAObject,
  2322. windowTextureNumber)
  2323. def updateObjWindowTexture(self, aDNAWindow, windowTextureNumber):
  2324. # Which window texture was picked by the user?
  2325. if windowTextureNumber < 0:
  2326. dnaString = self.activeMenu.getInitialState()
  2327. else:
  2328. dnaString = self.getWindowTextures()[windowTextureNumber]
  2329. # Now update the texture on the window with that texture
  2330. self.updateWindowTextureDNA(aDNAWindow, dnaString)
  2331. def updateWindowTextureDNA(self, aDNAWindow, dnaString):
  2332. aDNAWindow.setCode(self.dnaStore.findCode(dnaString))
  2333. # Replace object in levelObjects dictionary and scene graph
  2334. self.replaceLevelObjectNodePath(self.selectedLevelObject)
  2335. self.setWindowTexture(dnaString)
  2336. def roundTo(self, value, divisor):
  2337. return round(value/float(divisor)) * divisor
  2338. def autoPositionGrid(self):
  2339. # Move grid to prepare for placement of next object
  2340. selectedNode = self.direct.selected.last
  2341. if selectedNode:
  2342. dnaGroup = self.getDNAGroup(selectedNode)
  2343. groupClass = dnaGroup.__class__.getClassType()
  2344. deltaPos = Point3(20,0,0)
  2345. deltaHpr = VBase3(0)
  2346. if groupClass.eq(DNAFlatBuilding.getClassType()):
  2347. deltaPos.setX(self.getWallWidth())
  2348. elif groupClass.eq(DNAStreet.getClassType()):
  2349. objectType = self.getDNAString(dnaGroup)
  2350. if objectType == 'street_5x20':
  2351. deltaPos.setX(5.0)
  2352. elif objectType == 'street_10x20':
  2353. deltaPos.setX(10.0)
  2354. elif objectType == 'street_20x20':
  2355. deltaPos.setX(20.0)
  2356. elif objectType == 'street_40x20':
  2357. deltaPos.setX(40.0)
  2358. elif objectType == 'street_80x20':
  2359. deltaPos.setX(80.0)
  2360. elif objectType == 'street_5x40':
  2361. deltaPos.setX(5.0)
  2362. elif objectType == 'street_10x40':
  2363. deltaPos.setX(10.0)
  2364. elif objectType == 'street_20x40':
  2365. deltaPos.setX(20.0)
  2366. elif objectType == 'street_30x40':
  2367. deltaPos.setX(30.0)
  2368. elif objectType == 'street_40x40':
  2369. deltaPos.setX(40.0)
  2370. elif objectType == 'street_80x40':
  2371. deltaPos.setX(80.0)
  2372. elif objectType == 'street_angle_30':
  2373. deltaPos.setX(0.0)
  2374. elif objectType == 'street_angle_45':
  2375. deltaPos.setX(0.0)
  2376. elif objectType == 'street_angle_60':
  2377. deltaPos.setX(0.0)
  2378. elif objectType == 'street_inner_corner':
  2379. deltaPos.setX(20.0)
  2380. elif objectType == 'street_outer_corner':
  2381. deltaPos.setX(20.0)
  2382. elif objectType == 'street_full_corner':
  2383. deltaPos.setX(40.0)
  2384. elif objectType == 'street_t_intersection':
  2385. deltaPos.setX(40.0)
  2386. elif objectType == 'street_y_intersection':
  2387. deltaPos.setX(30.0)
  2388. elif objectType == 'street_street_20x20':
  2389. deltaPos.setX(20.0)
  2390. elif objectType == 'street_street_40x40':
  2391. deltaPos.setX(40.0)
  2392. elif objectType == 'street_sidewalk_20x20':
  2393. deltaPos.setX(20.0)
  2394. elif objectType == 'street_sidewalk_40x40':
  2395. deltaPos.setX(40.0)
  2396. elif objectType == 'street_divided_transition':
  2397. deltaPos.setX(40.0)
  2398. elif objectType == 'street_divided_40x70':
  2399. deltaPos.setX(40.0)
  2400. elif objectType == 'street_stairs_40x10x5':
  2401. deltaPos.setX(40.0)
  2402. elif objectType == 'street_4way_intersection':
  2403. deltaPos.setX(40.0)
  2404. elif objectType == 'street_incline_40x40x5':
  2405. deltaPos.setX(40.0)
  2406. elif objectType == 'street_courtyard_70':
  2407. deltaPos.setX(0.0)
  2408. elif objectType == 'street_courtyard_70_exit':
  2409. deltaPos.setX(0.0)
  2410. elif objectType == 'street_courtyard_90':
  2411. deltaPos.setX(0.0)
  2412. elif objectType == 'street_courtyard_90_exit':
  2413. deltaPos.setX(0.0)
  2414. elif objectType == 'street_50_transition':
  2415. deltaPos.setX(10.0)
  2416. elif objectType == 'street_20x50':
  2417. deltaPos.setX(20.0)
  2418. elif objectType == 'street_40x50':
  2419. deltaPos.setX(40.0)
  2420. elif groupClass.eq(DNALandmarkBuilding.getClassType()):
  2421. objectType = self.getDNAString(dnaGroup)
  2422. if objectType[:-1] == 'toon_landmark_building_0':
  2423. deltaPos.setX(25.0)
  2424. elif objectType[:-1] == 'toon_landmark_building_2':
  2425. deltaPos.setX(15.0)
  2426. elif objectType[:-1] == 'toon_landmark_building_3':
  2427. deltaPos.setX(20.0)
  2428. elif groupClass.eq(DNAProp.getClassType()):
  2429. objectType = self.getDNAString(dnaGroup)
  2430. if objectType == 'prop_sphere':
  2431. deltaPos.setX(40.0)
  2432. # Position grid for placing next object
  2433. # Eventually we need to setHpr too
  2434. taskMgr.removeTasksNamed('autoPositionGrid')
  2435. t = self.grid.lerpPos(deltaPos, 0.25,
  2436. other = selectedNode,
  2437. blendType = 'easeInOut',
  2438. task = 'autoPositionGrid')
  2439. t.deltaPos = deltaPos
  2440. t.selectedNode = selectedNode
  2441. t.uponDeath = self.autoPositionCleanup
  2442. # Also move the camera
  2443. taskMgr.removeTasksNamed('autoMoveDelay')
  2444. handlesToCam = self.direct.widget.getPos(self.direct.camera)
  2445. handlesToCam = handlesToCam * ( self.direct.chan.near/handlesToCam[1])
  2446. if ((abs(handlesToCam[0]) > (self.direct.chan.nearWidth * 0.4)) |
  2447. (abs(handlesToCam[2]) > (self.direct.chan.nearHeight * 0.4))):
  2448. taskMgr.removeTasksNamed('manipulateCamera')
  2449. self.direct.cameraControl.centerCamIn(self.direct.chan, 0.5)
  2450. def autoPositionCleanup(self,state):
  2451. self.grid.setPos(state.selectedNode, state.deltaPos)
  2452. if self.grid.getXyzSnap():
  2453. # Tighten up grid position
  2454. pos = self.grid.getPos()
  2455. roundVal = self.roundTo(self.grid.getGridSpacing(), 1)
  2456. x = self.roundTo(pos[0], roundVal)
  2457. y = self.roundTo(pos[1], roundVal)
  2458. z = self.roundTo(pos[2], roundVal)
  2459. self.grid.setPos(x,y,z)
  2460. def plantSelectedNodePath(self):
  2461. # Move grid to prepare for placement of next object
  2462. selectedNode = self.direct.selected.last
  2463. if selectedNode:
  2464. # Where is the mouse relative to the grid?
  2465. hitPt = self.getGridIntersectionPoint()
  2466. selectedNode.setPos(self.grid, self.hitPt)
  2467. dnaGroup = self.getDNAGroup(selectedNode)
  2468. if dnaGroup:
  2469. # Update props placement to reflect current mouse position
  2470. dnaGroup.setPos(self.direct.selected.last.getPos())
  2471. def resetLevel(self):
  2472. # Clear out all objects
  2473. self.direct.deselectAll()
  2474. children = self.levelObjects.getChildren()
  2475. for i in range(children.getNumPaths()):
  2476. path = children.getPath(i)
  2477. path.reparentTo(hidden)
  2478. path.remove()
  2479. # Create fresh DNA Object
  2480. self.levelObjectsDNA = DNAData('LevelObjects')
  2481. # Create new levelDictionary
  2482. self.levelDictionary = {}
  2483. # Create root node
  2484. self.createTopLevelGroup()
  2485. self.grid.setPosHpr(0,0,0,0,0,0)
  2486. def selectNodePath(self, aNodePath):
  2487. # Select new node path
  2488. self.direct.select(aNodePath)
  2489. # Update selectedLevelObject
  2490. self.selectedLevelObject = self.getLevelObject(aNodePath)
  2491. def getWallIntersectionPoint(self):
  2492. """
  2493. Return point of intersection between building's wall and line from cam
  2494. through mouse. Return false, if nothing selected
  2495. """
  2496. selectedNode = self.direct.selected.last
  2497. if not selectedNode:
  2498. return 0
  2499. # Find mouse point on near plane
  2500. chan = self.direct.chan
  2501. mouseX = chan.mouseX
  2502. mouseY = chan.mouseY
  2503. nearX = math.tan(deg2Rad(chan.fovH)/2.0) * mouseX * chan.near
  2504. nearZ = math.tan(deg2Rad(chan.fovV)/2.0) * mouseY * chan.near
  2505. # Initialize points
  2506. mCam2Wall = chan.camera.getMat(selectedNode)
  2507. mouseOrigin = Point3(0)
  2508. mouseOrigin.assign(mCam2Wall.getRow3(3))
  2509. mouseDir = Vec3(0)
  2510. mouseDir.set(nearX, chan.near, nearZ)
  2511. mouseDir.assign(mCam2Wall.xformVec(mouseDir))
  2512. # Calc intersection point
  2513. return planeIntersect(mouseOrigin, mouseDir, ZERO_POINT, NEG_Y_AXIS)
  2514. def getGridIntersectionPoint(self):
  2515. """
  2516. Return point of intersection between ground plane and line from cam
  2517. through mouse. Return false, if nothing selected
  2518. """
  2519. # Find mouse point on near plane
  2520. chan = self.direct.chan
  2521. mouseX = chan.mouseX
  2522. mouseY = chan.mouseY
  2523. nearX = math.tan(deg2Rad(chan.fovH)/2.0) * mouseX * chan.near
  2524. nearZ = math.tan(deg2Rad(chan.fovV)/2.0) * mouseY * chan.near
  2525. # Initialize points
  2526. mCam2Grid = chan.camera.getMat(self.direct.grid)
  2527. mouseOrigin = Point3(0)
  2528. mouseOrigin.assign(mCam2Grid.getRow3(3))
  2529. mouseDir = Vec3(0)
  2530. mouseDir.set(nearX, chan.near, nearZ)
  2531. mouseDir.assign(mCam2Grid.xformVec(mouseDir))
  2532. # Calc intersection point
  2533. return planeIntersect(mouseOrigin, mouseDir, ZERO_POINT, Z_AXIS)
  2534. class LevelEditorPanel(Pmw.MegaToplevel):
  2535. def __init__(self, levelEditor, parent = None, **kw):
  2536. INITOPT = Pmw.INITOPT
  2537. optiondefs = (
  2538. ('title', 'Toontown Level Editor', None),
  2539. )
  2540. self.defineoptions(kw, optiondefs)
  2541. Pmw.MegaToplevel.__init__(self, parent, title = self['title'])
  2542. self.levelEditor = levelEditor
  2543. self.direct = levelEditor.direct
  2544. # Handle to the toplevels hull
  2545. hull = self.component('hull')
  2546. balloon = self.balloon = Pmw.Balloon(hull)
  2547. # Start with balloon help disabled
  2548. self.balloon.configure(state = 'none')
  2549. menuFrame = Frame(hull, relief = GROOVE, bd = 2)
  2550. menuFrame.pack(fill = X, expand = 1)
  2551. menuBar = Pmw.MenuBar(menuFrame, hotkeys = 1, balloon = balloon)
  2552. menuBar.pack(side = LEFT, expand = 1, fill = X)
  2553. menuBar.addmenu('Level Editor', 'Level Editor Operations')
  2554. menuBar.addmenuitem('Level Editor', 'command',
  2555. 'Load DNA from specified file',
  2556. label = 'Load DNA...',
  2557. command = self.levelEditor.loadSpecifiedDNAFile)
  2558. menuBar.addmenuitem('Level Editor', 'command',
  2559. 'Save DNA data to specified file',
  2560. label = 'Save DNA As...',
  2561. command = self.levelEditor.saveToSpecifiedDNAFile)
  2562. menuBar.addmenuitem('Level Editor', 'command',
  2563. 'Save DNA File',
  2564. label = 'Save DNA',
  2565. command = self.levelEditor.outputDNADefaultFile)
  2566. menuBar.addmenuitem('Level Editor', 'command',
  2567. 'Exit Level Editor Panel',
  2568. label = 'Exit',
  2569. command = self.destroy)
  2570. menuBar.addmenu('Help', 'Level Editor Help Operations')
  2571. self.toggleBalloonVar = IntVar()
  2572. self.toggleBalloonVar.set(0)
  2573. menuBar.addmenuitem('Help', 'checkbutton',
  2574. 'Toggle balloon help',
  2575. label = 'Balloon Help',
  2576. variable = self.toggleBalloonVar,
  2577. command = self.toggleBalloon)
  2578. self.editMenu = Pmw.ComboBox(
  2579. menuFrame, labelpos = W,
  2580. label_text = 'Edit Mode:', entry_width = 12,
  2581. selectioncommand = self.chooseNeighborhood, history = 0,
  2582. scrolledlist_items = ['Toontown Central', 'Donalds Dock',
  2583. 'The Burrrgh', 'Minnies Melody Land'])
  2584. self.editMenu.selectitem('Toontown Central')
  2585. self.editMenu.pack(side = 'left', expand = 0)
  2586. # Create the notebook pages
  2587. notebook = Pmw.NoteBook(hull)
  2588. notebook.pack(fill = BOTH, expand = 1)
  2589. streetsPage = notebook.add('Streets')
  2590. toonBuildingsPage = notebook.add('Toon Bldgs')
  2591. landmarkBuildingsPage = notebook.add('Landmark Bldgs')
  2592. # suitBuildingsPage = notebook.add('Suit Buildings')
  2593. propsPage = notebook.add('Props')
  2594. sceneGraphPage = notebook.add('SceneGraph')
  2595. self.addStreetButton = Button(
  2596. streetsPage,
  2597. text = 'ADD STREET',
  2598. command = self.addStreetModule)
  2599. self.addStreetButton.pack(fill = 'x')
  2600. self.streetSelector = Pmw.ComboBox(
  2601. streetsPage,
  2602. dropdown = 0,
  2603. listheight = 200,
  2604. labelpos = W,
  2605. label_text = 'Street type:',
  2606. label_width = 12,
  2607. label_anchor = W,
  2608. entry_width = 30,
  2609. selectioncommand = self.setStreetModuleType,
  2610. scrolledlist_items = map(lambda s: s[7:],
  2611. levelEditor.getCatalogCodes(
  2612. 'street'))
  2613. )
  2614. self.streetModuleType = levelEditor.getCatalogCode('street',0)
  2615. self.streetSelector.selectitem(self.streetModuleType[7:])
  2616. self.streetSelector.pack(expand = 1, fill = 'both')
  2617. self.addToonBuildingButton = Button(
  2618. toonBuildingsPage,
  2619. text = 'ADD TOON BUILDING',
  2620. command = self.addFlatBuilding)
  2621. self.addToonBuildingButton.pack(fill = 'x')
  2622. self.toonBuildingSelector = Pmw.ComboBox(
  2623. toonBuildingsPage,
  2624. dropdown = 0,
  2625. listheight = 200,
  2626. labelpos = W,
  2627. label_width = 12,
  2628. label_anchor = W,
  2629. label_text = 'Toon bldg type:',
  2630. entry_width = 30,
  2631. selectioncommand = self.setFlatBuildingType,
  2632. scrolledlist_items = ('random20', 'random30',
  2633. 'toonTenTen', 'toonTwenty',
  2634. 'toonTenTwenty', 'toonTwentyTen',
  2635. 'toonTenTenTen', 'toonThirty')
  2636. )
  2637. self.toonBuildingType = 'random20'
  2638. self.toonBuildingSelector.selectitem(self.toonBuildingType)
  2639. self.toonBuildingSelector.pack(expand = 1, fill = 'both')
  2640. self.toonBuildingWidthScale = EntryScale.EntryScale(
  2641. toonBuildingsPage, min = 1.0, max = 30.0,
  2642. resolution = 0.01, text = 'Wall Width',
  2643. command = self.updateSelectedWallWidth)
  2644. self.toonBuildingWidthScale.pack(fill = 'x')
  2645. self.addLandmarkBuildingButton = Button(
  2646. landmarkBuildingsPage,
  2647. text = 'ADD LANDMARK BUILDING',
  2648. command = self.addLandmark)
  2649. self.addLandmarkBuildingButton.pack(fill = 'x')
  2650. self.landmarkBuildingSelector = Pmw.ComboBox(
  2651. landmarkBuildingsPage,
  2652. dropdown = 0,
  2653. listheight = 200,
  2654. labelpos = W,
  2655. label_width = 12,
  2656. label_anchor = W,
  2657. label_text = 'Landmark Building type:',
  2658. entry_width = 30,
  2659. selectioncommand = self.setLandmarkType,
  2660. scrolledlist_items = map(lambda s: s[14:],
  2661. levelEditor.getCatalogCodes(
  2662. 'toon_landmark'))
  2663. )
  2664. self.landmarkType = levelEditor.getCatalogCode(
  2665. 'toon_landmark',0)
  2666. self.landmarkBuildingSelector.selectitem(
  2667. levelEditor.getCatalogCode('toon_landmark',0)[14:])
  2668. self.landmarkBuildingSelector.pack(expand = 1, fill = 'both')
  2669. self.addPropsButton = Button(
  2670. propsPage,
  2671. text = 'ADD PROP',
  2672. command = self.addProp)
  2673. self.addPropsButton.pack(fill = 'x')
  2674. self.propSelector = Pmw.ComboBox(
  2675. propsPage,
  2676. dropdown = 0,
  2677. listheight = 200,
  2678. labelpos = W,
  2679. label_width = 12,
  2680. label_anchor = W,
  2681. label_text = 'Prop type:',
  2682. entry_width = 30,
  2683. selectioncommand = self.setPropType,
  2684. scrolledlist_items = map(lambda s: s[5:],
  2685. levelEditor.getCatalogCodes('prop'))
  2686. )
  2687. self.propType = levelEditor.getCatalogCode('prop',0)
  2688. self.propSelector.selectitem(
  2689. levelEditor.getCatalogCode('prop',0)[5:])
  2690. self.propSelector.pack(expand = 1, fill = 'both')
  2691. # Compact down notebook
  2692. notebook.setnaturalsize()
  2693. self.colorEntry = VectorWidgets.ColorEntry(
  2694. hull, text = 'Select Color',
  2695. command = self.updateSelectedObjColor)
  2696. self.colorEntry.pack(fill = 'x')
  2697. buttonFrame = Frame(hull)
  2698. self.fMapViz = IntVar()
  2699. self.fMapViz.set(0)
  2700. self.mapSnapButton = Checkbutton(buttonFrame,
  2701. text = 'Map Viz',
  2702. width = 6,
  2703. variable = self.fMapViz,
  2704. command = self.toggleMapViz)
  2705. self.mapSnapButton.pack(side = 'left', expand = 1, fill = 'x')
  2706. self.fXyzSnap = IntVar()
  2707. self.fXyzSnap.set(1)
  2708. self.xyzSnapButton = Checkbutton(buttonFrame,
  2709. text = 'XyzSnap',
  2710. width = 6,
  2711. variable = self.fXyzSnap,
  2712. command = self.toggleXyzSnap)
  2713. self.xyzSnapButton.pack(side = 'left', expand = 1, fill = 'x')
  2714. self.fHprSnap = IntVar()
  2715. self.fHprSnap.set(1)
  2716. self.hprSnapButton = Checkbutton(buttonFrame,
  2717. text = 'HprSnap',
  2718. width = 6,
  2719. variable = self.fHprSnap,
  2720. command = self.toggleHprSnap)
  2721. self.hprSnapButton.pack(side = 'left', expand = 1, fill = 'x')
  2722. self.fGrid = IntVar()
  2723. self.fGrid.set(0)
  2724. self.gridButton = Checkbutton(buttonFrame,
  2725. text = 'Show Grid',
  2726. width = 6,
  2727. variable = self.fGrid,
  2728. command = self.toggleGrid)
  2729. self.gridButton.pack(side = 'left', expand = 1, fill = 'x')
  2730. buttonFrame.pack(expand = 1, fill = 'x')
  2731. buttonFrame2 = Frame(hull)
  2732. self.groupButton = Button(
  2733. buttonFrame2,
  2734. text = 'New group',
  2735. command = self.levelEditor.createNewLevelGroup)
  2736. self.groupButton.pack(side = 'left', expand = 1, fill = 'x')
  2737. self.saveButton = Button(
  2738. buttonFrame2,
  2739. text = 'Set Parent',
  2740. command = self.levelEditor.setGroupParentToSelected)
  2741. self.saveButton.pack(side = 'left', expand = 1, fill = 'x')
  2742. self.isolateButton = Button(
  2743. buttonFrame2,
  2744. text = 'Isolate Selected',
  2745. command = self.levelEditor.isolateSelectedNodePath)
  2746. self.isolateButton.pack(side = 'left', expand = 1, fill = 'x')
  2747. self.showAllButton = Button(
  2748. buttonFrame2,
  2749. text = 'Show All',
  2750. command = self.levelEditor.showAll)
  2751. self.showAllButton.pack(side = 'left', expand = 1, fill = 'x')
  2752. buttonFrame2.pack(fill = 'x')
  2753. buttonFrame3 = Frame(hull)
  2754. self.driveMode = IntVar()
  2755. self.driveMode.set(1)
  2756. self.driveModeButton = Radiobutton(
  2757. buttonFrame3,
  2758. text = 'Drive Mode',
  2759. value = 0,
  2760. variable = self.driveMode,
  2761. command = self.levelEditor.useDriveMode)
  2762. self.driveModeButton.pack(side = 'left', expand = 1, fill = 'x')
  2763. self.directModeButton = Radiobutton(
  2764. buttonFrame3,
  2765. text = 'DIRECT Fly',
  2766. value = 1,
  2767. variable = self.driveMode,
  2768. command = self.levelEditor.useDirectFly)
  2769. self.directModeButton.pack(side = 'left', expand = 1, fill = 'x')
  2770. buttonFrame3.pack(fill = 'x')
  2771. self.sceneGraphExplorer = SceneGraphExplorer(
  2772. parent = sceneGraphPage,
  2773. root = self.levelEditor.getLevelObjects(),
  2774. menuItems = ['Select', 'Isolate', 'Flash',
  2775. 'Toggle Viz', 'Set Parent', 'Add Group'])
  2776. self.sceneGraphExplorer.pack(expand = 1, fill = 'both')
  2777. def toggleGrid(self):
  2778. if self.fGrid.get():
  2779. self.direct.grid.enable()
  2780. else:
  2781. self.direct.grid.disable()
  2782. def toggleXyzSnap(self):
  2783. self.direct.grid.setXyzSnap(self.fXyzSnap.get())
  2784. def toggleHprSnap(self):
  2785. self.direct.grid.setHprSnap(self.fXyzSnap.get())
  2786. def toggleMapViz(self):
  2787. self.levelEditor.toggleMapViz(self.fMapViz.get())
  2788. def setStreetModuleType(self,name):
  2789. self.streetModuleType = 'street_' + name
  2790. def addStreetModule(self):
  2791. self.levelEditor.addStreetModule(self.streetModuleType)
  2792. def setFlatBuildingType(self,name):
  2793. self.toonBuildingType = name
  2794. def addFlatBuilding(self):
  2795. self.levelEditor.addFlatBuilding(self.toonBuildingType)
  2796. def setLandmarkType(self,name):
  2797. self.landmarkType = 'toon_landmark_' + name
  2798. def addLandmark(self):
  2799. self.levelEditor.addLandmark(self.landmarkType)
  2800. def setPropType(self,name):
  2801. import pdb
  2802. pdb.set_trace()
  2803. self.propType = 'prop_' + name
  2804. def addProp(self):
  2805. self.levelEditor.addProp(self.propType)
  2806. def chooseNeighborhood(self, neighborhood):
  2807. if neighborhood == "Toontown Central":
  2808. self.levelEditor.editToontownCentral()
  2809. elif neighborhood == "Donalds Dock":
  2810. self.levelEditor.editDonaldsDock()
  2811. elif neighborhood == "The Burrrgh":
  2812. self.levelEditor.editTheBurrrgh()
  2813. elif neighborhood == "Minnies Melody Land":
  2814. self.levelEditor.editMinniesMelodyLand()
  2815. def updateSelectedWallWidth(self, strVal):
  2816. self.levelEditor.updateSelectedWallWidth(string.atof(strVal))
  2817. def setCurrentColor(self, colorVec):
  2818. self.colorEntry.set([int(colorVec[0] * 255.0),
  2819. int(colorVec[1] * 255.0),
  2820. int(colorVec[2] * 255.0),
  2821. 255])
  2822. self.colorEntry['resetValue'] = (
  2823. [int(colorVec[0] * 255.0),
  2824. int(colorVec[1] * 255.0),
  2825. int(colorVec[2] * 255.0),
  2826. 255])
  2827. def updateSelectedObjColor(self, color):
  2828. obj = self.levelEditor.targetDNAObject
  2829. if obj:
  2830. objClass = obj.__class__.getClassType()
  2831. if ((objClass.eq(DNAWall.getClassType())) |
  2832. (objClass.eq(DNAWindows.getClassType())) |
  2833. (objClass.eq(DNADoor.getClassType())) |
  2834. (objClass.eq(DNACornice.getClassType()))):
  2835. self.levelEditor.updateObjColor(
  2836. self.levelEditor.targetDNAObject,
  2837. VBase4((color[0]/255.0),
  2838. (color[1]/255.0),
  2839. (color[2]/255.0),
  2840. 1.0))
  2841. def toggleBalloon(self):
  2842. if self.toggleBalloonVar.get():
  2843. self.balloon.configure(state = 'balloon')
  2844. else:
  2845. self.balloon.configure(state = 'none')
  2846. """
  2847. !Level methodsFor: 'object operations' stamp: 'panda 00/00/0000 00:00'!
  2848. keyboardRotateNodePath: aNodePath key: arrowDirection
  2849. | pos hpr scale |
  2850. pos = aNodePath getPos.
  2851. scale = aNodePath getScale.
  2852. self.lastAngle = self.lastAngle + (arrowDirection caseOf: { [#left]->[ 90.0 ] .
  2853. [#right]->[ -90.0 ] .
  2854. [#up]->[ 90.0 ] .
  2855. [#down]->[ -90.0 ] }).
  2856. (self.lastAngle < -180.0) ifTrue: [ self.lastAngle = self.lastAngle + 360.0 ].
  2857. (self.lastAngle > 180.0) ifTrue: [ self.lastAngle = self.lastAngle - 360.0 ].
  2858. hpr = VBase3 new: self.lastAngle y: 0.0 z: 0.0.
  2859. aNodePath setPosHprScale: pos hpr: hpr scale: scale.
  2860. # Refresh DNA
  2861. self.updateDNAPosHpr: aNodePath.
  2862. # Position grid for placing next object
  2863. self.autoPositionGrid.
  2864. ! !
  2865. !Level methodsFor: 'object operations' stamp: 'panda 00/00/0000 00:00'!
  2866. keyboardTranslateNodePath: aNodePath key: arrowDirection
  2867. | pos deltaMove gridToCamera xAxis zAxis camXAxis xxDot xzDot |
  2868. gridToCamera = self.grid getMat: chanCenter camera.
  2869. xAxis = Vec3 right.
  2870. zAxis = Vec3 up.
  2871. camXAxis = gridToCamera xformVec: xAxis.
  2872. xxDot = camXAxis dot: xAxis.
  2873. xzDot = camXAxis dot: zAxis.
  2874. # get current object position
  2875. pos = aNodePath getPos: self.grid.
  2876. # what is the current grid spacing?
  2877. deltaMove = self.grid gridSpacing.
  2878. # Add or subtract the specified delta
  2879. (xxDot abs > xzDot abs) ifTrue: [
  2880. (xxDot < 0.0) ifTrue: [ deltaMove = deltaMove negated. ].
  2881. arrowDirection caseOf: { [#left]->[ pos setX: ((pos at: 0) - deltaMove) ] .
  2882. [#right]->[ pos setX: ((pos at: 0) + deltaMove) ] .
  2883. [#up]->[ pos setY: ((pos at: 1) + deltaMove) ] .
  2884. [#down]->[ pos setY: ((pos at: 1) - deltaMove) ] }
  2885. ]
  2886. ifFalse: [
  2887. (xzDot < 0.0) ifTrue: [ deltaMove = deltaMove negated. ].
  2888. arrowDirection caseOf: { [#left]->[ pos setY: ((pos at: 1) + deltaMove) ] .
  2889. [#right]->[ pos setY: ((pos at: 1) - deltaMove) ] .
  2890. [#up]->[ pos setX: ((pos at: 0) + deltaMove) ] .
  2891. [#down]->[ pos setX: ((pos at: 0) - deltaMove) ] }
  2892. ].
  2893. # Move it
  2894. aNodePath setPos: self.grid pos: pos.
  2895. # Refresh DNA
  2896. self.updateDNAPosHpr: aNodePath.
  2897. # Position grid for placing next object
  2898. self.autoPositionGrid.
  2899. ! !
  2900. !Level methodsFor: 'object operations' stamp: 'panda 00/00/0000 00:00'!
  2901. keyboardXformNodePath: arrowDirection
  2902. (direct fControl) ifTrue: [
  2903. direct selectedNodePaths
  2904. valuesDo: [ :np | self.keyboardRotateNodePath: np key: arrowDirection ].
  2905. ]
  2906. ifFalse: [
  2907. direct selectedNodePaths
  2908. valuesDo: [ :np | self.keyboardTranslateNodePath: np key: arrowDirection ].
  2909. ].
  2910. ! !
  2911. !Level methodsFor: 'object operations' stamp: 'panda 00/00/0000 00:00'!
  2912. mouseCrank: aNodePath
  2913. # Rotate object about its origin, based upon current mouse position
  2914. # Positive X axis of object is rotated to line up with current Crank Dir
  2915. (or closest snapAngle degree angle if HPR Snap is on
  2916. (self.grid getMouseIntersectionPoint: self.hitPt )
  2917. ifTrue: [self.crankDir = self.hitPt - self.crankOrigin.
  2918. ((self.crankDir length) > 1.0)
  2919. ifTrue: [ | deltaAngle newH |
  2920. deltaAngle = (self.getCrankAngle - startAngle).
  2921. newH = startH + deltaAngle.
  2922. self.hprSnap ifTrue: [ newH = newH roundTo: self.snapAngle. ].
  2923. aNodePath setH: newH.
  2924. # record angle (used for placing new instance)
  2925. self.lastAngle = newH.
  2926. ].
  2927. ].
  2928. ! !
  2929. def acceptArrowKeys(self):
  2930. # Accept arrow key events for swinging piece around
  2931. self.accept('left', self.keyboardXformNodePath, ['left'])
  2932. self.accept('right', self.keyboardXformNodePath, ['right'])
  2933. self.accept('up', self.keyboardXformNodePath, ['up'])
  2934. self.accept('down', self.keyboardXformNodePath, ['down'])
  2935. def keyboardXformNodePath(self,x):
  2936. pass
  2937. def ignoreArrowKeys(self):
  2938. # Accept arrow key events for swinging piece around
  2939. self.ignore('left')
  2940. self.ignore('right')
  2941. self.ignore('up')
  2942. self.ignore('down')
  2943. """