Embed widget

Microsoft Bookings, on your own website

Paste your public Bookings page link and get a booking widget that matches your site. No Microsoft sign-in, no admin consent. Bookings still land in Outlook and Teams, and Microsoft still sends the invites.

The real widget, running against a demo business. Try a booking; nothing is sent to anyone.

How it works

Three steps, none of them in Microsoft 365 admin

BookingsXP reads the same public booking page your customers already use. Your services, staff, hours and booking rules stay in Microsoft Bookings, and so do the bookings.
  1. 01

    Paste your Bookings page link

    Copy the public link from the Bookings app; it usually starts with outlook.office.com/book/. BookingsXP loads your services, staff and open times from it.

  2. 02

    Pick a template and your colours

    Seven layouts for contact pages, sidebars, landing pages and full-width sections. Set the accent colour and light or dark mode; Pro adds fonts, radius, density and more.

  3. 03

    Paste one snippet on your site

    A script tag and one element, a plugin, or a package for your framework. Visitors book without leaving your page; Microsoft Bookings creates the appointment and sends the confirmation.

Templates

Seven layouts, three of them free

Each template is the same booking flow in a different shape. Switch at any time from the dashboard; the snippet on your site does not change. See every template
BookingsXP widget templates, what each is for and which plan includes it
TemplateWhat it looks likeBest forPlan
ClassicMonth calendar beside the day's times — the layout visitors already know.Contact and booking pagesFree
CompactA scrolling day strip over a grid of times, built for sidebars and phones.Sidebars, landing pages, mobile-heavy trafficFree
Next availableThe soonest open times as one list — one tap to pick, nothing to browse.Sales calls and quick consultationsFree
SplitYour business and service details on the left, the calendar on the right.Hosted booking pages and full-width sectionsPro
Week viewSeven days side by side so visitors compare times at a glance.Clinics, salons and advisers with busy calendarsPro
GuidedOne question per step — service, person, day, time, details — with progress.Many services or staff; highest completion on mobilePro
Service cardsServices as rich cards with duration and price, then a clean time picker.Menus of services with pricesPro

Embed options

One script, then whatever your site speaks

Every option renders the same widget and sends the same tracking events. The dashboard's Install tab fills in your widget ID for you. Full reference in the docs.

HTML

Include the script once per page, then place the element where the widget should appear. Works in any HTML block: Webflow, Squarespace, Wix, Framer and HubSpot included.

Inline

The widget sits in the page and grows to fit its content.

HTML
<script src="https://bookingsxp.com/embed/v1.js" async></script>
<bookingsxp-widget widget="w_8fk2m1qz"></bookingsxp-widget>

Popup button

A button that opens the widget in a dialog. Esc or the close button dismisses it.

HTML
<script src="https://bookingsxp.com/embed/v1.js" async></script>
<bookingsxp-widget widget="w_8fk2m1qz" mode="popup"
  button-text="Book a call" accent="#0f766e"></bookingsxp-widget>

Floating button

A button fixed to the bottom-right corner on every page that includes it.

HTML
<script src="https://bookingsxp.com/embed/v1.js" async></script>
<bookingsxp-widget widget="w_8fk2m1qz" mode="floating"
  button-text="Book now" accent="#0f766e"></bookingsxp-widget>

Plain iframe

No JavaScript at all. The widget works, but host-page events and attribution are not available.

HTML
<iframe src="https://bookingsxp.com/embed/w_8fk2m1qz" title="Book an appointment" loading="lazy"
  style="width:100%;min-height:720px;border:0"></iframe>

Div form

For site builders that strip unknown tags.

HTML
<script src="https://bookingsxp.com/embed/v1.js" async></script>
<div data-bookingsxp data-widget="w_8fk2m1qz"></div>

Link only, no account

Use your Bookings link directly, no account. Free templates with the badge, and dataLayer events only: no dashboard analytics, GA4 or ad conversions.

HTML
<script src="https://bookingsxp.com/embed/v1.js" async></script>
<bookingsxp-widget
  booking-url="https://outlook.office.com/book/Contoso@contoso.com/"
  template="classic" accent="#0f766e"></bookingsxp-widget>

Frameworks

Thin, typed wrappers that load the script once and render the element. Safe with server rendering and hydration.

React

TSX
// @bookingsxp/react (npm release pending — the script embed works in every framework today)
import { BookingsXPWidget } from "@bookingsxp/react";

export function Booking() {
  return (
    <BookingsXPWidget
      widget="w_8fk2m1qz"
      onBooked={(e) => console.log("booked", e.booking?.id)}
    />
  );
}

Next.js

TSX
// app/book/page.tsx — @bookingsxp/react (npm release pending — the script embed works in every framework today)
"use client";
import { BookingsXPWidget } from "@bookingsxp/react";

export default function BookPage() {
  return <BookingsXPWidget widget="w_8fk2m1qz" redirectUrl="/thank-you" />;
}

