assimpImport.ed.tscript 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540
  1. //------------------------------------------------------------------------------
  2. // Fields that will be saved to settings
  3. $Assimp::textFields = "lodType" TAB "singleDetailSize" TAB "materialPrefix" TAB
  4. "alwaysImport" TAB "neverImport" TAB "alwaysImportMesh" TAB "neverImportMesh"
  5. TAB "upAxis" TAB "scale" TAB "animTiming" TAB "animFPS";
  6. $Assimp::checkboxFields = "overrideUpAxis" TAB "overrideScale" TAB "ignoreNodeScale"
  7. TAB "adjustCenter" TAB "adjustFloor" TAB "forceUpdateMaterials" TAB "convertLeftHanded"
  8. TAB "calcTangentSpace" TAB "removeRedundantMats" TAB "genUVCoords" TAB
  9. "transformUVCoords" TAB "flipUVCoords" TAB "findInstances" TAB "limitBoneWeights"
  10. TAB "joinIdenticalVerts" TAB "reverseWindingOrder" TAB "invertNormals";
  11. //------------------------------------------------------------------------------
  12. function ShapeImportTreeView::refresh(%this, %what)
  13. {
  14. %shapeRoot = %this.getFirstRootItem();
  15. %materialsRoot = %this.getNextSibling(%shapeRoot);
  16. %animRoot = %this.getNextSibling(%materialsRoot);
  17. // Refresh nodes
  18. if ((%what $= "all") || (%what $= "nodes"))
  19. {
  20. // Indicate whether nodes will be ignored on import
  21. %this._alwaysImport = strreplace(AssimpImportDlg-->alwaysImport.getText(), ";", "\t");
  22. %this._neverImport = strreplace(AssimpImportDlg-->neverImport.getText(), ";", "\t");
  23. %this._alwaysImportMesh = strreplace(AssimpImportDlg-->alwaysImportMesh.getText(), ";", "\t");
  24. %this._neverImportMesh = strreplace(AssimpImportDlg-->neverImportMesh.getText(), ";", "\t");
  25. %this.refreshNode(%this.getChild(%shapeRoot));
  26. }
  27. // Refresh materials
  28. if ((%what $= "all") || (%what $= "materials"))
  29. {
  30. %matPrefix = AssimpImportDlg-->materialPrefix.getText();
  31. %id = %this.getChild(%materialsRoot);
  32. while (%id > 0)
  33. {
  34. %baseName = %this.getItemValue(%id);
  35. %name = %matPrefix @ %baseName;
  36. // Indicate whether material name is already mapped
  37. %this.editItem(%id, %name, %baseName);
  38. %mapped = getMaterialMapping(%name);
  39. if (%mapped $= "")
  40. {
  41. %this.setItemTooltip(%id, "A new material will be mapped to this name");
  42. %this.setItemImages(%id, %this._imageMaterial, %this._imageMaterial);
  43. }
  44. else
  45. {
  46. %this.setItemTooltip(%id, %mapped SPC "is already mapped to this material name");
  47. %this.setItemImages(%id, %this._imageExMaterial, %this._imageExMaterial);
  48. }
  49. %id = %this.getNextSibling(%id);
  50. }
  51. }
  52. // Refresh animations
  53. if ((%what $= "all") || (%what $= "animations"))
  54. {
  55. %id = %this.getChild(%animRoot);
  56. while (%id > 0)
  57. {
  58. %this.setItemImages(%id, %this._imageAnim, %this._imageAnim);
  59. %id = %this.getNextSibling(%id);
  60. }
  61. }
  62. }
  63. function ShapeImportTreeView::refreshNode(%this, %id)
  64. {
  65. while (%id > 0)
  66. {
  67. switch$ (%this.getItemValue(%id))
  68. {
  69. case "mesh":
  70. // Check if this mesh will be ignored on import
  71. if (strIsMatchMultipleExpr(%this._alwaysImportMesh, %this.getItemText(%id)) ||
  72. !strIsMatchMultipleExpr(%this._neverImportMesh, %this.getItemText(%id)) )
  73. {
  74. %this.setItemTooltip(%id, "");
  75. %this.setItemImages(%id, %this._imageMesh, %this._imageMesh);
  76. }
  77. else
  78. {
  79. %this.setItemTooltip(%id, "This mesh will be ignored on import");
  80. %this.setItemImages(%id, %this._imageExNode, %this._imageExNode);
  81. }
  82. case "light":
  83. %this.setItemImages(%id, %this._imageLight, %this._imageLight);
  84. case "node":
  85. // Check if this node will be ignored on import
  86. if (strIsMatchMultipleExpr(%this._alwaysImport, %this.getItemText(%id)) ||
  87. !strIsMatchMultipleExpr(%this._neverImport, %this.getItemText(%id)) )
  88. {
  89. %this.setItemTooltip(%id, "");
  90. %this.setItemImages(%id, %this._imageNode, %this._imageNode);
  91. }
  92. else
  93. {
  94. %this.setItemTooltip(%id, "This node will be ignored on import");
  95. %this.setItemImages(%id, %this._imageExNode, %this._imageExNode);
  96. }
  97. }
  98. // recurse through children and siblings
  99. %this.refreshNode(%this.getChild(%id));
  100. %id = %this.getNextSibling(%id);
  101. }
  102. }
  103. function ShapeImportTreeView::onDefineIcons(%this)
  104. {
  105. // Set the tree view icon indices and texture paths
  106. %this._imageNone = 0;
  107. %this._imageNode = 1;
  108. %this._imageMesh = 2;
  109. %this._imageMaterial = 3;
  110. %this._imageLight = 4;
  111. %this._imageAnimation = 5;
  112. %this._imageExNode = 6;
  113. %this._imageExMaterial = 7;
  114. %icons = ":" @ // no icon
  115. "tools/gui/images/ColladaImport/iconNode:" @ // normal node
  116. "tools/gui/images/ColladaImport/iconMesh:" @ // mesh
  117. "tools/gui/images/ColladaImport/iconMaterial:" @ // new material
  118. "tools/gui/images/ColladaImport/iconLight:" @ // light
  119. "tools/gui/images/ColladaImport/iconAnimation:" @ // sequence
  120. "tools/gui/images/ColladaImport/iconIgnoreNode:" @ // ignored node
  121. "tools/gui/images/ColladaImport/iconExistingMaterial"; // existing material
  122. %this.buildIconTable( %icons );
  123. }
  124. function AssimpImportDlg::updateOverrideUpAxis(%this, %override)
  125. {
  126. %this-->overrideUpAxis.setStateOn(%override);
  127. %this-->upAxis.setActive(%override);
  128. if (!%override)
  129. %this-->upAxis.setText(ShapeImportTreeView._upAxis);
  130. }
  131. function AssimpImportDlg::updateOverrideScale(%this, %override)
  132. {
  133. %this-->overrideScale.setStateOn(%override);
  134. %this-->scale.setActive(%override);
  135. if (!%override)
  136. %this-->scale.setText(ShapeImportTreeView._unit);
  137. }
  138. function AssimpImportDlg::initFromConstructor(%this)
  139. {
  140. if (%this.constructor.upAxis !$= "DEFAULT")
  141. {
  142. %this-->upAxis.setText(%this.constructor.upAxis);
  143. %this.updateOverrideUpAxis(true);
  144. }
  145. else
  146. %this.updateOverrideUpAxis(false);
  147. if (%this.constructor.unit > 0)
  148. {
  149. %this-->scale.setText(%this.constructor.unit);
  150. %this.updateOverrideScale(true);
  151. }
  152. else
  153. %this.updateOverrideScale(false);
  154. %this-->lodType.setText(%this.constructor.lodType);
  155. %this-->singleDetailSize.setText(%this.constructor.singleDetailSize);
  156. %this-->materialPrefix.setText(%this.constructor.matNamePrefix);
  157. %this-->alwaysImport.setText(strreplace(%this.constructor.alwaysImport, "\t", ";"));
  158. %this-->neverImport.setText(strreplace(%this.constructor.neverImport, "\t", ";"));
  159. %this-->alwaysImportMesh.setText(strreplace(%this.constructor.alwaysImportMesh, "\t", ";"));
  160. %this-->neverImportMesh.setText(strreplace(%this.constructor.neverImportMesh, "\t", ";"));
  161. %this-->ignoreNodeScale.setStateOn(%this.constructor.ignoreNodeScale);
  162. %this-->adjustCenter.setStateOn(%this.constructor.adjustCenter);
  163. %this-->adjustFloor.setStateOn(%this.constructor.adjustFloor);
  164. %this-->forceUpdateMaterials.setStateOn(%this.constructor.forceUpdateMaterials);
  165. %this-->animTiming.setText(%this.constructor.animTiming);
  166. %this-->animFPS.setText(%this.constructor.animFPS);
  167. %this-->convertLeftHanded.setStateOn(%this.constructor.convertLeftHanded);
  168. %this-->calcTangentSpace.setStateOn(%this.constructor.calcTangentSpace);
  169. %this-->genUVCoords.setStateOn(%this.constructor.genUVCoords);
  170. %this-->transformUVCoords.setStateOn(%this.constructor.transformUVCoords);
  171. %this-->flipUVCoords.setStateOn(%this.constructor.flipUVCoords);
  172. %this-->findInstances.setStateOn(%this.constructor.findInstances);
  173. %this-->limitBoneWeights.setStateOn(%this.constructor.limitBoneWeights);
  174. %this-->joinIdenticalVerts.setStateOn(%this.constructor.joinIdenticalVerts);
  175. %this-->reverseWindingOrder.setStateOn(%this.constructor.reverseWindingOrder);
  176. %this-->invertNormals.setStateOn(%this.constructor.invertNormals);
  177. %this-->removeRedundantMats.setStateOn(%this.constructor.removeRedundantMats);
  178. }
  179. function AssimpImportDlg::initFromDefaults(%this)
  180. {
  181. %this.updateOverrideUpAxis(false);
  182. %this.updateOverrideScale(false);
  183. %this-->lodType.setText("TrailingNumber");
  184. %this-->singleDetailSize.setText("2");
  185. %this-->materialPrefix.setText("");
  186. %this-->alwaysImport.setText("");
  187. %this-->neverImport.setText("");
  188. %this-->alwaysImportMesh.setText("");
  189. %this-->neverImportMesh.setText("");
  190. %this-->ignoreNodeScale.setStateOn(0);
  191. %this-->adjustCenter.setStateOn(0);
  192. %this-->adjustFloor.setStateOn(0);
  193. %this-->forceUpdateMaterials.setStateOn(0);
  194. %this-->animTiming.setText("Seconds");
  195. %this-->animFPS.setText("30");
  196. %this-->convertLeftHanded.setStateOn(0);
  197. %this-->calcTangentSpace.setStateOn(0);
  198. %this-->genUVCoords.setStateOn(0);
  199. %this-->transformUVCoords.setStateOn(0);
  200. %this-->flipUVCoords.setStateOn(1);
  201. %this-->findInstances.setStateOn(0);
  202. %this-->limitBoneWeights.setStateOn(0);
  203. %this-->joinIdenticalVerts.setStateOn(1);
  204. %this-->reverseWindingOrder.setStateOn(1);
  205. %this-->invertNormals.setStateOn(0);
  206. %this-->removeRedundantMats.setStateOn(1);
  207. }
  208. function AssimpImportDlg::saveToConstructor(%this)
  209. {
  210. // Store values from GUI
  211. if (%this-->overrideUpAxis.getValue())
  212. %this.constructor.upAxis = %this-->upAxis.getText();
  213. else
  214. %this.constructor.upAxis = "DEFAULT";
  215. if (%this-->overrideScale.getValue())
  216. %this.constructor.unit = %this-->scale.getText();
  217. else
  218. %this.constructor.unit = -1;
  219. %this.constructor.lodType = %this-->lodType.getText();
  220. %this.constructor.singleDetailSize = %this-->singleDetailSize.getText();
  221. %this.constructor.matNamePrefix = %this-->materialPrefix.getText();
  222. %this.constructor.alwaysImport = strreplace(%this-->alwaysImport.getText(), ";", "\t");
  223. %this.constructor.neverImport = strreplace(%this-->neverImport.getText(), ";", "\t");
  224. %this.constructor.alwaysImportMesh = strreplace(%this-->alwaysImportMesh.getText(), ";", "\t");
  225. %this.constructor.neverImportMesh = strreplace(%this-->neverImportMesh.getText(), ";", "\t");
  226. %this.constructor.ignoreNodeScale = %this-->ignoreNodeScale.getValue();
  227. %this.constructor.adjustCenter = %this-->adjustCenter.getValue();
  228. %this.constructor.adjustFloor = %this-->adjustFloor.getValue();
  229. %this.constructor.forceUpdateMaterials = %this-->forceUpdateMaterials.getValue();
  230. %this.constructor.animTiming = %this-->animTiming.getText();
  231. %this.constructor.animFPS = %this-->animFPS.getText();
  232. %this.constructor.convertLeftHanded = %this-->convertLeftHanded.getValue();
  233. %this.constructor.calcTangentSpace = %this-->calcTangentSpace.getValue();
  234. %this.constructor.genUVCoords = %this-->genUVCoords.getValue();
  235. %this.constructor.transformUVCoords = %this-->transformUVCoords.getValue();
  236. %this.constructor.flipUVCoords = %this-->flipUVCoords.getValue();
  237. %this.constructor.findInstances = %this-->findInstances.getValue();
  238. %this.constructor.limitBoneWeights = %this-->limitBoneWeights.getValue();
  239. %this.constructor.joinIdenticalVerts = %this-->joinIdenticalVerts.getValue();
  240. %this.constructor.reverseWindingOrder = %this-->reverseWindingOrder.getValue();
  241. %this.constructor.invertNormals = %this-->invertNormals.getValue();
  242. %this.constructor.removeRedundantMats = %this-->removeRedundantMats.getValue();
  243. }
  244. function AssimpImportDlg::showDialog(%this, %shapePath, %cmd)
  245. {
  246. %this.settingVersion = 1.0;
  247. %this.path = %shapePath;
  248. %this.cmd = %cmd;
  249. // Check for an existing TSShapeConstructor object. Need to exec the script
  250. // manually as the resource may not have been loaded yet
  251. %csPath = filePath(%this.path) @ "/" @ fileBase(%this.path) @ "." @ $TorqueScriptFileExtension;
  252. if (isFile(%csPath))
  253. exec(%csPath);
  254. %this.constructor = findShapeConstructorByFilename(%this.path);
  255. // Only show the import dialog if required. Note that 'GetShapeInfo' will
  256. // fail if the source file is missing, or a cached.dts is available.
  257. $assimp::forceLoad = EditorSettings.value("forceLoadDAE");
  258. if (!GetShapeInfo(%shapePath, "ShapeImportTreeView"))
  259. {
  260. eval(%cmd);
  261. $assimp::forceLoad = false;
  262. return;
  263. }
  264. $assimp::forceLoad = false;
  265. // Initialise GUI
  266. ShapeImportTreeView.onDefineIcons();
  267. // Window Title
  268. %this-->window.text = "Shape Import:" SPC %this.path;
  269. // Fill Popups
  270. %this-->upAxis.clear();
  271. %this-->upAxis.add("X_AXIS", 1);
  272. %this-->upAxis.add("Y_AXIS", 2);
  273. %this-->upAxis.add("Z_AXIS", 3);
  274. %this-->lodType.clear();
  275. %this-->lodType.add("DetectDTS", 1);
  276. %this-->lodType.add("SingleSize", 2);
  277. %this-->lodType.add("TrailingNumber", 3);
  278. %this-->animTiming.clear();
  279. %this-->animTiming.add("Frames", 0);
  280. %this-->animTiming.add("Seconds", 1);
  281. %this-->animTiming.add("Milliseconds", 1000);
  282. // Set model details
  283. %this-->nodes.setText(ShapeImportTreeView._nodeCount);
  284. %this-->meshes.setText(ShapeImportTreeView._meshCount);
  285. %this-->lights.setText(ShapeImportTreeView._lightCount);
  286. %this-->materials.setText(ShapeImportTreeView._materialCount);
  287. %this-->polygons.setText(ShapeImportTreeView._polygonCount);
  288. %this-->animations.setText(ShapeImportTreeView._animCount);
  289. %this-->textures.setText(ShapeImportTreeView._textureCount);
  290. %this-->vertices.setText(ShapeImportTreeView._vertCount);
  291. %metaText = (ShapeImportTreeView._metaTagCount == 0) ? "No Records" : ShapeImportTreeView._metaTagCount;
  292. %this-->metadata.setText(%metaText);
  293. if (%this.constructor > 0)
  294. %this.initFromConstructor();
  295. else
  296. {
  297. %this.initFromDefaults();
  298. // If there's a default settings file for the file type, load it
  299. %defaultSISPath = EditorSettings.value("defaultSettingsPath", "Tools");
  300. %settingsFile = %defaultSISPath @ "/" @ getSubStr(fileExt(%shapePath),1) @ ".sis";
  301. if (isFile(%settingsFile))
  302. %this.loadSettingsFrom(%settingsFile);
  303. }
  304. Canvas.pushDialog(%this);
  305. ShapeImportTreeView.refresh("all");
  306. }
  307. function AssimpImportDlg::onLoadSettings(%this)
  308. {
  309. %defaultSISPath = EditorSettings.value("defaultSettingsPath", "Tools");
  310. %dlg = new OpenFileDialog()
  311. {
  312. Filters = "Shape Import Settings (*.sis)|*.sis|";
  313. DefaultPath = %defaultSISPath;
  314. DefaultFile = "";
  315. ChangePath = false;
  316. MustExist = true;
  317. };
  318. %ret = %dlg.Execute();
  319. if ( %ret )
  320. %fileName = %dlg.FileName;
  321. %dlg.delete();
  322. if ( !%ret )
  323. return;
  324. %this.loadSettingsFrom(%fileName);
  325. }
  326. function AssimpImportDlg::onSaveSettings(%this)
  327. {
  328. %defaultSISPath = EditorSettings.value("defaultSettingsPath", "Tools");
  329. %dlg = new SaveFileDialog()
  330. {
  331. Filters = "Shape Import Settings (*.sis)|*.sis|";
  332. DefaultPath = %defaultSISPath;
  333. DefaultFile = "";
  334. ChangePath = false;
  335. MustExist = true;
  336. };
  337. %ret = %dlg.Execute();
  338. if ( %ret )
  339. {
  340. %saveFile = %dlg.FileName;
  341. if(fileExt( %saveFile ) !$= ".sis")
  342. %saveFile = %saveFile @ ".sis";
  343. }
  344. %dlg.delete();
  345. if (!%ret)
  346. return;
  347. %this.saveSettingsTo(%saveFile);
  348. }
  349. function AssimpImportDlg::onCancel(%this)
  350. {
  351. Canvas.popDialog(%this);
  352. ShapeImportTreeView.clear();
  353. }
  354. function AssimpImportDlg::onOK(%this)
  355. {
  356. Canvas.popDialog(%this);
  357. ShapeImportTreeView.clear();
  358. if (%this.needsSave())
  359. {
  360. if (!isObject(%this.constructor))
  361. { // Create a new TSShapeConstructor object
  362. %this.constructor = ShapeEditor.createConstructor(%this.path);
  363. }
  364. }
  365. if (%this.constructor > 0)
  366. {
  367. %this.saveToConstructor();
  368. // Save new settings to file
  369. ShapeEditor.saveConstructor(%this.constructor);
  370. }
  371. // Load the shape (always from the DAE)
  372. $assimp::forceLoad = true;
  373. eval(%this.cmd);
  374. $assimp::forceLoad = false;
  375. }
  376. function AssimpImportDlg::needsSave(%this)
  377. {
  378. if ((%this-->overrideUpAxis.getValue() != 0) ||
  379. (%this-->overrideScale.getValue() != 0) ||
  380. (%this-->lodType.getText() !$= "DetectDTS") ||
  381. (%this-->singleDetailSize.getText() !$= "2") ||
  382. (%this-->materialPrefix.getText() !$= "") ||
  383. (%this-->alwaysImport.getText() !$= "") ||
  384. (%this-->neverImport.getText() !$= "") ||
  385. (%this-->alwaysImportMesh.getText() !$= "") ||
  386. (%this-->neverImportMesh.getText() !$= "") ||
  387. (%this-->ignoreNodeScale.getValue() != 0) ||
  388. (%this-->adjustCenter.getValue() != 0) ||
  389. (%this-->adjustFloor.getValue() != 0) ||
  390. (%this-->forceUpdateMaterials.getValue() != 0))
  391. return true;
  392. if ((%this-->animTiming.getText() !$= "Seconds") ||
  393. (%this-->animFPS.getText() !$= "30") ||
  394. (%this-->convertLeftHanded.getValue() != 0) ||
  395. (%this-->calcTangentSpace.getValue() != 0) ||
  396. (%this-->genUVCoords.getValue() != 0) ||
  397. (%this-->transformUVCoords.getValue() != 0) ||
  398. (%this-->flipUVCoords.getValue() != 1) ||
  399. (%this-->findInstances.getValue() != 0) ||
  400. (%this-->limitBoneWeights.getValue() != 0) ||
  401. (%this-->joinIdenticalVerts.getValue() != 1) ||
  402. (%this-->reverseWindingOrder.getValue() != 1) ||
  403. (%this-->invertNormals.getValue() != 0) ||
  404. (%this-->removeRedundantMats.getValue() != 1))
  405. return true;
  406. return false;
  407. }
  408. function AssimpImportDlg::loadSettingsFrom(%this, %filename)
  409. {
  410. %fileObj = new FileObject();
  411. if (!%fileObj.OpenForRead(%fileName))
  412. {
  413. error("Error opening file to write settings (" @ %fileName @ ").");
  414. %fileObj.delete();
  415. return;
  416. }
  417. %line = %fileObj.ReadLine();
  418. if (getSubStr(%line, 0, 4) !$= "SISV")
  419. return; // ? not sis file
  420. while( !%fileObj.isEOF() )
  421. {
  422. %line = %fileObj.ReadLine();
  423. %key = getField(%line, 0);
  424. %data = getFields(%line, 1);
  425. %ctrl = %this.findObjectByInternalName(%key, true);
  426. if (isObject(%ctrl))
  427. {
  428. %name = %ctrl.getClassName();
  429. if (%ctrl.getClassName() $= "GuiCheckBoxCtrl")
  430. %ctrl.setStateOn(%data);
  431. else
  432. %ctrl.setText(%data);
  433. }
  434. }
  435. %this.updateOverrideUpAxis(%this-->overrideUpAxis.getValue());
  436. %this.updateOverrideScale(%this-->overrideScale.getValue());
  437. %fileObj.close();
  438. %fileObj.delete();
  439. }
  440. function AssimpImportDlg::saveSettingsTo(%this, %filename)
  441. {
  442. %fileObj = new FileObject();
  443. if (!%fileObj.openForWrite(%fileName))
  444. {
  445. error("Error opening file to write settings (" @ %fileName @ ").");
  446. %fileObj.delete();
  447. return;
  448. }
  449. %fileObj.writeLine("SISV" @ %this.settingVersion);
  450. foreach$ (%key in $Assimp::textFields)
  451. {
  452. %ctrl = %this.findObjectByInternalName(%key, true);
  453. if (isObject(%ctrl))
  454. {
  455. %data = %ctrl.getText();
  456. %fileObj.writeLine(%key TAB %data);
  457. }
  458. }
  459. foreach$ (%key in $Assimp::checkboxFields)
  460. {
  461. %ctrl = %this.findObjectByInternalName(%key, true);
  462. if (isObject(%ctrl))
  463. {
  464. %data = %ctrl.getValue();
  465. %fileObj.writeLine(%key TAB %data);
  466. }
  467. }
  468. %fileObj.close();
  469. %fileObj.delete();
  470. }