Shepherd - Documentation

What is Shepherd?

Shepherd is a JavaScript library for creating interactive, guided tours and onboarding experiences for your web applications. It allows you to easily highlight specific elements on your page and provide context-sensitive instructions to guide users through your application’s features. Shepherd offers a simple, yet powerful API for creating tours with various customization options, enabling developers to build engaging and effective onboarding flows. It’s designed to be lightweight and unobtrusive, seamlessly integrating into existing projects without impacting performance.

Key Features and Benefits

Getting Started: Installation and Setup

Shepherd can be installed via npm or yarn:

npm install shepherd.js
# or
yarn add shepherd.js

Once installed, include Shepherd in your project:

import Shepherd from 'shepherd.js';

// or if using a bundler like webpack, you can import it directly
// import Shepherd from 'shepherd.js';

const tour = new Shepherd.Tour({
  defaults: {
    classes: 'shepherd-theme-arrows', // Add a theme to your tours
  },
});

// Add steps here (see Example Use Cases below)

tour.start();

Include the necessary CSS. You can either include a pre-built theme, or create your own. Many themes are available on the Shepherd.js website. For example, to use the default theme:

<link rel="stylesheet" href="path/to/shepherd.css" />

Replace "path/to/shepherd.css" with the actual path to your CSS file.

Example Use Cases

Here are a few examples to demonstrate Shepherd’s usage:

Basic Tour:

const tour = new Shepherd.Tour({
  defaultStepOptions: {
    cancelIcon: {
      enabled: true
    }
  }
});

tour.addStep({
  id: 'welcome',
  text: 'Welcome to our app!',
  attachTo: { element: '.welcome-message', on: 'bottom' },
});

tour.addStep({
  id: 'button',
  text: 'Click this button to continue!',
  attachTo: { element: '#next-button', on: 'bottom' },
});

tour.start();

Tour with Custom Classes and Elements:

const tour = new Shepherd.Tour();

tour.addStep({
  id: 'custom-step',
  text: 'This step has a custom class!',
  attachTo: { element: '#myElement', on: 'bottom' },
  classes: 'my-custom-class', // Add custom CSS class
  buttons: [
    {
        text: 'Next',
        action: tour.next
    }
  ]
});

tour.start();

Remember to replace placeholders like .welcome-message and #next-button with actual selectors for your elements. Refer to the Shepherd.js documentation for more advanced features and customization options.

Core Concepts

Tours and Steps

Shepherd organizes guided tours using two core concepts: Tours and Steps.

The relationship is hierarchical: a tour contains multiple steps, which are sequentially presented to the user during the tour. Navigation between steps is usually handled automatically by Shepherd, though custom button actions allow developers full control over tour flow.

Shepherd Elements and Components

Shepherd generates several HTML elements and components as part of its tours. Understanding these components is essential for customization and styling. Key elements include:

Shepherd Configuration Options

Shepherd offers various configuration options to customize the tour’s behavior and appearance. These options can be set at the tour level (affecting all steps) or at the individual step level. Key configuration options include:

You can customize individual steps using options such as text, attachTo, buttons, classes, beforeShowPromise, afterShowPromise, beforeHidePromise, and afterHidePromise allowing granular control over specific steps’ appearance and behaviour. These properties are documented fully in the Shepherd.js API Reference.

Creating Custom Shepherd Elements

Shepherd allows for extensive customization, and you can create your own custom elements to extend its functionality. To create custom elements, you would typically create a new step type that utilizes a custom template and overrides default step rendering. This involves creating a new component that extends Shepherd’s base Step class, defining its template (HTML structure), and potentially defining custom methods for behavior. This requires a deeper understanding of Shepherd’s internal structure and potentially its use of React or a similar framework, depending on the chosen approach. The Shepherd documentation should provide examples and best practices for extending Shepherd with custom elements. This is an advanced topic, and creating custom elements often requires familiarity with JavaScript frameworks and template engines.

Building Tours

Defining Tour Steps

