Skip to content
Guide

Add a talking AI mascot to your website with Wixzel Voice

At the end of this guide your website has a talking mascot in the corner. Visitors tap Call and talk to an agent that knows your business, in the browser, with no phone line and no app. It takes about 15 minutes: one request makes the agent and its mascot from your site, one turns on the widget, and one script tag puts it on the page. Making the agent is not charged. Calls are billed per second like a call on the same engine: $0.0491 per connected minute on Gemini Live, about $0.15 for a three-minute conversation, from a prepaid balance.

By · Published · Updated

Takes
About 15 minutes
Engine time
$0.0491 per connected minute
A dental clinic website with the mascot widget open at the bottom right: a speech bubble saying hello, a green mascot and a Call button

What do you need before you start?

  • A Wixzel Voice account with credit. Calls through the widget are paid from real credit, not the free test minutes; the minimum top-up is $5.
  • An API key with the agents:write and calls:write scopes, kept on your server. Everything below can also be done in the console, on the agent's Mascot tab.
  • A website served over HTTPS where you can add a script tag. Browsers only give a page the microphone over HTTPS.

How do you build this on Wixzel Voice, step by step?

  1. 01Make the agent from your website

    Give it your site and a role. role is receptionist, support, sales, guide or your own words:

    shell
    curl https://api.voice.wixzel.com/v1/agents/generate \
      -H "Authorization: Bearer $WIXZEL_API_KEY" \
      -H "Content-Type: application/json" \
      -d '{ "website_url": "https://smiledental.example", "role": "receptionist" }'
    make-agent.mjs (TypeScript SDK)
    import { WixzelVoice, waitForAgent } from 'wixzel-voice';
    
    const client = new WixzelVoice({ apiKey: process.env.WIXZEL_API_KEY });
    
    let agent = await client.agents.generate({
      website_url: 'https://smiledental.example',
      role: 'receptionist',
    });
    agent = await waitForAgent(client.agents, agent); // until the mascot is ready or failed
    console.log(agent.id, agent.name, agent.mascot.status, agent.knowledge_base_id);

    It answers at once with an agent that can already talk, and mascot.status: "building". In the background it reads your pages, writes the prompt and opening line, builds a knowledge base from what it read, and draws a mascot in your brand colour. Poll GET /v1/agents/{id} until mascot.status is ready, usually in under a minute; in the SDK, waitForAgent does the polling. A failed build leaves the agent working with the look it had.

    The agent starts on Gemini Live. Change its engine, voice or prompt like any other agent with PATCH /v1/agents/{id}; its mascot stays as it is.

  2. 02Turn on the widget, and choose who can call

    Sharing is off until you turn it on. List the origins your site is served from; the widget will not start a call anywhere else:

    shell
    curl -X PATCH https://api.voice.wixzel.com/v1/agents/AGENT_ID/mascot \
      -H "Authorization: Bearer $WIXZEL_API_KEY" \
      -H "Content-Type: application/json" \
      -d '{
        "welcome_message": "Hi! I am Molly from Smile Dental. Tap Call to talk to me.",
        "sharing": {
          "embed": true,
          "embed_origins": ["https://smiledental.example", "https://www.smiledental.example"],
          "caller_info": "contact",
          "max_call_seconds": 300,
          "daily_minutes": 60,
          "calls_per_visitor_daily": 3,
          "max_concurrent_calls": 2
        }
      }'

    caller_info is what a visitor gives before a call: none (the default) asks for nothing, contact asks for a name and a phone number or email, and google asks for a Google sign-in. A Google sign-in tells you who they are and never creates a Wixzel account for them; on your site it opens in a small window on voice.wixzel.com, which hands the result back only to an origin in embed_origins.

    The four caps keep public calls inside a budget: the longest call, public minutes a day for everyone together (until midnight UTC), calls one visitor may make a day, and calls at once. The values above are the defaults. Add "link": true to get a share page at voice.wixzel.com/m?id=… as well.

    The response carries mascot.public_id, such as m_4fT9qLx2Bv8K. It is the id in the script tag.

  3. 03Paste one script tag

    Add this to every page that should show the mascot, before the closing body tag:

    index.html
    <script src="https://voice.wixzel.com/embed.js" data-mascot="m_4fT9qLx2Bv8K" async></script>

    The mascot waits in the bottom right corner with its welcome message. A visitor taps Call, allows the microphone and talks; the mascot listens, thinks and moves its mouth with the agent's voice. The widget runs in a shadow root, so your CSS and its CSS never meet.

  4. 04Place it yourself, and let the agent act on your page

    To show it inside your own element instead of the corner, leave data-mascot off the tag and call WixzelMascot.mount once the script has loaded.

    A client tool runs on your page when the agent asks for it, for example to open the booking page. Create the tool for the agent in the console or with POST /v1/tools, then register what it does, before or after the script loads:

    index.html
    <div id="talk"></div>
    <script>
      window.WixzelMascot = Object.assign(window.WixzelMascot || {}, {
        tools: {
          open_page: ({ path }) => {
            location.href = path;
            return { opened: path };
          },
        },
      });
    </script>
    <script
      src="https://voice.wixzel.com/embed.js"
      async
      onload="WixzelMascot.mount(document.getElementById('talk'), { mascot: 'm_4fT9qLx2Bv8K' })"
    ></script>

    Whatever a handler returns goes back to the agent, which tells the caller. Webhook tools, which call your server, work on the widget too.

  5. 05See who called, and block someone

    Every widget call records its caller. List an agent's callers:

    shell
    curl "https://api.voice.wixzel.com/v1/callers?agent_id=AGENT_ID&limit=20" \
      -H "Authorization: Bearer $WIXZEL_API_KEY"
    
    curl -X PATCH https://api.voice.wixzel.com/v1/callers/CALLER_ID \
      -H "Authorization: Bearer $WIXZEL_API_KEY" \
      -H "Content-Type: application/json" \
      -d '{ "blocked": true }'

    Each caller has an approximate location (city, region and country, worked out from the IP address, which is kept only as a hash), platform (browser, operating system and device), the page_url they called from, what they gave you, and call_count. A random id their browser keeps groups one person's calls; there is no fingerprinting, and the widget tells callers what is shared with you.

    A blocked caller cannot call that agent again from the widget, the share link, the app or by phone. Each call is also in GET /v1/calls with its transcript and cost, filterable by caller_id.

