Visit Reservation Widget

Integrate a beautiful visit reservation booking widget into your website with just a few lines of code.

Integration Guide

Table of Contents

Quick Start

Add the visit reservation widget to your page in 3 simple steps:

Step 1: Include Required Files

<!-- Bootstrap CSS (optional - provides a good base for styling, required when using our pre-built themes) -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.8/dist/css/bootstrap.min.css"
      rel="stylesheet"
      integrity="sha384-sRIl4kxILFvY47J16cr9ZwB07vP4J8+LH7qKQnuqkuIAvNWLzeN8tE5YBujZqJLB"
      crossorigin="anonymous">

<!-- Widget CSS (required) -->
<link href="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.css" rel="stylesheet">

<!-- Widget Script (place before closing </body>) -->
<script src="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.js"></script>

Step 2: Add the Widget Element

<realsuite-visitreservation-widget
    apikey="YOUR_API_KEY"
    guid="YOUR_PUBLICATION_GUID">
</realsuite-visitreservation-widget>

Step 3: (Optional) Customize the Theme

<style>
  :root {
    --rs-primary: #72A98F;  /* Your brand color */
  }
</style>

Step 4: Bringing It All Together

Here's a complete working example you can copy and use as a starting point:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>Book a Visit</title>

  <!-- Bootstrap CSS (optional - provides a good base for styling, required when using our pre-built themes) -->
  <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.8/dist/css/bootstrap.min.css"
        rel="stylesheet"
        integrity="sha384-sRIl4kxILFvY47J16cr9ZwB07vP4J8+LH7qKQnuqkuIAvNWLzeN8tE5YBujZqJLB"
        crossorigin="anonymous">

  <!-- Widget CSS (required) -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.css" rel="stylesheet">

  <!-- Optional: Use one of our pre-built themes (requires Bootstrap CSS) -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/styles/theme-brand.css"
        rel="stylesheet">

  <!-- Optional: Custom brand color -->
  <style>
    :root {
      --rs-primary: #72A98F;  /* Your brand color */
    }
  </style>
</head>
<body>

  <!-- The Widget -->
  <realsuite-visitreservation-widget
      apikey="YOUR_API_KEY"
      guid="YOUR_PUBLICATION_GUID">
  </realsuite-visitreservation-widget>

  <!-- Widget Script (required) -->
  <script src="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.js"></script>

</body>
</html>
Tip: That's it! The widget will automatically load available visit moments for the specified property.

Prerequisites

Dependencies

Dependency Version Required Purpose
Bootstrap CSS 5.3.x Optional Provides a good base for styling (cards, buttons, forms, grid layout). Required when using our pre-built themes.
Note: Bootstrap CSS is optional but highly recommended as it provides a solid foundation for styling. If you plan to use any of our pre-built themes, Bootstrap CSS is required. If you're already using Bootstrap on your site, you don't need to include it again.

Widget Attributes

Configure the widget using HTML attributes on the <realsuite-visitreservation-widget> element:

Attribute Type Required Description
apikey string Required Your RealSuite API key for authentication. Contact your RealSuite representative to obtain this.
guid string Required The unique identifier (GUID) of the estate/property for which to show visit reservations.
languageId string Optional Language code for translations. Default: "nl-be". Supported: "nl-be", "fr-be", "en"
translationsuri string Optional URL to a JSON file containing custom translation overrides (see Translations)

Example with All Attributes

<realsuite-visitreservation-widget
    apikey="your-api-key-here"
    guid="43aaef38-816b-43ed-83c6-35d027a1c325"
    languageId="nl-be"
    translationsuri="/my-translations.json">
</realsuite-visitreservation-widget>

Events

The widget emits custom DOM events that you can listen to for handling user interactions.

Available Events

Event Name Description When Fired
bookingCompleted Emitted when the user clicks the "Close" button on the booking success screen After a successful booking, when the user clicks the action button

Listening to Events