Vue 3

Vue
<!-- @bookingsxp/vue (npm release pending — the script embed works in every framework today) -->
<script setup>
import { BookingsXPWidget } from "@bookingsxp/vue";
const onBooked = (e) => console.log("booked", e.booking?.id);
</script>

<template>
  <BookingsXPWidget widget="w_8fk2m1qz" @booked="onBooked" />
</template>

Svelte 5

Svelte
<!-- @bookingsxp/svelte (npm release pending — the script embed works in every framework today) -->
<script>
  import BookingsXPWidget from "@bookingsxp/svelte";
</script>

<BookingsXPWidget widget="w_8fk2m1qz" onbooked={(e) => console.log(e.booking?.id)} />

Astro

Server-rendered, ships no framework runtime.

Astro
---
// @bookingsxp/astro (npm release pending — the script embed works in every framework today)
import BookingsXPWidget from "@bookingsxp/astro/BookingsXPWidget.astro";
---
<BookingsXPWidget widget="w_8fk2m1qz" />

WordPress

Install the plugin, then use the shortcode or the BookingsXP block in the editor. A settings page stores a default widget ID. Download the plugin (.zip)

Shortcode

Text
[bookingsxp widget="w_8fk2m1qz"]

<!-- Or link-only, no account -->
[bookingsxp url="https://outlook.office.com/book/Contoso@contoso.com/"]

<!-- Popup button -->
[bookingsxp widget="w_8fk2m1qz" mode="popup" button_text="Book a call" accent="#0f766e"]

Hosted booking page

Every saved widget also has its own page at bookingsxp.com/book/<widgetId> for email signatures, social bios and ads that need a link rather than an embed. Same template and colours, and it counts in your analytics.

Prefill

Skip the typing for people you already know

Microsoft's booking page cannot be prefilled; a Microsoft Q&A question asking for it has more than 90 “I have the same question” votes. The widget accepts name, email, phone and notes from attributes, the JavaScript API or the hosted page URL, and can open straight on one service.

Attributes

For logged-in areas and personalised landing pages.

HTML
<bookingsxp-widget widget="w_8fk2m1qz"
  name="Alex Rivera" email="alex.rivera@example.com"
  phone="+1 555 0142" notes="Referred by Dr. Chen"
  service="YOUR_SERVICE_ID"></bookingsxp-widget>

JavaScript API

After a form on your page, or from your own data.

HTML
<script>
  window.BookingsXP = window.BookingsXP || { q: [] };
  BookingsXP.q.push(["render", "#booking", {
    widget: "w_8fk2m1qz",
    prefill: { name: "Alex Rivera", email: "alex.rivera@example.com" },
  }]);
</script>
<div id="booking"></div>

Hosted page URL

For links in emails and CRM sequences.

Text
https://bookingsxp.com/book/w_8fk2m1qz?name=Alex%20Rivera&email=alex.rivera%40example.com

The loader hands prefill values to the widget inside the page. They are never added to the widget's iframe URL, so they do not end up in server logs or analytics tools.

Theming

Match your site, not ours

Free covers the essentials: the accent colour your buttons use and light or dark mode. Pro opens the rest of the design settings and removes the badge.
Widget styling on the Free and Pro plans
SettingFreePro and Business
TemplatesClassic, Compact, Next availableAll 7
Accent colourIncludedIncluded
Light, dark or match the visitorIncludedIncluded
Business header and logoIncludedIncluded
Font (System, Geist, Serif, Rounded, Mono)Not includedIncluded
Corner radiusNot includedIncluded
Density (comfortable or compact)Not includedIncluded
Button style (solid, soft, outline)Not includedIncluded
Background colour or transparent backgroundNot includedIncluded
“Powered by BookingsXP” badgeShownRemoved

Accessibility and performance

The details that decide whether people finish

Visitor time zone
Times always open in the visitor's own time zone. You can let visitors switch zone, and choose a 12 or 24 hour clock and the first day of the week.
Auto-resize
The widget reports its height to the page on every step, so there is no inner scrollbar and no fixed height to guess.
Lazy loading
Inline widgets load when they come near the viewport. The loader is about 8 KB gzipped and loads with async.
Keyboard and screen readers
The calendar is a labelled grid you move through with the arrow keys; month changes and the confirmation are announced; focus is visible throughout.
Reduced motion
Transitions are switched off when the visitor's system asks for reduced motion.
Mobile first
Every template adapts below its ideal width. Compact and Next available are built for sidebars and phones.
Safe to embed
The widget runs in its own iframe and talks to your page only through messages checked against both origins. You can restrict each widget to your own domains.

Want the tracking side too? Tracking and analytics

FAQ

Questions about the widget

Your calendar, on your site

Start with one widget on the Free plan. Keep Microsoft Bookings exactly as it is.