Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

@jscad/stl-deserializer in the browser? #1332

Closed
tsdexter opened this issue Apr 1, 2024 · 7 comments
Closed

@jscad/stl-deserializer in the browser? #1332

tsdexter opened this issue Apr 1, 2024 · 7 comments

Comments

@tsdexter
Copy link
Contributor

tsdexter commented Apr 1, 2024

Can the stl-deserializer be used in the browser? There is only a node example and the code below is not working (I have tried with multiple STLs exported from jscad and other sources)

Expected Behavior

geometry is logged in the console

Actual Behavior

Uncaught (in promise) Error: three or more points are required
    at Object.polyhedron (chunk-JDTWA6TY.js?v=0f31f1e5:518:15)
    at toPolyhedron (@jscad_stl-deserializer.js?v=0f31f1e5:4617:25)
    at elementFormatterObject (@jscad_stl-deserializer.js?v=0f31f1e5:4335:84)
    at deserializeBinarySTL (@jscad_stl-deserializer.js?v=0f31f1e5:4523:15)
    at Object.deserialize (@jscad_stl-deserializer.js?v=0f31f1e5:4340:38)

Steps to Reproduce the Problem

use the below file handler on a file input and open the jscad logo jscad.stl exported from jscad.app

reproduction: https://codesandbox.io/p/sandbox/jscad-react-js-demo-forked-hfgxh8

download and unzip attached file and then choose the unzipped jscad.stl in the file picker:
jscad.zip

function handleFilesSelect(e) {
		const { acceptedFiles, fileRejections } = e.detail;
		files.accepted = [...files.accepted, ...acceptedFiles];
		files.rejected = [...files.rejected, ...fileRejections];
		console.log('files', files);
		//create rawData arraybuffer
		const rawData = new Uint8Array(files.accepted[0].data);
		const geometry = stlDeserializer.deserialize(
			{ output: 'geometry', filename: files.accepted[0].name },
			rawData
		);
		console.log('geometry', geometry);
	}

Specifications

  • Version: "@jscad/modeling": "^2.12.1",
    "@jscad/stl-deserializer": "^2.1.23",
  • Platform: windows
  • Environment: browser
@z3dev
Copy link
Member

z3dev commented Apr 1, 2024

@tsdexter just a simple question... is this a custom website? Or just want to get the contents of an STL file via the JSCAD website?

@tsdexter
Copy link
Contributor Author

tsdexter commented Apr 1, 2024

@z3dev it's a custom site, I want to get the geometry from the STL (or 3mf and other formats with deserializers) opened via <input type="file" /> and display it in my custom viewer that already handles jscad data (ie: models: Array<Geometry>).

@tsdexter
Copy link
Contributor Author

tsdexter commented Apr 1, 2024

@z3dev I would also need to load/import them via browser fetch (to my cloud file storage) in the frontend - which I assume (maybe naively) that once I get the file input working, fetching should also work pretty much the same way.

@tsdexter
Copy link
Contributor Author

tsdexter commented Apr 1, 2024

debugging it, I see that when using script output, the points, faces, and colors are all empty arrays, hence the error. Still trying to track down why they are empty

//
  // producer: JSCAD STL Deserializer 2.1.23
  // date: Mon Apr 01 2024 10:30:53 GMT-0400 (Eastern Daylight Time)
  // source: jscad.stl
  // objects: 1
  //
  const {primitives} = require('@jscad/modeling')
//
// solid 1 : 0 points, 0 faces, 0 colors
//
const solid1 = () => {
  const points = [
  ]
  const faces = [
  ]
  const colors = [
  ]
  return primitives.polyhedron({points, faces, colors, orientation: 'inside'})
}

const main = () => {
 return [solid1()]
}

module.exports = {main}

@tsdexter
Copy link
Contributor Author

tsdexter commented Apr 1, 2024

@z3dev I added a reproduction to the issue (I'm not using the jscad-react package, was just a quick setup in codesandbox and does reproduce there as well)

@tsdexter
Copy link
Contributor Author

tsdexter commented Apr 1, 2024

@z3dev nevermind, I figured it out. Just have to read the file in as a string, instead of raw.

function readFileAsText(file: File): Promise<string> {
	return new Promise((resolve, reject) => {
		const reader = new FileReader();
		reader.onload = (event) => resolve(event.target?.result as string);
		reader.onerror = (error) => reject(error);
		reader.readAsText(file);
	});
}

async function handleFilesSelect(e) {
		const { acceptedFiles, fileRejections } = e.detail;
		files.accepted = [...files.accepted, ...acceptedFiles];
		files.rejected = [...files.rejected, ...fileRejections];
		const fileText = await readFileAsText(files.accepted[0]);
		const geometry = stlDeserializer.deserialize(
			{ output: 'geometry', filename: files.accepted[0].name },
			fileText
		);
		console.log({geometry}); // working
	}

@tsdexter tsdexter closed this as completed Apr 1, 2024
@tsdexter
Copy link
Contributor Author

tsdexter commented Apr 1, 2024

@z3dev working now, but found other issue with certain STLs now - do you think this is unavoidable due to bad STLs or is stl-deserializer broken? #1333

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants