![](/img/trans.png)
[英]Autodesk Forge Viewer in Sharepoint just shows black models
[英]Forge Autodesk load multiple models in Viewer with ReactJS
我们正在使用 Forge Autodesk Viewer 加载 Forge 模型。 我们正在为我们的应用程序使用框架 ReactJS 并且我们有 function 波纹管在查看器中加载一个 model:
function loadModel(viewer, documentId) {
function onDocumentLoadSuccess(viewerDocument) {
// viewerDocument is an instance of Autodesk.Viewing.Document
const bubbleNode = viewerDocument.getRoot();
let defaultModel;
if (props.phaseName) {
defaultModel = bubbleNode.getMasterView(props.phaseName);
} else if (props.guid) {
defaultModel = bubbleNode.findByGuid(props.guid);
} else if (props.viewableID) {
const results = bubbleNode.search({viewableID: props.viewableID});
if (results && results.length) {
defaultModel = results[0];
}
} else if (props.geomIndex) {
const geoms = bubbleNode.search({type: "geometry"});
if (geoms.length) {
if (props.geomIndex < 0 || props.geomIndex >= geoms.length) {
console.warn("GeometryIndex Error: Invalid geometry index.");
}
const index = Math.min(Math.max(props.geomIndex, 0), geoms.length - 1); // Ensure index is valid.
defaultModel = geoms[index];
}
}
if (!defaultModel) defaultModel = bubbleNode.getDefaultGeometry(true);
const skipHiddenFragments = props.skipHiddenFragments || false;
viewer.loadDocumentNode(viewerDocument, defaultModel, {
keepCurrentModels: true,
skipHiddenFragments: skipHiddenFragments,
});
viewer.prefs.set("ghosting", false);
viewer.loadExtension("Autodesk.Viewing.MarkupsCore")
viewer.loadExtension("Autodesk.Viewing.MarkupsGui")
}
function onDocumentLoadFailure() {
console.error("Failed fetching Forge manifest");
}
if (documentId) {
Autodesk.Viewing.Document.load(
documentId,
onDocumentLoadSuccess,
onDocumentLoadFailure
);
} else {
props.eventBus.dispatchEvent({type: "VIEWER_READY", data: {viewer}});
}
}
我们实际上想知道如何使用 ReactJS 加载多个模型。 谢谢您的答复。
使代码支持 w/ 和 w/o react.js 之间的多个模型没有区别。 您可以通过搜索https://stackoverflow.com/search?q=%5Bautodesk-forge%5D+multiple+models找到很多示例
反正...
这是一个用于加载多个模型的方法,但是您必须更改传递给 Viewer 组件的道具,并相应地更改 Viewer 组件外部的事件调用。
//process each promise
//refer to http://jsfiddle.net/jfriend00/h3zaw8u8/
const promisesInSequence = (tasks, callback) => {
const results = [];
return tasks.reduce((p, item) => {
return p.then(() => {
return callback(item).then((data) => {
results.push(data);
return results;
});
});
}, Promise.resolve());
};
const AGGREGATE_GEOMETRY_LOADED_EVENT = 'aggregateGeometryLoaded';
/**
* @component
* Component for rendering LMV
* @param {Object} props
* @param {("AutodeskProduction"|"AutodeskStaging"|"MD20ProdUS"|"MD20ProdEU")} [props.env] Forge API environment
* @param {Function} props.getToken Returns the Forge API token to access LMV
* @param {"derivativeV2"|"derivativeV2_EU"|"modelDerivativeV2"|"fluent"|"D3S"|"D3S_EU"} [props.api] Default = "derivativeV2". Please refer to LMV documentation for more information.
* @param {Object[]} [props.docUrns] Model data to be loaded
* @param {string} [modelURNs[].urn] Document URN of the model to be loaded
* @param {Object} [modelURNs[].options] model options used in loading the specfic model
* @param {string} [modelURNs[].options.phaseName] phaseName of view to load in scene.
* @param {string} [modelURNs[].options.guid] guid of BubbleNode to load in scene.
* @param {string} [modelURNs[].options.viewableID] viewableID of BubbleNode to load in scene.
* @param {number} [modelURNs[].options.geomIndex] Index of geometry to load in scene.
* @param {Boolean} [modelURNs[].options.skipHiddenFragments] Boolean to specify if hidden fragments should be skipped (Default: false,
* Hidden fragments are required for heatmaps in rooms, only applicable to SVF2)
* @param {OnModelLoaded} [props.onModelLoaded] Callback function invoked when the model has loaded
* @param {OnViewerInitialized} [props.onViewerInitialized] Callback function invoked when LMV has been intialized
* @param {string[]} [props.extensions] List of extension ids forwarded to viewer config to load.
* @param {Object.<string, Object>} [props.disabledExtensions] Default extensions to prevent being loaded.
* @param {Object} [props.viewerOptions] Options object to forward to Autodesk.Viewing.Initializer
* @memberof Autodesk.DataVisualization.UI
* @alias Autodesk.DataVisualization.UI.Viewer
*/
export default function Viewer(props) {
const viewerRef = useRef(null);
const viewerDomRef = useRef(null);
function onModelLoaded(event) {
const viewer = viewerRef.current;
// const av = Autodesk.Viewing;
// viewer.removeEventListener(av.GEOMETRY_LOADED_EVENT, onModelLoaded);
viewer.removeEventListener(AGGREGATE_GEOMETRY_LOADED_EVENT, onModelLoaded);
if (props.onModelLoaded) {
props.onModelLoaded(viewer, event);
}
}
/**
* Initializes LMV.
*
* @memberof Autodesk.DataVisualization.UI
* @alias Autodesk.DataVisualization.UI.Viewer#initializeViewer
* @private
*/
function initializeViewer() {
let viewerOptions = props.viewerOptions;
var options = Object.assign({}, viewerOptions, {
env: props.env,
api: props.api || "derivativeV2", // for models uploaded to EMEA change this option to 'derivativeV2_EU'
getAccessToken: async function (onTokenReady) {
let token = await props.getToken();
var timeInSeconds = 3600; // Use value provided by Forge Authentication (OAuth) API
onTokenReady(token, timeInSeconds);
},
});
Autodesk.Viewing.Initializer(options, async function () {
const extensionsToLoad = props.extensions;
const extensionsWithConfig = [];
const extensionsWithoutConfig = [];
for (let key in extensionsToLoad) {
const config = extensionsToLoad[key];
if (Object.keys(config).length === 0) {
extensionsWithoutConfig.push(key);
} else {
extensionsWithConfig.push(key);
}
}
const viewer = new Autodesk.Viewing.GuiViewer3D(viewerDomRef.current, {
extensions: extensionsWithoutConfig,
disabledExtensions: props.disabledExtensions || {},
});
extensionsWithConfig.forEach((ext) => {
viewer.loadExtension(ext, extensionsToLoad[ext]);
});
viewerRef.current = viewer;
const startedCode = viewer.start(undefined, undefined, undefined, undefined, options);
if (startedCode > 0) {
console.error("Failed to create a Viewer: WebGL not supported.");
return;
}
// loadModel(viewer, props.docUrn);
await loadModels(viewer, props.docUrns);
if (props.onViewerInitialized) {
props.onViewerInitialized(viewer);
}
});
}
/**
* Loads the specified models into the viewer.
*
* @param {Object} viewer Initialized LMV object
* @param {string} documentId Document URN of the model to be loaded
* @param {Object} options
* @param {string} [options.phaseName] phaseName of view to load in scene.
* @param {string} [options.guid] guid of BubbleNode to load in scene.
* @param {string} [options.viewableID] viewableID of BubbleNode to load in scene.
* @param {number} [options.geomIndex] Index of geometry to load in scene.
* @param {Boolean} [options.skipHiddenFragments] Boolean to specify if hidden fragments should be skipped (Default: false,
* Hidden fragments are required for heatmaps in rooms, only applicable to SVF2)
* @memberof Autodesk.DataVisualization.UI
* @alias Autodesk.DataVisualization.UI.Viewer#loadModelAsync
* @private
*/
async function loadModelAsync(viewer, documentId, options) {
return new Promise((resolve, reject) => {
async function onDocumentLoadSuccess(viewerDocument) {
// viewerDocument is an instance of Autodesk.Viewing.Document
const bubbleNode = viewerDocument.getRoot();
let defaultModel;
if (options.phaseName) {
defaultModel = bubbleNode.getMasterView(options.phaseName);
} else if (options.guid) {
defaultModel = bubbleNode.findByGuid(options.guid);
} else if (options.viewableID) {
const results = bubbleNode.search({ viewableID: options.viewableID });
if (results && results.length) {
defaultModel = results[0];
}
} else if (options.geomIndex) {
const geoms = bubbleNode.search({ type: "geometry" });
if (geoms.length) {
if (options.geomIndex < 0 || options.geomIndex >= geoms.length) {
console.warn("GeometryIndex Error: Invalid geometry index.");
}
const index = Math.min(Math.max(options.geomIndex, 0), geoms.length - 1); // Ensure index is valid.
defaultModel = geoms[index];
}
}
if (!defaultModel) defaultModel = bubbleNode.getDefaultGeometry(true);
const skipHiddenFragments = options.skipHiddenFragments || false;
let model = await viewer.loadDocumentNode(viewerDocument, defaultModel, {
keepCurrentModels: true,
skipHiddenFragments: skipHiddenFragments,
});
// modify the preference settings, since ghosting is causing heavy z-fighting with the room geometry
// it would be good we turn it off
if (!viewer.model)
viewer.prefs.set("ghosting", false);
await viewer.waitForLoadDone();
resolve(model);
}
function onDocumentLoadFailure() {
console.error("Failed fetching Forge manifest");
}
if (documentId) {
Autodesk.Viewing.Document.load(
documentId,
onDocumentLoadSuccess,
onDocumentLoadFailure
);
} else {
props.eventBus.dispatchEvent({ type: "VIEWER_READY", data: { viewer } });
}
});
}
/**
* Loads the specified models into the viewer.
*
* @param {Object} viewer Initialized LMV object
* @param {Object[]} modelURNs Model data to be loaded
* @param {string} [modelURNs[].urn] Document URN of the model to be loaded
* @param {Object} [modelURNs[].options] model options used in loading the specfic model
* @param {string} [modelURNs[].options.phaseName] phaseName of view to load in scene.
* @param {string} [modelURNs[].options.guid] guid of BubbleNode to load in scene.
* @param {string} [modelURNs[].options.viewableID] viewableID of BubbleNode to load in scene.
* @param {number} [modelURNs[].options.geomIndex] Index of geometry to load in scene.
* @param {Boolean} [modelURNs[].options.skipHiddenFragments] Boolean to specify if hidden fragments should be skipped (Default: false,
* Hidden fragments are required for heatmaps in rooms, only applicable to SVF2)
* @memberof Autodesk.DataVisualization.UI
* @alias Autodesk.DataVisualization.UI.Viewer#loadModelAsync
* @private
*/
async function loadModelsAsync(viewer, modelURNs) {
// const av = Autodesk.Viewing;
// viewer.addEventListener(av.GEOMETRY_LOADED_EVENT, onModelLoaded, { once: true });
viewer.addEventListener(AGGREGATE_GEOMETRY_LOADED_EVENT, onModelLoaded, { once: true });
const results = await promisesInSequence(modelURNs, (d) => loadModelAsync(d.urn, d.options));
viewer.fireEvent({
type: AGGREGATE_GEOMETRY_LOADED_EVENT,
models: results
});
}
useEffect(() => {
initializeViewer();
return function cleanUp() {
if (viewerRef.current) {
viewerRef.current.finish();
}
};
}, []);
return <div id="forgeViewer" ref={viewerDomRef}></div>;
}
Viewer.displayName = "Viewer";
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.