<div class="supt-country-picker">
    <div class="supt-country-picker__wrapper">
        <div class="supt-country-picker__header">
            <p class="supt-country-picker__title">Select your country</p>
            <button class="supt-country-picker__close-btn" aria-label="Close">
                <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 12 12" fill="none" stroke="currentColor" stroke-width="1.5">
                    <path d="M0.75 0.75L11.25 11.25" stroke-linecap="round" />
                    <path d="M11.25 0.75L0.75 11.25" stroke-linecap="round" />
                </svg>
            </button>
        </div>

        <div class="supt-country-picker__content">
            <!-- Europe Section -->
            <div class="supt-country-picker__region -europe">
                <p class="supt-country-picker__region__title">Europe</p>
                <div class="supt-country-picker__countries">
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.be" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/belgium.svg" alt="Belgium">
                                <span class="supt-button-country__title">Belgium</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.dk" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/denmark.svg" alt="Denmark">
                                <span class="supt-button-country__title">Denmark</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.fi" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/finland.svg" alt="Finland">
                                <span class="supt-button-country__title">Finland</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.fr" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/france.svg" alt="France">
                                <span class="supt-button-country__title">France</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.de" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/germany.svg" alt="Germany">
                                <span class="supt-button-country__title">Germany</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.it" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/italy.svg" alt="Italy">
                                <span class="supt-button-country__title">Italy</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.ie" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/ireland.svg" alt="Ireland">
                                <span class="supt-button-country__title">Ireland</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.nl" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/netherlands.svg" alt="Netherlands">
                                <span class="supt-button-country__title">Netherlands</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.no" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/norway.svg" alt="Norway">
                                <span class="supt-button-country__title">Norway</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.securitasdirect.pt" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/portugal.svg" alt="Portugal">
                                <span class="supt-button-country__title">Portugal</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.securitasdirect.es" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/spain.svg" alt="Spain">
                                <span class="supt-button-country__title">Spain</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.se" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/sweden.svg" alt="Sweden">
                                <span class="supt-button-country__title">Sweden</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.co.uk" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/uk.svg" alt="UK">
                                <span class="supt-button-country__title">UK</span>
                            </span>
                        </a>
                    </div>
                </div>
            </div>

            <!-- Latin America Section -->
            <div class="supt-country-picker__region -latin-america">
                <p class="supt-country-picker__region__title">Latin America</p>
                <div class="supt-country-picker__countries">
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.com.ar" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/argentina.svg" alt="Argentina">
                                <span class="supt-button-country__title">Argentina</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.com.br" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/brazil.svg" alt="Brazil">
                                <span class="supt-button-country__title">Brazil</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.cl" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/chile.svg" alt="Chile">
                                <span class="supt-button-country__title">Chile</span>
                            </span>
                        </a>
                    </div>
                    <div class="supt-country-picker__country">
                        <a href="https://www.verisure.pe" class="supt-button-country" target="_blank" rel="noopener noreferrer">
                            <span class="supt-button-country__inner">
                                <img class="supt-button-country__flag" src="/sites/gv/files/flmngr/countries/peru.svg" alt="Peru">
                                <span class="supt-button-country__title">Peru</span>
                            </span>
                        </a>
                    </div>
                </div>
            </div>
        </div>
    </div>

    <div class="supt-country-picker__overlay" aria-hidden="true"></div>
</div>

No notes defined.

<div class="supt-country-picker">
	<div class="supt-country-picker__wrapper">
		<div class="supt-country-picker__header">
			<p class="supt-country-picker__title">Select your country</p>
			<button class="supt-country-picker__close-btn" aria-label="Close">
				{% include '02-icons/close-icon.twig' %}
			</button>
		</div>

		<div
			class="supt-country-picker__content">
			<!-- Europe Section -->
			<div class="supt-country-picker__region -europe">
				<p class="supt-country-picker__region__title">Europe</p>
				<div class="supt-country-picker__countries">
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Belgium',
					href: 'https://www.verisure.be',
					flag: '/sites/gv/files/flmngr/countries/belgium.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Denmark',
					href: 'https://www.verisure.dk',
					flag: '/sites/gv/files/flmngr/countries/denmark.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Finland',
					href: 'https://www.verisure.fi',
					flag: '/sites/gv/files/flmngr/countries/finland.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'France',
					href: 'https://www.verisure.fr',
					flag: '/sites/gv/files/flmngr/countries/france.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Germany',
					href: 'https://www.verisure.de',
					flag: '/sites/gv/files/flmngr/countries/germany.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Italy',
					href: 'https://www.verisure.it',
					flag: '/sites/gv/files/flmngr/countries/italy.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Ireland',
					href: 'https://www.verisure.ie',
					flag: '/sites/gv/files/flmngr/countries/ireland.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Netherlands',
					href: 'https://www.verisure.nl',
					flag: '/sites/gv/files/flmngr/countries/netherlands.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Norway',
					href: 'https://www.verisure.no',
					flag: '/sites/gv/files/flmngr/countries/norway.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Portugal',
					href: 'https://www.securitasdirect.pt',
					flag: '/sites/gv/files/flmngr/countries/portugal.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Spain',
					href: 'https://www.securitasdirect.es',
					flag: '/sites/gv/files/flmngr/countries/spain.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Sweden',
					href: 'https://www.verisure.se',
					flag: '/sites/gv/files/flmngr/countries/sweden.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'UK',
					href: 'https://www.verisure.co.uk',
					flag: '/sites/gv/files/flmngr/countries/uk.svg'
				} %}
					</div>
				</div>
			</div>

			<!-- Latin America Section -->
			<div class="supt-country-picker__region -latin-america">
				<p class="supt-country-picker__region__title">Latin America</p>
				<div class="supt-country-picker__countries">
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Argentina',
					href: 'https://www.verisure.com.ar',
					flag: '/sites/gv/files/flmngr/countries/argentina.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Brazil',
					href: 'https://www.verisure.com.br',
					flag: '/sites/gv/files/flmngr/countries/brazil.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Chile',
					href: 'https://www.verisure.cl',
					flag: '/sites/gv/files/flmngr/countries/chile.svg'
				} %}
					</div>
					<div class="supt-country-picker__country">
						{% include 'atoms/buttons/button-country/button-country.twig' with {
					title: 'Peru',
					href: 'https://www.verisure.pe',
					flag: '/sites/gv/files/flmngr/countries/peru.svg'
				} %}
					</div>
				</div>
			</div>
		</div>
	</div>

	<div class="supt-country-picker__overlay" aria-hidden="true"></div>
