Вопрос или проблема
Привет, мне действительно хотелось бы знать, почему я могу отображать только один элемент, когда пытаюсь загрузить элементы по конкретным dbIds. Я передаю массив вот так [12345, 6789]
, и он отображает только один элемент. Я проверил, что внешние идентификаторы, которые я передаю, правильно возвращают objectIds, и также убедился, что js получает правильную структуру данных для массива dbId. Что также странно и, возможно, связано, так это то, что элемент загружается, но не подходит для просмотра. Вот мой код:
async function loadAndInitializeForgeViewer(urn, accessToken, dbIds) {
if (typeof Autodesk === 'undefined') {
console.log("Пространство имен Autodesk не найдено, загружаю скрипты Forge Viewer...");
try {
// Загружаем CSS Forge Viewer
await new Promise((resolve, reject) => {
var link = document.createElement('link');
link.rel="stylesheet";
link.href="https://developer.api.autodesk.com/modelderivative/v2/viewers/style.min.css";
link.onload = resolve;
link.onerror = reject;
document.head.appendChild(link);
});
// Загружаем JS Forge Viewer
await new Promise((resolve, reject) => {
var script = document.createElement('script');
script.src="https://developer.api.autodesk.com/modelderivative/v2/viewers/viewer3D.min.js";
script.onload = resolve;
script.onerror = reject;
document.head.appendChild(script);
});
console.log("Скрипты Forge Viewer успешно загружены.");
} catch (error) {
console.error("Ошибка при загрузке скриптов Forge Viewer:", error);
return;
}
} else {
console.log("Скрипты Forge Viewer уже загружены.");
}
await initializeForgeViewer(urn, accessToken, dbIds);
}
let globalViewer = null;
async function initializeForgeViewer(encodedUrn, accessToken, dbIds) {
let options = {
env: 'AutodeskProduction',
getAccessToken: (callback) => {
callback(accessToken, 3600); // Токен доступа истекает через 3600 секунд (1 час)
}
};
Autodesk.Viewing.Initializer(options, async () => {
let viewerDiv = document.getElementById('forgeViewerContainer');
globalViewer = new Autodesk.Viewing.GuiViewer3D(viewerDiv);
globalViewer.start();
let documentId = 'urn:' + encodedUrn;
Autodesk.Viewing.Document.load(documentId, async (doc) => {
let viewables = doc.getRoot().getDefaultGeometry();
if (!viewables) {
console.error("В документе не найдена пригодная для просмотра геометрия.");
return;
}
// Определяем параметры для загрузки конкретных элементов по их dbIds
const loadOptions = {
ids: dbIds // Используем динамический массив dbIds для загрузки всех указанных элементов
};
console.log("Загрузка модели с указанными идентификаторами элементов:", dbIds);
try {
await globalViewer.loadDocumentNode(doc, viewables, loadOptions);
console.log("Модель загружена только с указанными идентификаторами элементов.");
if (dbIds && dbIds.length > 0) {
globalViewer.fitToView(dbIds);
console.log("Подгонка вида под указанные элементы.");
}
} catch (error) {
console.error("Ошибка при загрузке узла документа:", error);
}
}, (errorCode) => {
console.error("Не удалось загрузить документ. Код ошибки:", errorCode);
});
});
}
Ответ или решение
Почему при использовании loadDocumentNode в Forge Viewer API загружается только один элемент при передаче массива
При работе с API Autodesk Forge Viewer для загрузки элементов с помощью метода loadDocumentNode
, многие разработчики сталкиваются с проблемой, когда вместо ожидаемого массива элементов показывается только один. Рассмотрим наиболее распространенные сценарии и возможные решения данной проблемы.
Разбор проблемы
-
Структура кода: Вы уже проверили, что массив
dbIds
, который вы передаете в функцию, имеет правильную структуру, и что все ID соответствуют существующим объектам. Это первый шаг к решению проблемы. -
Параметры загрузки: В вашем коде параметры для загрузки элементы передаются как объект с ключом
ids
:const loadOptions = { ids: dbIds // Используйте динамический массив dbIds для загрузки всех указанных элементов };
Убедитесь, что
loadOptions
правильно интерпретируется API. На некоторых версиях API данный метод может поддерживать только один идентификатор для загрузки. -
Метод fitToView: После загрузки вы используете метод
fitToView
, что правильно, но стоит проверить, правильно ли обработаны вашиdbIds
. В результате может происходить некорректное центрирование на загруженном элементе. -
Тип загружаемого объекта: Иногда загружаемые элементы могут быть сложными и не поддерживать многократное отображение. Проверьте, что вы передаете доступные объектные ID, которые хорошо интегрируются в вашу сцену.
Решение
Для корректного отображения более чем одного элемента, попробуйте следующие подходы:
1. Проверка совместимости API
Убедитесь, что используете актуальную версию API Autodesk Forge, так как изменения в API могут привести к несовместимостям. Проверяйте официальную документацию для получения информации о поддерживаемых функциях.
2. Перезагрузка каждого объекта отдельно
Если проблема сохранится, можете попробовать загружать каждый объект по отдельности в цикле. Это не самое оптимальное решение, но позволит убедиться, что все объекты корректно загружаются:
for (const dbId of dbIds) {
const loadOptions = { ids: [dbId] }; // Загружаем по одному элементу
await globalViewer.loadDocumentNode(doc, viewables, loadOptions);
}
3. Отладка
Добавьте дополнительный вывод в консоль, чтобы фиксировать состояние вашего кода до и после загрузки. Это поможет вам понять, на каком этапе что-то идет не так.
console.log("Загружаю элементы с ID:", dbIds);
4. Проверка ошибок
Обратите особое внимание на сообщения об ошибках, которые могут появляться в вашем коде, и используйте их для дальнейшей отладки.
Заключение
Вопрос, который вы подняли, имеет множество возможных причин. Предложенные решения требуют тщательной проверки и могут варьироваться в зависимости от конкретного случая использования. При дальнейшем тестировании новых методов и стратегий вы сможете лучше понять поведение Forge Viewer API и устранить неполадки с загрузкой нескольких элементов.
Постоянное обновление знаний о возможностях Autodesk Forge и тщательное чтение документации помогут избежать множества проблем в будущем.