Use addEventListener to listen for widget events. This is useful for navigating to another page, closing a modal, or performing any custom action after the booking is completed.

Step 1: Enable the Close Button

The "Close" button is hidden by default. To show it, add the following CSS to your page:

<style>
  .btn-completed {
    visibility: visible !important;
  }
</style>

Step 2: Attach the Event Listener

<realsuite-visitreservation-widget
    apikey="your-api-key"
    guid="your-estate-guid">
</realsuite-visitreservation-widget>

<script>
  // Get reference to the widget
  const widget = document.querySelector('realsuite-visitreservation-widget');

  // Listen for the bookingCompleted event
  widget.addEventListener('bookingCompleted', function(event) {
    console.log('Booking completed!');

    // Example: Navigate to a thank you page
    window.location.href = '/thank-you';

    // Or: Close a modal dialog
    // myModal.close();

    // Or: Show a custom notification
    // showNotification('Your booking has been confirmed!');
  });
</script>

The Action Button

After a successful booking, a "Close" button can be shown on the success screen. The button is hidden by default via CSS. When you want users to be able to close/navigate away, you need to:

  1. Enable the button with CSS: .btn-completed { visibility: visible !important; }
  2. Attach an event listener to handle the bookingCompleted event
Tip: If you're dynamically creating the widget (e.g., reinitializing it), make sure to re-attach the event listener to the new widget instance.

Dynamic Widget Creation Example

When creating the widget dynamically via JavaScript, attach the event listener before or immediately after inserting the widget:

<script>
  function createWidget(apiKey, guid) {
    // Remove existing widget if any
    const existing = document.querySelector('realsuite-visitreservation-widget');
    if (existing) existing.remove();

    // Create new widget
    const widget = document.createElement('realsuite-visitreservation-widget');
    widget.setAttribute('apikey', apiKey);
    widget.setAttribute('guid', guid);

    // Attach event listener BEFORE or AFTER inserting into DOM
    widget.addEventListener('bookingCompleted', function() {
      console.log('Booking completed!');
      window.location.href = '/thank-you';
    });

    // Insert widget into page
    document.getElementById('widget-container').appendChild(widget);
  }
</script>

Usage in a Modal Dialog

A common use case is embedding the widget in a modal and closing it when the booking is complete:

<!-- Enable the close button -->
<style>
  .btn-completed { visibility: visible !important; }
</style>

<!-- Bootstrap Modal Example -->
<div class="modal" id="bookingModal">
  <div class="modal-dialog modal-lg">
    <div class="modal-content">
      <div class="modal-header">
        <h5 class="modal-title">Book a Visit</h5>
        <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
      </div>
      <div class="modal-body">
        <realsuite-visitreservation-widget
          apikey="your-api-key"
          guid="your-estate-guid">
        </realsuite-visitreservation-widget>
      </div>
    </div>
  </div>
</div>

<script>
  const modal = new bootstrap.Modal(document.getElementById('bookingModal'));
  const widget = document.querySelector('realsuite-visitreservation-widget');

  widget.addEventListener('bookingCompleted', function() {
    // Close the modal when booking is done
    modal.hide();
  });
</script>

Theming & Customization

The widget uses CSS custom properties (variables) for easy theming. Simply override the variables in your CSS to match your brand.

Quick Brand Color Override

The fastest way to customize the widget is to override the primary color:

<style>
  :root {
    --rs-primary: #e13d3f;  /* Your brand color */

    /* Auto-generated variants (optional - will be calculated if not set) */
    --rs-primary-dark: color-mix(in srgb, var(--rs-primary) 80%, black);
    --rs-primary-light: color-mix(in srgb, var(--rs-primary) 60%, white);
  }
</style>
Tip: The color-mix() function automatically creates dark and light variants of your primary color!

CSS Variables Reference

Here are all available CSS variables you can customize:

Core Colors

Variable Default Description
--rs-primary #72A98F Primary brand color - used for buttons, links, active states
--rs-primary-dark #5A8A73 Darker shade for hover states
--rs-primary-light #A3C9B7 Lighter shade for backgrounds and highlights

