ref: bd079fb59cff60792842d2726737002fabcc8951
parent: 677b3dca6496046d60e46bce7db0fe4b9dfb4ca3
author: rodri <rgl@antares-labs.eu>
date: Sat May 24 21:08:18 EDT 2025
new tool: tostl
--- a/mkfile
+++ b/mkfile
@@ -9,6 +9,7 @@
procgen\
obj\
stl\
+ tostl\
OFILES=\
alloc.$O\
--- a/readme
+++ b/readme
@@ -16,6 +16,7 @@
- solar: a solar system planetarium (WIP)
- obj: an OBJ to model(6) conversion tool
- stl: an STL to model(6) conversion tool
+ - tostl: a model(6) to STL conversion tool
USAGE
@@ -115,6 +116,15 @@
Just like with obj, by default it will try to compress the resulting
model by deduplicating entries, to disable this feature use -d.
+
+
+ tostl [-t] [file]
+
+ Converts a model(6) into an STL model and writes it to stdout.
+ If there are no arguments, it will read the model(6) from stdin.
+
+ Use the t option to write an ASCII STL file, otherwise a
+ binary one will be written.
CUBEMAPS
--- /dev/null
+++ b/tostl.c
@@ -1,0 +1,93 @@
+#include <u.h>
+#include <libc.h>
+#include <thread.h>
+#include <draw.h>
+#include <memdraw.h>
+#include <geometry.h>
+#include "libgraphics/graphics.h"
+#include "fns.h"
+#include "libstl/stl.h"
+
+static int
+loadstlmodel(Stl *stl, Model *m)
+{
+ Primitive *p;
+ Stltri **tri, *t;
+ int i;
+
+ snprint((char*)stl->hdr, sizeof(stl->hdr), "Exported with libstl from ⑨");
+
+ /* XXX we assume all prims are triangles */
+ stl->ntris = m->nprims;
+ stl->tris = emalloc(stl->ntris*sizeof(Stltri*));
+
+ /* since we don't use attributes we can allocate tris in bulk */
+ t = emalloc(stl->ntris*sizeof(Stltri));
+ memset(t, 0, stl->ntris*sizeof(Stltri));
+ for(tri = stl->tris; tri < stl->tris+stl->ntris; tri++)
+ *tri = &t[tri - stl->tris];
+
+ tri = stl->tris;
+ for(p = m->prims; p < m->prims+m->nprims; p++){
+ if(p->type != PTriangle){
+ stl->ntris--;
+ continue;
+ }
+
+ (*tri)->n[0] = p->v[0].n.x;
+ (*tri)->n[1] = p->v[0].n.y;
+ (*tri)->n[2] = p->v[0].n.z;
+
+ for(i = 0; i < 3; i++){
+ (*tri)->v[i][0] = p->v[i].p.x;
+ (*tri)->v[i][1] = p->v[i].p.y;
+ (*tri)->v[i][2] = p->v[i].p.z;
+ }
+ tri++;
+ }
+
+ return stl->ntris;
+}
+
+static void
+usage(void)
+{
+ fprint(2, "usage: %s [-t] [mdlfile]\n", argv0);
+ exits("usage");
+}
+
+void
+main(int argc, char *argv[])
+{
+ Model *m;
+ Stl *stl;
+ char *infile;
+ int fd, ofmt;
+
+ ofmt = STLBINARY;
+ infile = "/fd/0";
+ ARGBEGIN{
+ case 't': ofmt = STLTEXT; break;
+ default: usage();
+ }ARGEND;
+ if(argc == 1)
+ infile = argv[0];
+ else if(argc > 1)
+ usage();
+
+ fd = open(infile, OREAD);
+ if(fd < 0)
+ sysfatal("open: %r");
+
+ m = readmodel(fd);
+ if(m == nil)
+ sysfatal("readmodel: %r");
+
+ stl = emalloc(sizeof(Stl));
+ loadstlmodel(stl, m);
+
+ if(writestl(1, stl, ofmt) == 0)
+ sysfatal("writestl: %r");
+
+ exits(nil);
+}
--
⑨