Best practices
3DVue
Technical guides for preparing your 3D files, textures, proofing assets and integrating the configurator on your site. Last updated April 2026.
Preparing your 3D files
Accepted formats, conversion rules and Blender best practices for a friction-free integration.
Accepted formats
The 3DVue platform accepts several 3D formats. GLTF is the recommended format : it offers the best quality-to-file-size ratio for real-time web rendering.
Converting from SolidWorks : STEP / STL → GLTF
Files from CAD software (SolidWorks, Fusion 360, CATIA) are generally in .STEP, .STP or .STL format. They must be converted before integration.
1. Open FreeCAD 2. Import the STEP/STL file Ctrl + I → select your .stp or .stl file 3. Export to GLTF or DAE Ctrl + E → choose DAE or GLTF format Online converter (quick alternative): https://imagetostl.com/fr/convertir/un-fichier/stp/en/glb
Export from Blender
If you work directly in Blender, here are the recommended GLTF export settings for the 3DVue platform. Using Draco compression significantly reduces the file size.
Format: glTF Binary (.glb) ← bundles everything into one file Compression: Draco enabled ← reduces file size by 60–80% Textures: Include → check Materials: Export materials → check Transforms: Apply → check ← required, see Transforms section
Blender collection naming
Scripts automate the export of GLTF files and UV maps. For them to work correctly, Blender collections must follow a precise structure.
Collection └── product-name ← no accents or spaces ├── modelisation ← all 3D objects └── gltf ← generated export files Correct examples: product-name: butterfly-chair ✓ product-name: tolix-chair-a ✓ Incorrect examples: product-name: Butterfly Chair ✗ uppercase + space product-name: siège-étagère ✗ accented characters
Transforms & scale
- Always apply transforms Ctrl + A → All Transforms before exporting : otherwise UV maps are incorrect
- Work at scale 1 (real-world scale in metres) : avoids scale errors in the configurator
- If an object does not touch the ground (e.g. a pendant light), add an invisible plane named RA sized 0.0001m at position 0,0,0 for augmented reality
UV Mapping
UV unwrapping determines the quality of texture rendering. A poorly done UV creates visible distortions : patterns stretch or compress on certain faces.
Recommended Blender addons
These addons are used systematically by the 3DVue team to guarantee quality UVs on all projects.
| Addon | Main use |
|---|---|
| UV Toolkit | Checker map to visualise UV distortions : essential for verifying unwrap quality before export |
| Texel Density | Ensures density consistency across all objects in the same project. If wood appears on multiple objects, it must always have the same apparent size |
| UVPackmaster | Optimises the placement of UV islands on the map, manages orientation based on object direction (useful for wood, directional-pattern fabrics) |
| Mio3 | Straightens distorted UVs, allows overlapping similar UVs (saves space on the UV map) |
Texel Density consistency
Texel density defines how many texture pixels cover a given real surface area. If two objects from the same client have different texel densities, a wood texture will appear at different scales on each object : which is not realistic.
Favour UV unwraps based on seams with the Conformal method : except for objects with a uniform colour that do not need a precise unwrap.
UV for SVG proofing
When the configurator uses an SVG proof (personalisation with logo upload or text), additional rules apply to UV unwrapping.
- All UVs must fit on a single UV map
- Export the UV map at 4096×4096 px
- The GLTF must correspond exactly to the exported UV map
- A Blender script automates the export of the GLTF and UV map : collections must be correctly named for it to work
- If needed, paint on the UV map to assist with creating the Illustrator file (pattern alignment)
PBR Textures
Naming conventions, formats and specifications for texture files compatible with the 3DVue platform.
Texture file naming
Each PBR channel corresponds to a texture file with a standardised name. The platform identifies the role of each texture by its name.
| File name | Role | Support |
|---|---|---|
| albedo | Base colour of the material (also called diffuse) | ✅ Full |
| roughness | Glossiness level : white = matte, black = glossy | ✅ Full |
| metallic | Metallic properties : environment reflections | ✅ Full |
| normal | Faux relief : simulates bumps and indentations without extra polygons | ✅ Full |
| emissive | Luminous areas (LEDs, screens, backlit parts) | ✅ Full |
| occlusion | Contact shadows between surfaces (ambient occlusion) | ✅ Full |
| bump | Alternative to normal map : ignored if a normal map is already present | ⚠️ Ignored if normal present |
| alpha | Transparency : to be tested per use case, not compatible with AR | ⚠️ Not compatible with AR |
Formats & resolution
- Square format required : 1024×1024 or 2048×2048 (maximum 2K)
- File format: PNG (recommended for transparency and quality) or JPEG (lighter file size)
- An overly heavy normal map can be losslessly compressed via imagecompressor.com
Creating an SVG proof
Illustrator guide for personalisation projects : logo upload, engraved text, marking zones. The SVG proof is the production file generated by the configurator.
General rules
- Square format required, 4K resolution (4096×4096 px)
- Naming: BAT-modelname-dimension_albedo.svg
- No accented characters, no spaces in the file name
- All editable elements must be vectorised in the SVG : no raster elements
Format: BAT-modelname-dimension_albedo.svg Examples: BAT-matchjersey-sizeL_albedo.svg ✓ BAT-cup-25cl_albedo.svg ✓ BAT-match jersey size L albedo.svg ✗ spaces not allowed BAT-matchjersey-sizelé_albedo.svg ✗ accented characters not allowed
Illustrator layer structure
Illustrator layers must be organised according to a precise structure so that the configurator can identify editable zones and reference zones.
| Layer name | Role | Editable? |
|---|---|---|
| masqué | Working layer : test elements or elements set aside without deletion | ✅ Free |
| non vecto | Non-vectorised text kept for reuse : not exported | ✅ Free |
| gabarit | 3D model boundaries : placement guide, do not modify | 🚫 Do not touch |
| logo | All logos correctly renamed | ✅ Free |
| design, design-1, design-2… | Graphic elements for each design variant | ✅ Free |
| présentation | Template common to all designs : do not modify | 🚫 Do not touch |
SVG export from Illustrator
- Vectorise all editable elements before export : Shift + Ctrl + O
- Name the exported file using the convention designname_albedo.svg
- No raster elements in the exported file : everything must be vector
- Check that the gabarit and présentation layers are hidden on export
Shift + Ctrl + O : vectorise selected shape
Ctrl + C : copy
Ctrl + Shift + V : paste in place
Illustrator renaming script
JSX script to automatically rename selected layers to the color_XXX format. Considerable time saving on projects with many editable zones.
Installation
1. Copy the code below into a text file 2. Rename the file to RenameColor.jsx 3. Copy to the Illustrator scripts folder: C:\Program Files\Adobe\Adobe Illustrator 2026\Presets\fr_FR\Scripts\ 4. Run from Illustrator: File → Scripts → RenameColor
Script code
// Script Rename Color : Ultra Fast // Renames all selected objects to "color_XXX" (function() { if (app.documents.length === 0) { alert("Please open an Illustrator document."); return; } var doc = app.activeDocument; var selection = doc.selection; if (selection.length === 0) { alert("Please select at least one object to rename."); return; } var number = prompt("Number (e.g. 001, 002, etc.):", "001"); if (number === null || number === "") { return; } var finalName = "color" + number; for (var i = 0; i < selection.length; i++) { selection[i].name = finalName; } alert(selection.length + " object(s) renamed to: " + finalName); })();
Embedding the 3DVue viewer
The 3DVue viewer is a native Web Component. It works in any HTML environment : Shopify, WooCommerce, PrestaShop, WordPress, or a custom site.
Include the script
Add the script once in your <head> or before </body>. One inclusion is enough for all pages of your site.
<script src="https://cdn.jsdelivr.net/gh/3dvue/api@v4/viewer-3dvue-min.js"></script>
Declare the component
Place the <viewer-3dvue> tag where you want the viewer to appear. Two attributes are required: name (unique identifier on the page) and src (URL of your configurator, provided by 3DVue at delivery).
<!-- Required attributes --> <viewer-3dvue name="myViewer" src="https://app.3dvue.fr/view?p=AB01-CD02" ></viewer-3dvue> <!-- With debug enabled (console logs) --> <viewer-3dvue name="myViewer" src="https://app.3dvue.fr/view?p=AB01-CD02" debug ></viewer-3dvue>
Control without JavaScript
The component automatically listens for click and change events on any element carrying the attributes below. No JavaScript needed.
| Attribute | Value | Usage |
|---|---|---|
| viewer-3dvue | Name of the targeted viewer | Required on every trigger element |
| viewer-3dvue-clic | setMaterial | Triggers a material change on click |
| viewer-3dvue-change | setMaterial | Triggers a change on <select> selection |
| viewer-3dvue-meshs-materials | JSON {"meshIndex":"materialId"} | Materials to apply (multiple meshes supported) |
| viewer-3dvue-mesh | "1,2,3" | Targeted mesh indexes for a <select> |
<!-- Button that changes multiple materials on click --> <button viewer-3dvue="myViewer" viewer-3dvue-clic="setMaterial" viewer-3dvue-meshs-materials='{"1":"0n","3":"2b"}' > Midnight Blue </button> <!-- Select that applies the chosen value --> <select viewer-3dvue="myViewer" viewer-3dvue-change="setMaterial" viewer-3dvue-mesh="2,4" > <option value="0n">Red</option> <option value="1a">Blue</option> </select>
JavaScript API
For advanced cases : dynamic loading, image capture, SVG export. Retrieve the component reference via querySelector.
| Method | Description |
|---|---|
| setMaterial(materials, index) | Applies materials to the meshes of an object |
| loadModel(id) | Replaces the current model |
| addModel(id) | Adds an object to the scene |
| removeModel(index) | Removes an object by its index |
| resetCamera() | Resets the camera to its initial position |
| pauseRenderer() / startRenderer() | Manual renderer control (managed automatically by IntersectionObserver) |
| captureToBase64() | Captures the render as a base64 image → onCaptureBase64Complete event |
| exportSVG() | Generates the SVG proof for the product → onSVGExportComplete event |
| addSVGText(text, opts) | Adds text on an editable zone of the product |
| addSVGImage(source, opts) | Adds an image (File or ArrayBuffer) on an editable zone |
| loadFonts(fonts) | Preloads Google Fonts or custom .woff2 fonts |
| setSVGElementParam(param, value, id) | Modifies a parameter of an SVG element : fill, text, fontFamily, scaleX, scaleY, angle, colorStop.N. Without id: applies to the currently selected element |
| removeSVGElement(id) | Removes an added SVG element (text or image). Without id: removes the selected element |
| showSVG2D() / hideSVG2D() | Switches the viewer to flat 2D view for SVG editing / back to 3D view |
| captureSVGToBase64() | Captures the SVG texture as a base64 image |
Events
Listen to events directly on the viewer-3dvue element via addEventListener.
| Event | e.detail properties | Description |
|---|---|---|
| onLoadComplete | - | Viewer loaded and ready : recommended time to call loadFonts() |
| onCaptureBase64Complete | base64, error | Render captured by captureToBase64() |
| onSVGExportComplete | path, error | Proof generated by exportSVG() : path = URL of the file on the server |
| onSVGObjectSelected | obj.id, obj.type, obj.text, obj.fill, obj.fontFamily, obj.scale, obj.angle | An SVG element has been selected in the viewer |
| onSVGObjectDeselected | - | The active SVG element has been deselected |
// Get the component reference const viewer = document.querySelector('viewer-3dvue[name="myViewer"]'); // Wait for the viewer to be ready (recommended for loadFonts) viewer.addEventListener("onLoadComplete", () => { viewer.loadFonts([{ family: "Bebas Neue" }, { family: "Pacifico" }]); }); // Change materials viewer.setMaterial({ "1": "0n", "3": "2b" }); // Modify the selected SVG element viewer.setSVGElementParam("fill", "#ff0000"); // colour viewer.setSVGElementParam("text", "My text"); // text content viewer.setSVGElementParam("colorStop.0", "#7C3AED", "zone-id"); // gradient // React to SVG element selection viewer.addEventListener("onSVGObjectSelected", (e) => { const obj = e.detail.obj; // obj.id, obj.type, obj.text, obj.fill, obj.fontFamily, obj.scale, obj.angle if (obj.type === "text") inputText.value = obj.text ?? ""; }); viewer.addEventListener("onSVGObjectDeselected", () => { inputText.value = ""; }); // Capture the current render viewer.captureToBase64(); viewer.addEventListener("onCaptureBase64Complete", (e) => { const { base64, error } = e.detail; if (!error) document.querySelector("#preview").src = base64; });
Matthieu replies directly : no ticketing, no delay. If something is unclear or your case is not covered here, book a meeting.