Background & Surface Colors

Variable Default Description
--rs-background #FAFAFA Main background color of the widget
--rs-surface #F8F9FA Secondary surface color (card headers, etc.)
--rs-card-bg #FFFFFF Background color for cards
--rs-border #E8E8E8 Border color for cards and dividers

Text Colors

Variable Default Description
--rs-text #2D3436 Primary text color
--rs-text-muted #636E72 Secondary/muted text color

Error Colors

Variable Default Description
--rs-error-bg #dc354530 Background color for error messages
--rs-error-text #dc3545 Text color for error messages

Complete Variables Block

:root {
  /* Primary Colors */
  --rs-primary: #72A98F;
  --rs-primary-dark: #5A8A73;
  --rs-primary-light: #A3C9B7;

  /* Backgrounds */
  --rs-background: #FAFAFA;
  --rs-surface: #F8F9FA;
  --rs-card-bg: #FFFFFF;
  --rs-border: #E8E8E8;

  /* Text */
  --rs-text: #2D3436;
  --rs-text-muted: #636E72;

  /* Errors */
  --rs-error-bg: #dc354530;
  --rs-error-text: #dc3545;
}

Pre-built Themes

We provide several pre-built themes you can use as-is or as a starting point for customization.

Important: When using our pre-built themes, Bootstrap CSS is required as the themes build upon Bootstrap's styling foundation.

Available Themes

Theme Description Best For
theme-brand.css Clean, minimal Scandinavian design with sage green Modern real estate agencies
theme-steps.css Wizard-style with prominent step indicators (beads) Multi-step booking experiences
override-008.css Luxury dark mode with gold accents Premium/luxury properties
override-009.css Corporate professional with blue tones Business/corporate properties

Using a Pre-built Theme

<!-- Include the theme CSS after Bootstrap -->
<link href="https://elements.realsuite.be/visitreservation-widget/beta/styles/theme-brand.css" rel="stylesheet">

Combining Theme with Custom Primary Color

<!-- Use a theme but override the primary color -->
<link href="https://elements.realsuite.be/visitreservation-widget/beta/styles/theme-steps.css" rel="stylesheet">
<style>
  :root {
    --rs-primary: #8cc63f;  /* Your custom color */
  }
</style>

Custom Translations

Override default widget text using a JSON translations file:

Step 1: Create a translations.json file

{
  "widget-title": "Book a visit to our property",
  "button-next": "Continue",
  "button-previous": "Go Back",
  "button-submit": "Confirm Reservation",
  "step-1-title": "Select a Date",
  "step-1-description": "Choose your preferred visit day",
  "step-2-title": "Select a Time",
  "step-2-description": "Pick an available time slot",
  "step-3-title": "Your Information",
  "step-3-description": "Please fill in your contact details",
  "booking-confirmed-title": "Booking Confirmed!",
  "booking-confirmed-message": "You will receive a confirmation email shortly.",
  "available-spots": "available spots",
  "no-spots-available": "Fully booked",
  "form-name": "First Name",
  "form-lastname": "Last Name",
  "form-email": "Email",
  "form-phone": "Phone",
  "form-message": "Additional Message"
}

Step 2: Reference it in the widget

<realsuite-visitreservation-widget
    apikey="your-api-key"
    guid="your-guid"
    translationsuri="/path/to/translations.json">
</realsuite-visitreservation-widget>
Tip: You only need to include the keys you want to override. Missing keys will fall back to the default translations.

Advanced CSS Customization

Styling the Widget Container

/* Set max-width and center the widget */
realsuite-visitreservation-widget {
  max-width: 1000px;
  display: block;
  margin: 0 auto;
  background-color: var(--rs-background);
  border-radius: 24px;
  padding: 40px;
  box-shadow: 0 4px 24px rgba(0, 0, 0, 0.04);
}

Hiding Completed/Fully Booked Slots