Defining tour steps involves creating step objects and adding them to the tour instance. Each step object requires an id (a unique identifier), and typically includes text (the content displayed in the step), and attachTo (specifying the target element and its relative position). Here’s an example:

const tour = new Shepherd.Tour();

tour.addStep({
  id: 'welcome-step',
  text: 'Welcome to our application!',
  attachTo: { element: '#welcome-message', on: 'bottom' },
});

tour.addStep({
  id: 'search-step',
  text: 'Use the search bar to find what you need.',
  attachTo: { element: '#search-bar', on: 'top' },
});

tour.start();

The attachTo property is crucial. element is a CSS selector for the target element, and on specifies the position relative to the element (top, bottom, left, right). Additional options within attachTo offer finer control over positioning (see Step Positioning and Alignment). Remember to replace '#welcome-message' and '#search-bar' with the actual selectors for your elements.

Step Positioning and Alignment

Precise positioning is vital for a user-friendly tour. The attachTo property’s on option determines initial placement, but Shepherd provides more control:

Example with offset:

tour.addStep({
  id: 'offset-step',
  text: 'This step is offset 20px to the right and 10px down.',
  attachTo: { element: '#my-element', on: 'bottom', offset: { left: 20, top: 10 } },
});

Experiment with on and offset to find the best placement for each step within your application’s layout. The boundary option is particularly useful for handling steps near the edges of the viewport.

Step Content and Customization

Step content goes beyond simple text. You can include:

Example with title and classes:

tour.addStep({
  id: 'styled-step',
  title: 'Important Information',
  text: 'This step uses custom styling.',
  classes: 'my-custom-step-class',
  attachTo: { element: '#important-info', on: 'top' },
});

Remember to define the CSS for .my-custom-step-class in your stylesheet to apply custom styling. Using a template allows for the most control, creating entirely custom step layouts.

Adding Buttons and Actions

Shepherd’s default buttons (“Next,” “Back,” “Cancel”) are customizable, and you can add your own. The buttons array in a step’s options allows you to define custom buttons and actions:

tour.addStep({
  id: 'custom-buttons',
  text: 'This step has custom buttons!',
  buttons: [
    {
      text: 'Continue',
      action: tour.next,
    },
    {
      text: 'Skip this step',
      action: tour.show, // Or any custom function
    },
  ],
  attachTo: { element: '#custom-buttons-area', on: 'bottom' },
});

action can be any function. Shepherd provides tour.next, tour.back, tour.cancel, and tour.show to control tour navigation. You can also define your own custom functions to perform actions on button clicks.

Advanced Step Options (e.g., scroll behavior)

Shepherd offers several advanced options for fine-grained control:

Example using beforeShowPromise:

tour.addStep({
  id: 'async-step',
  text: 'This step loads data asynchronously.',
  beforeShowPromise: () => {
    return fetch('/my-data').then(response => response.json()); // Simulates async data loading
  },
  attachTo: { element: '#async-data', on: 'bottom' },
});

These advanced options provide fine-grained control over the tour’s behavior and integrate seamlessly with asynchronous operations, creating truly dynamic and engaging guided experiences.

Tour Navigation and Control

Back and Next Buttons

Shepherd provides built-in “Back” and “Next” buttons for standard sequential tour navigation. These buttons are automatically included in each step unless explicitly overridden using the buttons option. The “Next” button advances the tour to the next step, while the “Back” button navigates to the previous step. The behavior of these buttons is managed internally by Shepherd. If you remove the default buttons via the buttons array you will need to provide your own custom buttons that call the tour.next() and tour.back() methods.

Canceling a Tour

Users can cancel a Shepherd tour using the default “Cancel” button (if enabled via configuration options) or by pressing the Escape key (if exitOnEsc is enabled). Programmatically, you can cancel a tour using the tour.cancel() method. This abruptly ends the tour, closing all open steps.

To enable the cancel button you should set showCancelLink to true in the Shepherd.Tour options:

const tour = new Shepherd.Tour({
  showCancelLink: true
});

Conditional Logic and Routing

