Bodygram
DrawUtils

Draw avatar

Render the bare 3D avatar from any supported Bodygram or Body2Fit estimation response.

Overview

drawAvatar(response, options) renders the interactive 3D avatar mesh from any estimation response that includes one. There are no overlays — just the avatar.

This is the most general draw method: it works with both Bodygram Scanner Platform responses (where the avatar arrives as a base64-encoded .obj) and Body2Fit responses (where it arrives as a .glb). DrawUtils normalizes the two formats internally, so your code doesn't need to branch on response type.


Supported responses

Source methodAvatar fieldNotes
getBodygramScannerPlatformPhotoEstimationentry.avatar (.obj)
getBodygramScannerPlatformStatsEstimationentry.avatar (.obj)Avatar is generated from the supplied stats.
getBody2FitPhotoEstimationestimations.glb
getBody2FitStatsEstimationestimations.glb
getBody2FitTokenEstimationestimations.glb

drawAvatar throws if the response is missing avatar data — for Body2Fit responses, that means the request was made without GLB output enabled.


Usage

Bodygram Scanner Platform

const utils = new BodygramSDKDrawUtils({ locale: 'en' });

const response = await sdk.getBodygramScannerPlatformPhotoEstimation({ /* … */ });

utils.drawAvatar(response, { container: 'avatar' });

Body2Fit

const utils = new BodygramSDKDrawUtils({ locale: 'en' });

const response = await sdk.getBody2FitPhotoEstimation({ /* … */ });

utils.drawAvatar(response, { container: 'avatar' });
<div id="avatar"></div>

The method returns the rendered DOM node, so you can also append it yourself:

const node = utils.drawAvatar(response, { container: null });
myCustomMount.appendChild(node);

Reference


Localization

The bare avatar has no labels of its own, but the locale you pass to the DrawUtils constructor is forwarded to the rendered avatar canvas — so any text rendered by the canvas (and by the rings, indicators, and posture overlays drawn from the same instance) follows the same locale. See supported locales for the accepted codes.

const utils = new BodygramSDKDrawUtils({ locale: 'ja' });
utils.drawAvatar(response, { container: 'avatar' });

Playground

Try drawAvatar with a Bodygram Scanner Platform sample, a Body2Fit sample, or your own response. Each render hands the full response straight to DrawUtils — no extra wiring required.

Interactive Demo

Scan response

Fetched from /success-response/platform-success-response-2.json.

Locale

Locale is forwarded to the rendered avatar canvas and reflected in the snippet on the right.

Avatar

Loading…
index.html · UMD
<!doctype html>
<html>
<head>
  <meta charset="utf-8" />
  <title>Bodygram DrawUtils — Avatar</title>
  <style>
    body { font-family: system-ui, sans-serif; margin: 24px; }
    #avatar { width: 100%; aspect-ratio: 3 / 4; background: #ffffff; border: 1px solid #e5e5e5; }
  </style>

  <!-- 1. Bodygram Headless SDK (UMD) — produces the estimation response -->
  <script src="https://headless.body2fit.bodygram.com/sdk.umd.js"></script>

  <!-- 2. three.js — UMD requires three <= 0.160.0 -->
  <script src="https://unpkg.com/three@0.160.0/build/three.min.js"></script>

  <!-- 3. DrawUtils (UMD build) -->
  <script src="https://headless.body2fit.bodygram.com/sdk.drawutils.umd.js"></script>
</head>
<body>
  <div id="avatar"></div>

  <script>
    (async () => {
      // 1. Run a scan and estimate measurements with the main SDK.
      //    `token` comes from your server, where your API key lives.
      const sdk = new BodygramSDK({ clientKey: 'YOUR_CLIENT_KEY', locale: 'en' });
      const { front, side } = await sdk.scan();
      const response = await sdk.getBodygramScannerPlatformPhotoEstimation({
        token,
        front,
        side,
        age: 25,
        gender: 'male',
        height: 1800,
        weight: 70000,
      });

      // 2. Hand the full response to DrawUtils.
      const utils = new BodygramSDKDrawUtils({ locale: 'en' });
      utils.drawAvatar(response, { container: 'avatar' });

      // ---
      // The same drawAvatar call also accepts Body2Fit responses:
      //
      //   const b2f = await sdk.getBody2FitPhotoEstimation({ … });
      //   utils.drawAvatar(b2f, { container: 'avatar' });
      //
      // DrawUtils normalizes the avatar format (.obj vs .glb)
      // internally — your code path stays the same.
    })();
  </script>
</body>
</html>

How it works

The playground does what the snippet on the right does:

  1. Load three.js and DrawUtils. The UMD example loads three@0.160.0 first (the last UMD release on npm) so it attaches to window.THREE, then loads sdk.drawutils.umd.js which reads THREE off the global. The ES example skips both globals and uses an importmap to resolve the bare import "three" inside the ES build.
  2. Fetch the scan response. In production you call your own server endpoint that proxies the estimation method so your API key never reaches the browser. The playground uses static samples at /success-response/platform-success-response-2.json and /b2f-responses/b2f-photo-success-avatar-response.json.
  3. Construct DrawUtils. A single instance is reused across renders.
  4. Draw the avatar. drawAvatar mounts an interactive avatar canvas inside the target container and returns the node. The same call works for both response types — DrawUtils normalizes the avatar format internally.

On this page