/* Hide time slots that are fully booked */
rs-time-slot.complete {
  display: none;
}

/* Hide date slots that are fully booked */
rs-date-slot.complete {
  display: none;
}

/* Or just visually dim them */
rs-time-slot.complete,
rs-date-slot.complete {
  opacity: 0.5;
  pointer-events: none;
}

Customizing Buttons

/* Override Bootstrap button styling */
.btn-primary {
  --bs-btn-bg: var(--rs-primary);
  --bs-btn-border-color: var(--rs-primary);
  --bs-btn-hover-bg: var(--rs-primary-dark);
  --bs-btn-hover-border-color: var(--rs-primary-dark);
  --bs-btn-disabled-bg: #E8E8E8;
  --bs-btn-disabled-border-color: #E8E8E8;
  --bs-btn-disabled-color: #B2BEC3;

  border-radius: 50px;           /* Pill-shaped buttons */
  padding: 12px 24px;
  font-weight: 500;
  text-transform: uppercase;
  letter-spacing: 1px;
  font-size: 0.75rem;
}

Customizing Form Fields

/* Style form labels */
rs-form-field .form-label,
rs-form-text-area .form-label {
  font-size: 0.8rem;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 1px;
  color: var(--rs-text-muted);
}

/* Style form inputs */
rs-form-field .form-control,
rs-form-text-area .form-control {
  border: 2px solid var(--rs-border);
  border-radius: 12px;
  padding: 14px 16px;
  font-size: 1rem;
  transition: all 0.2s ease;
}

/* Focus state */
rs-form-field .form-control:focus,
rs-form-text-area .form-control:focus {
  border-color: var(--rs-primary);
  box-shadow: 0 0 0 4px rgba(114, 169, 143, 0.15);
  outline: none;
}

Customizing Cards (Date/Time Slots)

/* Date slot cards */
rs-date-slot .card {
  border: none;
  border-radius: 16px;
  overflow: hidden;
  background: var(--rs-card-bg);
  box-shadow: 0 2px 12px rgba(0, 0, 0, 0.04);
  transition: all 0.3s ease;
}

/* Hover effect */
rs-date-slot .card:hover {
  transform: translateY(-4px);
  box-shadow: 0 8px 24px rgba(114, 169, 143, 0.15);
}

/* Selected state */
rs-date-slot.selected .card {
  border: 2px solid var(--rs-primary) !important;
}

Component CSS Selectors

Use these selectors to target specific parts of the widget:

Main Components

Selector Description
realsuite-visitreservation-widget The main widget container
rs-visit-reservation-wizard The wizard component that handles the step flow
rs-steps The step indicator/pagination component
rs-visit-moments-list Container for date or time slot listings
rs-date-slot Individual date slot card
rs-time-slot Individual time slot card
rs-contact-data Contact form container
rs-form-field Individual form input field
rs-form-text-area Textarea form field
rs-error-message Error message component

Wizard Structure

Selector Description
.wizard-header Header area containing title, description, and steps
.wizard-title Container for step title and description
.step-title The current step's title
.step-description The current step's description text
.wizard-content Main content area for the current step
.wizard-footer Footer with navigation buttons
.wizard-content.booking-completed Success state after booking is complete

State Classes

Class Applied To Description
.selected rs-date-slot, rs-time-slot Currently selected slot
.complete rs-date-slot, rs-time-slot, rs-visit-moments-list Fully booked / no spots available
.active .page-item in steps Current active step
.disabled .page-item, a.icon-link Disabled/unavailable state
.invalid .form-label Form validation error state

Full Examples

Example 1: Basic Integration

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>Property Visit Booking</title>

  <!-- Bootstrap CSS (optional - provides good base styling) -->
  <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.8/dist/css/bootstrap.min.css"
        rel="stylesheet">

  <!-- Widget CSS (required) -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.css" rel="stylesheet">
