Skip to main content
New tool CRON Expression Builder — preview next run times before you schedule Apex. Open the builder →
A visual guide demonstrating how to implement Text-to-Speech LWC in a Salesforce application interface.
LWC

Text-to-Speech LWC Guide - Browser-Based Voice for Salesforce

I found a very simple way to make Salesforce components talk using the native Web Speech API. It covers a lot of accessibility and Agentforce ground, and it does not hit any governor limits.

A client asked me for a way to read out case updates for visually impaired users, and that is when I realised how little work a Text-to-Speech LWC actually takes. You don't need an expensive third-party integration or a heavy library to make your Salesforce org talk to you. Most modern browsers already do the work for us through the Web Speech API.

Why you should consider Text-to-Speech LWC for your next project

We tend to think of accessibility as high-contrast colors and screen reader support. Giving a user a native way to hear text is a big win on top of that. I've seen teams add it to Experience Cloud portals for people who struggle with long blocks of text, and it puts a bit of personality into a custom component along the way.

Voice is also becoming the standard as more of the platform leans on AI. If you're looking into Agentforce use cases, a component that can actually speak the agent's response makes the whole experience feel more natural. It all runs in the browser, so none of it counts against your Salesforce governor limits.

Building a basic Text-to-Speech LWC from scratch

You work with the speechSynthesis interface, which is part of the Web Speech API. Create an "utterance" (the text you want spoken), tell the browser which voice to use, and hit play. Here is how I usually structure the code.

The JavaScript logic

One thing that trips people up is that voices don't always load immediately. Check that the browser supports speech before you try to run the function. Here's a clean way to handle the logic:

import { LightningElement, track } from 'lwc';

export default class TextToSpeechLwc extends LightningElement {
    @track textToSpeak = 'Welcome to the Salesforce ecosystem!';

    handleInputChange(event) {
        this.textToSpeak = event.target.value;
    }

    speak() {
        if (!window.speechSynthesis) {
            console.error('This browser does not support text-to-speech.');
            return;
        }

        // Always stop any current speech before starting new audio
        window.speechSynthesis.cancel();

        const utterance = new SpeechSynthesisUtterance(this.textToSpeak);
        utterance.lang = 'en-US';

        // Grab the available voices from the browser
        const voices = window.speechSynthesis.getVoices();
        if (voices.length > 0) {
            // I usually just grab the first English voice found
            utterance.voice = voices.find(v => v.lang.includes('en')) || voices[0];
        }

        window.speechSynthesis.speak(utterance);
    }
}

The HTML template

The UI can stay plain. A textarea and a button do the job. If you're building something more involved, LWC component communication lets you trigger the speech from a parent component.

<template>
    <lightning-card title="Voice Assistant" icon-name="utility:volume_high">
        <div class="slds-var-p-around_medium">
            <lightning-textarea 
                label="Enter text to hear it aloud" 
                value={textToSpeak} 
                onchange={handleInputChange}>
            </lightning-textarea>
            <lightning-button 
                label="Speak Now" 
                onclick={speak} 
                variant="brand" 
                class="slds-var-m-top_small">
            </lightning-button>
        </div>
    </lightning-card>
</template>

Real-world tips for the Text-to-Speech LWC

Just because your app can talk doesn't mean it should talk all the time. Most teams get this wrong by making it too intrusive. Here's what I've learned from running this in production orgs:

  • Don't auto-play. Browsers usually block audio that starts without a user click anyway, so wait for the user to trigger the speech.
  • Add a stop button. There is nothing more annoying than a three-minute paragraph you can't silence. Use window.speechSynthesis.cancel() to give users control.
  • Check mobile. Safari on iOS can be picky with the Web Speech API, so test on a physical device rather than the Chrome emulator.
  • Watch the language. If your users are global, don't hardcode 'en-US'. Grab the user's locale from Salesforce and match the voice accordingly.

Pro Tip: The getVoices() method is often called asynchronously. If it returns an empty list the first time, you might need to listen for the voiceschanged event before selecting a voice.

Key takeaways

  • A Text-to-Speech LWC is a browser-native way to improve accessibility without extra costs.
  • Use speechSynthesis.cancel() before every new utterance to prevent overlapping audio.
  • Always provide a clear UI control so users can start and stop the voice as they please.
  • This approach works well for Experience Cloud sites and custom internal tools.

Is a Text-to-Speech LWC something every org needs? Probably not. For a specific accessibility requirement, or for making a custom app feel more modern, it's worth keeping in your back pocket. It's lightweight and needs no server-side Apex logic. Try it in your sandbox and see how it changes the user experience.

Newsletter

One email every Tuesday

New guides, tool updates, and the release-note changes that break things.

No spam. Unsubscribe in one click.

Comments

Loading comments...

Leave a Comment