User Rating 0.0
Total Usage 0 times
Drop .obj file here or click to browse Supports vertices, normals, texcoords & faces
Is this tool helpful?

Your feedback helps us improve.

About

Wavefront OBJ is a plain-text geometry format dating to the 1980s. Its simplicity makes it ubiquitous but its lack of native browser support creates friction in WebGL pipelines. Manually parsing vertex positions (v), texture coordinates (vt), and face index triplets (f) is error-prone. Mismatched index bases (OBJ uses 1-based indexing; WebGL expects 0-based) cause silent rendering failures: missing triangles, inverted normals, black textures. This converter parses OBJ files client-side with correct index rebasing, fan triangulation of n-gon faces, and outputs a structured JSON object ready for gl.bufferData(). No server upload required. The tool approximates the OBJ specification for polygonal geometry; it does not handle free-form curves, material libraries (.mtl), or group hierarchies.

obj to json 3d model converter wavefront obj webgl json obj parser 3d file converter mesh converter

Formulas

OBJ face indices are 1-based. WebGL and most JSON consumers expect 0-based indexing. The rebasing operation for each index i is:

ijson = iobj 1

For negative indices (relative references from end of current list of length n):

ijson = n + iobj

N-gon faces with k vertices (where k > 3) are triangulated via fan decomposition, producing k 2 triangles. For vertices [v0, v1, …, vk−1], triangle j is:

Tj = (v0, vj+1, vj+2)   forj = 0, …, k 3

Where v0 is the pivot vertex, k is the face vertex count, and Tj represents the j-th output triangle.

Reference Data

OBJ PrefixData TypeComponentsJSON KeyExample Line
vVertex Positionx, y, zverticesv 1.0 2.0 3.0
vtTexture Coordinateu, vtexcoordsvt 0.5 0.8
vnVertex Normalx, y, znormalsvn 0.0 1.0 0.0
fFace (tri/quad/n-gon)v/vt/vn indicesfacesf 1/1/1 2/2/1 3/3/1
fFace (pos only)v indicesfacesf 1 2 3
fFace (pos+normal)v//vn indicesfacesf 1//1 2//1 3//1
fFace (pos+tex)v/vt indicesfacesf 1/1 2/2 3/3
#Comment - Ignored# cube mesh
oObject Namestringnameo MyCube
gGroup NamestringIgnoredg front
sSmooth Shadingon/off/intIgnoreds 1
mtllibMaterial LibraryfilenameIgnoredmtllib cube.mtl
usemtlMaterial UsagenameIgnoredusemtl wood

Frequently Asked Questions

Faces with more than 3 vertices are decomposed into triangles using fan triangulation. A quad (4 vertices) produces 2 triangles; a pentagon produces 3. The first vertex of the face serves as the pivot. This method is correct for convex faces but may produce incorrect geometry for concave polygons. Most modeling software exports convex faces by default.
OBJ supports negative indices as relative references. An index of -1 refers to the last defined vertex, -2 to the second-to-last, and so on. The converter resolves these by adding the negative index to the current count of the respective element type (vertices, normals, or texture coordinates), then converts to 0-based indexing.
The converter offers two output modes. "Indexed" mode preserves separate arrays for vertices, normals, texcoords, and face indices - useful for gl.drawElements(). "Flat" mode de-indexes the data into interleaved per-vertex arrays where each triangle vertex has its own position, normal, and texcoord - ready for gl.drawArrays() without an index buffer. Choose based on your rendering pipeline.
Material libraries require loading external .mtl files and resolving texture image paths, which exceeds the scope of geometry conversion. Group and object names are informational metadata. The converter captures the first object name ('o' directive) in the JSON output but does not split geometry by group. For multi-object files, all geometry merges into a single mesh.
Parsing runs in a Web Worker to avoid blocking the UI. Files up to approximately 100 MB can be processed depending on available browser memory. The parser uses line-by-line streaming rather than loading the entire file into a single string, which reduces peak memory usage. A progress indicator shows parsing advancement for files exceeding 1 MB.
Each line is validated against expected component counts: "v" must have 3 floats, "vt" must have at least 2, "vn" must have 3, and "f" must have at least 3 vertex references. Lines that fail validation are counted and reported in the conversion summary. Face indices referencing out-of-range vertices are flagged as errors. The converter continues processing valid lines rather than aborting on the first error.