Shepherd doesn’t directly support conditional branching within a tour based on user actions or data. However, you can achieve conditional routing using custom logic and the when option in steps, combined with the tour.show() method to control which step is displayed next.

The when property accepts a function. If the function returns false, the step is skipped. This allows you to conditionally show or hide steps based on conditions checked in your function:

const tour = new Shepherd.Tour();

tour.addStep({
  id: 'step1',
  when: () => someConditionIsTrue(), //Your conditional logic here
  // ...
});

tour.addStep({
  id: 'step2',
  // ...
});

// Example of a function to conditionally show a step
function someConditionIsTrue() {
  return localStorage.getItem('hasVisitedBefore') === null;
}
tour.start();

The tour.show(stepId) method allows you to explicitly navigate to a specific step, bypassing the default sequential flow. This enables creating complex tour flows based on user interactions or dynamic data.

Custom Navigation Controls

You can replace or supplement the default Shepherd navigation buttons with your own custom buttons. This gives complete control over the user interface and the tour’s flow. You do this by defining custom buttons within the buttons array of a step’s options, as shown previously. The actions of your custom buttons will call tour.next(), tour.back(), tour.cancel(), or tour.show(stepId).

Handling User Interactions

Shepherd itself doesn’t directly handle user interactions beyond button clicks. You’ll typically use standard JavaScript event listeners (e.g., click, mouseover) on your application’s elements to trigger actions within your Shepherd tour. These actions might involve:

By combining event listeners and Shepherd’s API methods, you create interactive tours that respond to user behavior and dynamic application state. Remember to ensure appropriate error handling and updates of the tour’s internal state to avoid unexpected behavior.

Styling and Theming

Default Styling

Shepherd comes with a default CSS stylesheet that provides a basic, functional appearance for your tours. This default styling ensures a consistent look and feel across different browsers and devices. However, the default styles are designed to be easily overridden or extended with your own custom styles. The default styles prioritize readability and accessibility. You’ll likely want to customize the appearance to match your application’s branding.

Custom CSS and Styling

You can customize Shepherd’s appearance using custom CSS. You can add custom CSS classes to the tour container and individual steps using the classes option. This allows you to target specific elements within Shepherd’s generated markup and apply your own styling rules.

Remember that Shepherd generates its own HTML structure. Inspect the generated HTML in your browser’s developer tools to identify the appropriate classes and elements to target with your custom CSS. For example, you could target the default step container using a class such as shepherd-element or individual elements within the steps.

To add a custom CSS class to a step:

tour.addStep({
  id: 'custom-styled-step',
  text: 'This step has custom styling applied!',
  classes: 'my-custom-class',
  attachTo: { element: '#myElement', on: 'bottom' },
});

Then, in your CSS file:

.my-custom-class {
  background-color: #f0f0f0;
  border-radius: 5px;
  padding: 10px;
}

Theming with CSS Variables

Modern CSS allows for creating themes using CSS variables (custom properties). You can define your theme’s colors, fonts, and other styles using CSS variables and then apply those variables throughout your stylesheet. This makes it easy to switch between different themes without needing to modify many individual CSS rules. Shepherd doesn’t directly manage themes but it’s well-suited for theming using CSS variables. You define your variables, then target the appropriate Shepherd classes and elements with your themed CSS.

Example of defining a theme using CSS variables:

:root {
  --shepherd-primary-color: #007bff;
  --shepherd-background-color: #f8f9fa;
  --shepherd-text-color: #333;
}

.shepherd-element {
  background-color: var(--shepherd-background-color);
  color: var(--shepherd-text-color);
}

.shepherd-button {
  background-color: var(--shepherd-primary-color);
  color: white;
}

This approach improves maintainability and makes it simpler to create and switch between multiple themes.

Creating Custom Themes

To create a fully custom theme, create a new CSS file containing all your styles. This file should completely or partially override the default Shepherd styles. Remember to include this new stylesheet in your application, replacing or supplementing the default Shepherd stylesheet. You can achieve this by creating new classes for elements and assigning them as the classes option for the steps within your Shepherd.Tour or using CSS variables as described above. A well-structured approach involves creating a set of CSS classes that specifically target Shepherd’s elements and applying them through the classes option on steps or the tour itself. Consider using a CSS preprocessor (like Sass or Less) to manage larger and more complex themes effectively.