What does this build cost on Wixzel Voice?

Engine time for 3-minute sessions on the gemini-live engine at $0.0491 per connected minute: about $0.15 per session. There is no telephony cost, because there is no phone line.

Monthly engine cost for this guide’s build
Sessions per monthConnected minutesEngine cost per month
300900$44.19
1,5004,500$221
6,00018,000$884

Making the agent and its mascot from your website is not charged, and neither is the widget. Calls cost what a call on the agent's engine costs, per second, from your prepaid balance, with no phone line to pay for. With the default cap of 60 public minutes a day, the widget can spend at most about $2.95 a day on Gemini Live.

Prepaid, with no subscription and no free tier: add credit from $5 and usage spends it. Estimate your own mix.

Which Wixzel Voice limits apply to this build?

  • Audio is phone quality, G.711 µ-law at 8 kHz in both directions.
  • The widget starts calls only from the origins in embed_origins, up to 20 of them.
  • Public calls stay inside the caps on the agent. Past daily_minutes, calls are refused until midnight UTC.
  • Widget calls count toward the account's concurrent-call limit, five by default, alongside phone calls and app sessions. max_concurrent_calls keeps a busy page from taking all of them.
  • Widget calls use real credit. The free test minutes are for talking to your own agents from the console.
  • There is no transfer to a person from a web call; transfers need a phone line.

Frequently asked questions

How do I put a talking AI mascot on my website?

Make an agent with POST /v1/agents/generate (or New agent, From your website, in the Wixzel Voice console), turn on its widget with PATCH /v1/agents/{id}/mascot and your site in embed_origins, and add <script src="https://voice.wixzel.com/embed.js" data-mascot="m_…" async></script> to your pages. Visitors tap Call and talk to it in the browser.

Does the website widget work with any website builder?

Yes, anywhere you can add a script tag to the page: plain HTML, WordPress, Webflow, Shopify themes, Next.js and so on. The page has to be served over HTTPS for the browser to allow the microphone, and its origin has to be in embed_origins.

Can another site copy my embed code and use my credit?

No. The widget only starts calls from the origins you listed, and the session is tied to that page. If an id leaks anyway, POST /v1/agents/{id}/mascot/rotate-public-id gives the mascot a new one and the old embed code and link stop working at once.

Can the mascot speak Hindi or Malayalam?

Yes. Set the agent's language and engine like any agent: Gemini Live covers many languages, and the sarvam engine is built for Indian languages, including Hindi, Tamil, Telugu, Kannada and Malayalam. The mascot's mouth follows whatever audio the agent sends.

Can I change how the mascot looks?

Yes. Send a new spec with PATCH /v1/agents/{id}/mascot: a shape (circle, drop, triangle, cloud, pill, flower, squircle, blob or heart), a colour and an eye style. Or call POST /v1/agents/{id}/mascot/generate with a website or a description for a new look. The agent's prompt does not change when its look does.

Where to read more

  • Mascotsdocs

    The look, the share link, the widget, who can call and the caps.

  • Callersdocs

    Caller records, the caller on each call, and blocking.

  • Toolsdocs

    Webhook tools and client tools, including on your website.

  • Knowledge basesdocs

    What an agent made from a website knows, and adding documents.

APIs for agentic telephony

About Wixzel Voice

Wixzel Voice is a voice AI API for building AI agents that place and answer real phone calls over your own SIP trunk, or talk to people in your web and mobile apps. One API key and one prepaid balance cover every voice engine, billed per second of actual usage.

Build your first voice agent