How to get Autodesk Viewer LayerManager to RestoreState properly - autodesk-forge

I've encountered a bug in the Autodesk Viewer LayerManager extension that breaks the restoreState functionality. I am saving the state of a multilayer DWG file using getState and re-applying that state using restoreState. When i restore state, most or all of the layers are hidden, even if they weren't when i saved the state.
It looks like this is an issue with how the state is being saved and interpreted. I dug into the state JSON and found the list of visible layers (state.objectSet[0].isolated) in this form:
["0","1","2","3","4","5"]
After some experimenting i found out that the LayerManager is expecting either the integer indices of the layers or the string names of the layers. Something like:
[0,1,2,3,4,5]
or
["layer0","layer1","layer2","layer3","layer4","layer5"]
(assuming those are the names of each layer)
So the current implementation breaks because it looks for layers with the names "0", "1", "2", etc. no matter what the actual layer names are.
I am wondering if there is a way to fix or work around this. A temporary solution is to parse the state JSON and cast the layer numbers to integers but that is a bit of a hack.

This is a known issue and is currently being looked into by our Engineering. Can stay tuned to our Forge Blog and look out for the releases notes to keep tabs on a fix.
In the meantime as quick workaround you can programmatically reveal all the layers once all graphics are loaded:
viewer.addEventListener(Autodesk.Viewing.GEOMETRY_LOADED_EVENT, ()=>viewer.showAll())

Related

Forge-Viewer is missing iPart Factory Members and colors are wrong

