Building a Custom Language Switcher

While SwiftLingo provides a ready-to-use language switcher, you might want to build your own custom switcher to perfectly match your website’s design, integrate with existing UI components, or implement unique language selection logic. This guide explains the technical details you need to know to create your own language switcher.

How SwiftLingo Handles Languages

SwiftLingo uses language-specific subdomains to serve translated content. For example, if your original website is example.com and you translate it into French and German, the translated versions will be accessible at fr.example.com and de.example.com respectively. The original language version remains at example.com.

To switch languages, your custom switcher will need to redirect the user to the appropriate language subdomain for the current page.

Key Concepts for a Custom Switcher

1. Getting the Current Language

The current language of the page can typically be inferred from the URL’s subdomain. For example, if the URL is fr.example.com/about-us, the current language is French (fr). If the URL is example.com/about-us, it’s the original language.

You can also leverage the document.documentElement.lang attribute, which SwiftLingo sets to the active language code.

2. Constructing Language-Specific URLs

To switch to a different language, you need to construct the correct URL for the current page in the target language. This involves modifying the hostname of the current URL.

Let’s assume your original domain is your-website.com.

  • Original Language URL: https://your-website.com/path/to/page
  • Translated Language URL (e.g., French): https://fr.your-website.com/path/to/page

Here’s a JavaScript example of how you might construct these URLs:

function getLanguageUrl(targetLangCode) {
    const currentUrl = new URL(window.location.href);
    const hostnameParts = currentUrl.hostname.split('.');

    // Remove existing language subdomain if present
    if (hostnameParts.length > 2 && hostnameParts[0].length === 2) {
        // Assuming two-letter language codes like 'fr.example.com'
        hostnameParts.shift(); // Remove the language code
    }

    let newHostname;
    if (targetLangCode === 'original') { // Or your original language code, e.g., 'en'
        newHostname = hostnameParts.join('.');
    } else {
        newHostname = `${targetLangCode}.${hostnameParts.join('.')}`;
    }

    currentUrl.hostname = newHostname;
    return currentUrl.toString();
}

// Example usage:
// const frenchUrl = getLanguageUrl('fr');
// const originalUrl = getLanguageUrl('original'); // Or getLanguageUrl('en') if 'en' is original

3. Triggering a Language Change

Once you have the target language URL, you can trigger the language change by navigating the user to that URL. The simplest way is to set window.location.href:

function switchLanguage(targetLangCode) {
    const newUrl = getLanguageUrl(targetLangCode);
    window.location.href = newUrl;
}

// Example: switchLanguage('de');

4. Notifying Other Components of Language Changes

When your custom language switcher successfully changes the language (by navigating to the new URL), it’s good practice to dispatch a custom event. This allows other parts of your application to react to the language switch, ensuring consistency and enabling dynamic updates without requiring a full page reload for every component.

SwiftLingo’s built-in switcher dispatches a languageChange event. You can dispatch a similar event from your custom switcher to maintain compatibility and allow other components to listen for a single, consistent event.

Dispatching the Event

After window.location.href = newUrl; (or after your chosen method of navigation), you can dispatch a CustomEvent:

window.dispatchEvent(new CustomEvent('languageChange', {
    detail: { language: targetLangCode }
}));

Listening for the Event

Other parts of your application can then listen for this event:

window.addEventListener('languageChange', (event) => {
    const newLanguage = event.detail.language;
    console.log('Custom switcher: Language switched to:', newLanguage);
    // Perform actions based on the new language
    // e.g., update UI elements, re-fetch data, etc.
});

For more details on listening for language change events, refer to the Listening for Language Change Events documentation.

Example: A Simple Custom Dropdown

Here’s a basic HTML and JavaScript example for a custom dropdown language switcher:

<select id="custom-language-selector">
    <option value="en">English</option>
    <option value="fr">Français</option>
    <option value="de">Deutsch</option>
</select>

<script>
    document.addEventListener('DOMContentLoaded', () => {
        const selector = document.getElementById('custom-language-selector');

        // Set initial selection based on current page language
        const currentLang = document.documentElement.lang; // SwiftLingo sets this
        if (selector) {
            selector.value = currentLang;
        }

        selector.addEventListener('change', (event) => {
            const targetLangCode = event.target.value;
            const newUrl = getLanguageUrl(targetLangCode);
            window.location.href = newUrl;
        });

        function getLanguageUrl(targetLangCode) {
            const currentUrl = new URL(window.location.href);
            const hostnameParts = currentUrl.hostname.split('.');

            // Assuming two-letter language codes like 'fr.example.com'
            // Adjust logic if your original domain has more parts (e.g., 'www.example.com')
            if (hostnameParts.length > 2 && hostnameParts[0].length === 2) {
                hostnameParts.shift(); // Remove the language code
            }

            let newHostname;
            // Assuming 'en' is the original language and doesn't use a subdomain
            if (targetLangCode === 'en') {
                newHostname = hostnameParts.join('.');
            } else {
                newHostname = `${targetLangCode}.${hostnameParts.join('.')}`;
            }

            currentUrl.hostname = newHostname;
            return currentUrl.toString();
        }
    });
</script>

This example provides a starting point. You can expand upon it to include flags, native language names, and more sophisticated UI/UX elements as needed for your specific use case.

Was this page helpful?