diff --git a/src/pages/Index.tsx b/src/pages/Index.tsx index 479530a..1cba512 100644 --- a/src/pages/Index.tsx +++ b/src/pages/Index.tsx @@ -62,18 +62,41 @@ const Index = () => { } }, [setModel]); - const handleLoadDemo = useCallback(async () => { - setLoadingDemo(true); + const handleLoadCloud = useCallback(async () => { + const url = window.prompt('URL do modelo (GLB · OBJ · STL · IFC):', 'https://'); + if (!url) return; + setLoadingCloud(true); try { - const { blob, fileName, fileSize } = await generateDemoBeamGLB(); - const url = URL.createObjectURL(blob); - setModel({ fileName, fileSize, url }); - toast.success('Modelo demo "IPE 200 — 1000mm" carregado!'); + const fileName = url.split('/').pop()?.split('?')[0] || 'modelo-cloud'; + const ext = getSupportedExtension(fileName); + if (!ext) { + toast.error('URL deve apontar para .GLB, .OBJ, .STL ou .IFC'); + return; + } + const response = await fetch(url, { mode: 'cors' }); + if (!response.ok) throw new Error(`HTTP ${response.status}`); + const buffer = await response.arrayBuffer(); + + let blob: Blob; + let outName = fileName; + let outSize = buffer.byteLength; + if (ext === 'glb') { + blob = new Blob([buffer], { type: 'model/gltf-binary' }); + } else if (ext === 'ifc') { + const r = await convertIFCtoGLB(buffer, fileName); + blob = r.blob; outName = r.fileName; outSize = r.fileSize; + } else { + const r = await convertToGLB(buffer, ext, fileName); + blob = r.blob; outName = r.fileName; outSize = r.fileSize; + } + const blobUrl = URL.createObjectURL(blob); + setModel({ fileName: outName, fileSize: outSize, url: blobUrl }); + toast.success(`"${outName}" carregado da nuvem (RAM)`); } catch (err) { console.error(err); - toast.error('Falha ao gerar modelo demo'); + toast.error('Falha ao carregar da nuvem (verifique URL/CORS)'); } finally { - setLoadingDemo(false); + setLoadingCloud(false); } }, [setModel]);