</head>
<body>

  <realsuite-visitreservation-widget
      apikey="your-api-key"
      guid="your-publication-guid">
  </realsuite-visitreservation-widget>

  <!-- Widget Script -->
  <script src="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.js"></script>

</body>
</html>

Example 2: Branded with Custom Colors

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>Property Visit Booking</title>

  <!-- Bootstrap CSS (optional - provides good base styling) -->
  <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.8/dist/css/bootstrap.min.css"
        rel="stylesheet">

  <!-- Widget CSS (required) -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.css" rel="stylesheet">

  <!-- Your brand colors -->
  <style>
    :root {
      --rs-primary: #e13d3f;
      --rs-primary-dark: #c12b2d;
      --rs-primary-light: #f47173;
    }

    body {
      background: #f5f5f5;
      padding: 40px 20px;
    }

    realsuite-visitreservation-widget {
      max-width: 800px;
      margin: 0 auto;
      background: white;
      border-radius: 16px;
      padding: 32px;
      box-shadow: 0 10px 40px rgba(0,0,0,0.1);
    }
  </style>
</head>
<body>

  <realsuite-visitreservation-widget
      apikey="your-api-key"
      guid="your-publication-guid"
      languageId="en"
      translationsuri="/translations.json">
  </realsuite-visitreservation-widget>

  <script src="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.js"></script>

</body>
</html>

Example 3: Using Pre-built Theme with Customizations

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>Property Visit Booking</title>

  <!-- Bootstrap CSS (required when using pre-built themes) -->
  <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.8/dist/css/bootstrap.min.css"
        rel="stylesheet">

  <!-- Widget CSS (required) -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.css" rel="stylesheet">

  <!-- Pre-built theme -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/styles/theme-steps.css" rel="stylesheet">

  <!-- Custom overrides -->
  <style>
    :root {
      --rs-primary: #8cc63f;
    }

    /* Hide fully booked slots */
    rs-time-slot.complete,
    rs-date-slot.complete {
      display: none;
    }

    /* Make buttons more rounded */
    .btn-primary {
      border-radius: 50px;
    }
  </style>
</head>
<body>

  <realsuite-visitreservation-widget
      apikey="your-api-key"
      guid="your-publication-guid"
      languageId="nl-be">
  </realsuite-visitreservation-widget>

  <script src="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.js"></script>

</body>
</html>

Example 4: Dark Theme for Luxury Properties

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>Luxury Property Tour</title>

  <!-- Bootstrap CSS (optional - provides good base styling) -->
  <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.8/dist/css/bootstrap.min.css"
        rel="stylesheet">

  <!-- Widget CSS (required) -->
  <link href="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.css" rel="stylesheet">

  <style>
    :root {
      --rs-primary: #D4AF37;
      --rs-background: #1A1A2E;
      --rs-surface: #16213E;
      --rs-card-bg: #0F0F1A;
      --rs-border: #2A2A4A;
      --rs-text: #FFFFFF;
      --rs-text-muted: #8B8BA3;
    }

    body {
      background: linear-gradient(180deg, #0D0D1A 0%, #1A1A2E 100%);
      min-height: 100vh;
      padding: 40px 20px;
    }

    realsuite-visitreservation-widget {
      max-width: 900px;
      margin: 0 auto;
      background: var(--rs-surface);
      border-radius: 20px;
      padding: 48px;
      border: 1px solid var(--rs-border);
      box-shadow: 0 25px 50px rgba(0, 0, 0, 0.5);
    }

    /* Gold gradient for buttons */
    .btn-primary {
      background: linear-gradient(135deg, #D4AF37 0%, #F4D03F 50%, #D4AF37 100%);
      border: none;
      color: #0F0F1A;
    }
  </style>
</head>
<body>

  <realsuite-visitreservation-widget
      apikey="your-api-key"
      guid="your-publication-guid"
      languageId="en">
  </realsuite-visitreservation-widget>

  <script src="https://elements.realsuite.be/visitreservation-widget/beta/realsuite-visitreservation-widget.js"></script>

</body>
</html>