</div>
/* No context defined. */
  • Content:
    .supt-country-picker {
    	position: fixed;
    	inset: 0;
    	display: flex;
    	align-items: center;
    	justify-content: center;
    
    	pointer-events: none;
    
    	padding: 16px;
    
    	z-index: $z-index-country-picker;
    
    	&__wrapper {
    		background-color: $color-grey-background;
    
    		width: 100%;
    		height: 100%;
    		max-width: 826px;
    		max-height: 100%;
    		overflow-y: auto;
    		z-index: 1;
    
    		opacity: 0;
    		transform: translateY(20px);
    
    		@media (min-width: $breakpoint-md) {
    			height: auto;
    		}
    	}
    
    	&__header {
    		display: flex;
    		align-items: center;
    		justify-content: space-between;
    		padding: $spacing-4 $spacing-6;
    		background-color: $color-grey-background;
    		border-bottom: 1px solid $color-grey-2;
    
    		position: sticky;
    		top: 0;
    		z-index: 1;
    	}
    
    	&__title {
    		@extend %t-body-sm;
    		font-weight: 500;
    	}
    
    	&__close-btn {
    		@extend %reset-button;
    		color: $color-grey-5;
    
    		svg {
    			display: block;
    			width: 12px;
    			height: 12px;
    		}
    
    		&:hover,
    		&:focus-visible {
    			color: $color-black;
    		}
    	}
    
    	&__content {
    		display: flex;
    		flex-direction: column;
    
    		@media (min-width: $breakpoint-md) {
    			flex-direction: row;
    			justify-content: space-between;
    			padding: $spacing-10 $spacing-6;
    		}
    
    		&::after {
    			content: '';
    			display: none;
    			background-color: $color-grey-2;
    			flex-shrink: 0;
    			order: 1;
    			width: 100%;
    			height: 1px;
    
    			@media (min-width: $breakpoint-md) {
    				display: block;
    				width: 1px;
    				height: auto;
    				margin: calc(22px + $spacing-4) $spacing-6 0;
    			}
    		}
    	}
    
    	&__region {
    		padding: $spacing-6 $spacing-6 $spacing-8;
    		border-bottom: 1px solid $color-grey-2;
    
    		@media (min-width: $breakpoint-md) {
    			padding: 0;
    			border-bottom: none;
    		}
    
    		&__title {
    			@extend %t-body-s;
    			font-weight: 500;
    
    			@media (min-width: $breakpoint-md) {
    				padding-left: $spacing-3-5;
    			}
    		}
    
    		&.-europe {
    			order: 0;
    
    			@media (min-width: $breakpoint-md) {
    				width: 495px;
    			}
    
    			.supt-country-picker__countries {
    				@media (min-width: $breakpoint-md) {
    					columns: 3;
    				}
    			}
    		}
    		&.-latin-america {
    			order: 2;
    			padding-bottom: $spacing-4;
    
    			@media (min-width: $breakpoint-md) {
    				width: 175px;
    				padding-bottom: 0;
    			}
    
    			.supt-country-picker__countries {
    				@media (min-width: $breakpoint-md) {
    					columns: 1;
    				}
    			}
    		}
    	}
    
    	&__countries {
    		columns: 2;
    		margin-top: $spacing-6;
    		column-gap: $spacing-3;
    
    		@media (min-width: $breakpoint-md) {
    			margin-top: $spacing-4;
    			column-gap: 87px;
    		}
    	}
    
    	/* Country Button */
    	&__country {
    		margin-bottom: $spacing-4;
    		@media (min-width: $breakpoint-md) {
    			margin-bottom: 0;
    		}
    	}
    
    	&__overlay {
    		position: absolute;
    		inset: 0;
    		background-color: rgba(0, 0, 0, 0.5);
    
    		opacity: 0;
    		transition: opacity 0.3s ease-in-out 0.1s;
    	}
    
    	&.-is-visible {
    		pointer-events: auto;
    
    		.supt-country-picker__overlay {
    			opacity: 1;
    			transition-delay: 0s;
    		}
    		.supt-country-picker__wrapper {
    			opacity: 1;
    			transform: translateY(0);
    			transition-delay: 0.1s;
    		}
    	}
    
    	body.-is-loaded & {
    		&__wrapper {
    			transition:
    				opacity 0.3s ease-in-out,
    				transform 0.3s ease-in-out;
    		}
    	}
    }
    
  • URL: /components/raw/country-picker/country-picker.css
  • Filesystem Path: src/components/molecules/country-picker/country-picker.css
  • Size: 3.1 KB
  • Content:
    const COUNTRY_PICKER_EVENT_NAME = 'country-picker-toggle';
    export const COUNTRY_PICKER_EVENT = new CustomEvent(COUNTRY_PICKER_EVENT_NAME);
    
    const COUNTRY_PICKER_HASH = '#country-picker';
    
    export class CountryPicker {
    	$element: Element;
    	$closeButton: HTMLElement;
    	$countryButtons: NodeListOf<HTMLElement>;
    	$overlay: HTMLElement;
    	isVisible: boolean;
    	focusableElements: HTMLElement[];
    	firstFocusableElement: HTMLElement | null;
    	lastFocusableElement: HTMLElement | null;
    
    	constructor($element: Element) {
    		// Bindings
    		this.toggle = this.toggle.bind(this);
    		this.close = this.close.bind(this);
    		this.handleKeyDown = this.handleKeyDown.bind(this);
    
    		// Elements
    		this.$element = $element;
    		this.$closeButton = $element.querySelector('.supt-country-picker__close-btn') as HTMLElement;
    		this.$countryButtons = $element.querySelectorAll(
    			'.supt-button-country'
    		) as NodeListOf<HTMLElement>;
    		this.$overlay = $element.querySelector('.supt-country-picker__overlay') as HTMLElement;
    
    		this.isVisible = false;
    		this.firstFocusableElement = null;
    		this.lastFocusableElement = null;
    
    		this.focusableElements = [this.$closeButton, ...this.$countryButtons];
    
    		this.firstFocusableElement = this.focusableElements[0] || null;
    		this.lastFocusableElement = this.focusableElements[this.focusableElements.length - 1] || null;
    
    		this.init();
    	}
    
    	init() {
    		this.bindEvents();
    	}
    
    	bindEvents() {
    		document.addEventListener(COUNTRY_PICKER_EVENT_NAME, this.toggle);
    
    		// Close button functionality
    		if (this.$closeButton) {
    			this.$closeButton.addEventListener('click', this.close);
    		}
    
    		// Keyboard navigation
    		this.$element.addEventListener('keydown', this.handleKeyDown as EventListener);
    
    		this.$overlay.addEventListener('click', this.close);
    
    		// Close on escape key
    		document.addEventListener('keydown', event => {
    			if (event.key === 'Escape' && this.isVisible) {
    				this.close();
    			}
    		});
    
    		// ON hash change
    		window.addEventListener('hashchange', this.onHashChange.bind(this));
    		this.onHashChange(); // Init
    	}
    
    	onHashChange() {
    		if (window.location.hash === COUNTRY_PICKER_HASH) {
    			this.open();
    		}
    	}
    
    	toggle() {
    		if (this.isVisible) {
    			this.close();
    		} else {
    			this.open();
    		}
    	}
    
    	open() {
    		this.isVisible = true;
    
    		this.$element.classList.add('-is-visible');
    
    		// Focus first focusable element for accessibility
    		this.firstFocusableElement?.focus();
    	}
    
    	close() {
    		this.isVisible = false;
    
    		this.$element.classList.remove('-is-visible');
    
    		// Remove hash from url
    		window.history.replaceState({}, '', window.location.pathname);
    	}
    
    	handleKeyDown(event: KeyboardEvent) {
    		const { key } = event;
    		const focusedElement = document.activeElement as HTMLElement;
    
    		if (!this.isVisible || !this.$element.contains(focusedElement)) return;
    
    		switch (key) {
    			case 'Escape':
    				event.preventDefault();
    				this.close();
    				break;
    			case 'Tab':
    				if (event.shiftKey) {
    					// Shift + Tab (backwards)
    					if (focusedElement === this.firstFocusableElement) {
    						event.preventDefault();
    						this.lastFocusableElement?.focus();
    					}
    				} else {
    					// Tab (forwards)
    					if (focusedElement === this.lastFocusableElement) {
    						event.preventDefault();
    						this.firstFocusableElement?.focus();
    					}
    				}
    				break;
    		}
    	}
    }
    
  • URL: /components/raw/country-picker/index.ts
  • Filesystem Path: src/components/molecules/country-picker/index.ts
  • Size: 3.3 KB
  • Handle: @country-picker
  • Preview:
  • Filesystem Path: src/components/molecules/country-picker/country-picker.twig