Please be patient, I'm new to Forge, C-language, and web-apps, so I'm going to misuse terms and nomenclature like crazy. I'm working on converting a configurator from Configurator 360 to Forge. I created the original Inventor Assembly and iLogic and we farmed out the Forge side of the project. We use our ERP system to generate the engineering number we want from Forge. That number is passed to Forge through a URL and reversed engineered to select all the right options in Inventor. Then .step, .pdf, and .svf files are created with the viewer presenting the .svf and two buttons to download the .step or .pdf respectively. The .step and .pdf look just like they used to from C360 but my viewable is just wrong.
capture from Forge-viewer wrong capture from Inventor-step right
The color of the object should be black and it's white and all parts that are created using iFactories are missing. I don't know if this is two separate issues or caused by the way we are zipping the files for conversion.
I know I haven't given much to go on as to code that could be wrong because I'm not really sure where to start. I do see this in the Immediate Window
Loading model: dXJuOmFkc2sub2JqZWN0czpvcy5vYmplY3Q6cHJpbmNlX291dHB1dF9idWNrZXRfMTVlNDY2ZDYyNDU5NGQ3YmIyMjg0OWM3MDMxODgzOTAxL1BDNDAyMDAyMEEwMC0yOTBYVFhMLAAAAA
Exception thrown: 'Microsoft.JSInterop.JSException' in System.Private.CoreLib.dll
And then it throws that same exception 9 more times... that appears to be one less time then the number of parts that are missing from the viewer.
Any help is much appreciated even if it's just asking questions that might point me in the right direction.
Edit 1:
Found a new error that might help. It shows up if I refresh the browser.
ERROR: Cannot read properties of undefined (reading 'getRoot')
TypeError: Cannot read properties of undefined (reading 'getRoot')
at Object.loadDocumentNode (https://localhost:44365/_content/ForgeFunctions/forgeViewerJsInterop.js:168:40)
at https://localhost:44365/_framework/blazor.server.js:1:70369
at new Promise (<anonymous>)
at e.beginInvokeJSFromDotNet (https://localhost:44365/_framework/blazor.server.js:1:70335)
at https://localhost:44365/_framework/blazor.server.js:1:26442
at Array.forEach (<anonymous>)
at e.invokeClientMethod (https://localhost:44365/_framework/blazor.server.js:1:26412)
at e.processIncomingData (https://localhost:44365/_framework/blazor.server.js:1:24223)
at e.connection.onreceive (https://localhost:44365/_framework/blazor.server.js:1:17308)
at WebSocket.i.onmessage (https://localhost:44365/_framework/blazor.server.js:1:46784)
Edit 2:
I noticed when all the files were being copied to make the zip to create the svf, that a subdirectory was created for the iPart Members (named after the iFactory.) I use a flat zip file (all files in one big folder) so I tried creating a zip with a file structure to match our Vault structure. I then got errors that parts couldn't be found. Lots of other things were tried and then I found this blog post. I used the first option to add the "/p" in my Activity Command Line and set "autodesk.inventor.interop -> Embed Interop Types = false". My iFactory Members are now in the viewable!
Anyone have ideas on what's wrong with the colors? I believe "black" is the only color that is wrong. I do think it's a modified appearance from the appearance library but again the .step file looks good (aka is the color I set) so what in the viewer controls colors?
Edit 3:
So... I fixed the colors... I opened the file in Inventor. Opened the Appearance Browser and Unchecked "Self Illumination" for the "Black" color. Saved, Tested, Worked. Went back in turned "Self Illumination" back on, Saved, Tested, Still Works! So didn't really change anything just changed it and changed back and boom.

How to add geometries from latest version of three.js in forge-viewer?

I am trying to add customized geometry in forge-viewer, I am facing following issue:
The forge viewer I am using is 4.2.* , which uses THREE-R71. (All versions of forge-viewer uses THREE-R71).
The Customized Geometry I am trying to add in forge viewer is from THREE-R94. It throws exception:
THREE.Object3D.add: object not an instance of THREE.Object3D
I tried to upgrade the scene as : viewer.impl.scene=new THREE.Scene()
(THREE-R94)
But the renderer is still from THREE-R71, so renderer cannot render the scene.
Is there any way to add geometries and objects from latest threejs in forge-viewer?
You can't. Threejs has made breaking changes in many of its version upgrades, making them incompatible.
We have some forge articles that say otherwise, like this:
https://forge.autodesk.com/blog/how-add-newest-threejs-features-forge-viewer
It's possible to use different versions, depending heavily on which version, but almost all changes break the code compatibility.
I was unable to use different versions with the methods and objects I wanted.
If you don't want any trouble, stuck with r71 and extend the methods you need yourself.

Custom property (Identity Data) in Revit model got translated wrong

We are experiencing troubles when using the model derivative API to translate and extract properties from a Revit Model.
As the screenshot implies, we have a custom property under Identity Data. But after translation its under Mark (the property on top of it).
It's a model created in Revit 2018.
Is this a bug?
kind regards
This issue has been logged as RVTLMV-4 in our internal case system to our engineering team to allocate time to investigate what happened yesterday and they're working on it. We will get back to you A.S.A.P. once there is any update. Apologizing for any inconvenience had caused to you.
I am seeing this issue too - custom properties appear to be coming through with "Cost" as the PropertyName. The ModelDerivative translation process seems to be the source of the bug. Happens on Revit 2018 or Revit 2019 model.
Is there any chance this issue can be escalated?
Our (live) Forge application relies on custom properties being correctly named and this current API release has broken our application when new models are uploaded.
Image of Model Derivative JSON
Image of Properties in Revit
#Eason Kang: FYI
I met this issue too. However, this issue happened when the translated field was not in the top of the Properties list. When this field was in the top, translation succeeded.
Hope this could give more information to your team.
I attached the image as below. First screenshot, it translated correctly. The 3 following screenshots, it translated wrong

CKEditor 4: How to save and restore the cursor / caret position?

I know that there are some similar questions posted here but none seemed to answer my problematic (or maybe it is that I don't understand well the concept). I started by wanting to get and set the caret position within a CKeditor instance (question is here). With help, I understood that I needed to use ranges and offsets to achieve this goal.
However my problem now is that I don't know how to save this position somewhere, possibly a database and restore the position of the caret. You can imagine a user modifying a document and saving it. When he comes back to continue the edition, the document should be loaded and the caret returned to the last known position.
So, to get the caret position from CKeditor in javascript, that is ok. I can get my range object. But how do I save it? How do I send it to the server for storing? How do I get it back? As a string?
Are there mechanisms to serialize and deserialize ranges or dom nodes?
Thank you for the help!
Are there mechanisms to serialize and deserialize ranges or dom nodes?
There is a mechanism called bookmarks in CKEditor 4. You can use CKEDITOR.dom.range.createBookmark, which basically creates a bookmark for the current range (selection) and then it can be restored via CKEDITOR.dom.range.moveToBookmark.
To make bookmark serializable (so you can save whole content with it to DB and then restore selection when content is loaded), you have to pass true to creatBookmark like createBookmark( true ), this indicates that the bookmark nodes must contain IDs, which can be used to restore the range.

creating and run your own algorithms on localized map

So here is my problem. I plan to implement a localized map for my college presenting all the locations such as main block, Tech park etc. Not only do i plan to develop a GUI but also I also want to run my own algorithms, such as finding the quickest route from one block to another etc (Note: the algorithm is something i will be writing since i don't want to take the shortest route as the quickest but want to add my own parameters as weights). I want to host the map locally (say on a in house system) and should be able to cater real time request (displaying route to the nearest cafeteria) and display current data (such as what event is taking place in what corner of the campus). I know Google Maps API or Openstreetmap/OpenLyers API will enable me to build my own map, but can i run my own algorithms on them? also can I add elements that i have created and replace the traditional building/office components with my own?
You can do the following :
1. Export a part of open street map from their website. (go to the export tab)
2. Use ElementTree in python to parse the exported the xml data.
3. Use networkx to add the parsed data into a graph.
4. Run your algorithms on it.