Advanced Topics

Integrating with other JavaScript libraries

Shepherd is designed to be compatible with other JavaScript libraries. However, the specific integration approach depends on the library. For example, integrating with a UI framework like React, Vue, or Angular usually involves creating custom components that wrap Shepherd’s functionality and manage state. Ensure that you handle potential conflicts between the libraries’ event handling or DOM manipulation. Consider carefully how Shepherd’s DOM manipulation might interact with other libraries modifying the same elements. Careful planning and testing are essential to avoid unexpected behavior or conflicts.

Accessibility Considerations

Accessibility is crucial for inclusive design. When creating tours with Shepherd, follow these best practices:

Internationalization and Localization

To support multiple languages, you’ll need to internationalize (i18n) and localize (l10n) your tours. This involves:

Performance Optimization

For optimal performance:

Troubleshooting and Debugging

If you encounter issues:

API Reference

This section provides a detailed overview of the Shepherd.js API. Note that specific options and their data types might vary depending on the Shepherd.js version. Always refer to the most current documentation for the most accurate information.

Shepherd Constructor

The Shepherd.Tour constructor creates a new tour instance.

const tour = new Shepherd.Tour({ options });

options is an object containing configuration options for the tour (see options object properties below).

addStep() method

Adds a new step to the tour.

tour.addStep({
  id: 'stepId', // Required: Unique identifier for the step
  text: 'Step content', // Step text (can be HTML)
  attachTo: { element: '#targetElement', on: 'bottom' }, // Required: Target element and position
  // ... other step options
});

Returns the tour instance.

show() method

Shows a specific step in the tour.

tour.show('stepId');

stepId is the unique identifier of the step to show. If the step doesn’t exist, it will likely throw an error or have no effect. Returns the tour instance.

hide() method

Hides the currently active step.

tour.hide();

Returns the tour instance.

next() method

Advances the tour to the next step.

tour.next();

Returns the tour instance. If it’s the last step, it might complete the tour or trigger an event depending on the configuration.

back() method

Navigates to the previous step in the tour.

tour.back();

Returns the tour instance. If it’s the first step, it might have no effect or trigger a specific event.

cancel() method

Cancels and closes the tour.

tour.cancel();

Returns the tour instance. This method typically cleans up the tour’s elements from the DOM.

on() method

Attaches an event listener to the tour.

tour.on('complete', () => {
  console.log('Tour completed!');
});

The first argument is the event name (e.g., 'complete', 'start', 'cancel', 'show', 'hide'). The second argument is the callback function to execute when the event occurs. Returns the tour instance.

off() method

Removes an event listener from the tour.

tour.off('complete', myCompletionHandler);

The first argument is the event name; the second is the callback function to remove. Returns the tour instance.

options object properties

The options object passed to the Shepherd.Tour constructor allows for configuring various aspects of the tour. Key properties include:

This is not an exhaustive list, and specific options and their availability might depend on the Shepherd.js version. Consult the latest official documentation for a complete and up-to-date list of options and their functionalities. Note that many options can also be specified directly at the step level, overriding the tour-level defaults.

Appendix

Frequently Asked Questions (FAQ)

Glossary of Terms

Contributing to Shepherd

If you’d like to contribute to Shepherd, please refer to the project’s contribution guidelines (if available). These guidelines typically include information on setting up the development environment, coding style, testing procedures, and the process for submitting pull requests. Contributions might involve bug fixes, feature enhancements, documentation improvements, or creation of new examples.

(Note: This section should be replaced with links to actual contribution guidelines if the project has them.)

License Information

Shepherd is licensed under the [License Name] license. See the LICENSE file for more details.

(Note: Replace “[License Name]” with the actual license name of the Shepherd project. This section should also include a link to the LICENSE file if one is present in the project.)