Recipe List

Wix Blocks

Recipe List

Wix Blocks
This template is built with:
This list template showcases a pre-designed app that’s connected to a collection. The collection contains sample content that you can easily replace. Users can manage the app’s data from a dashboard page pre-built following the Wix Design System. The template comes with responsive presets, allowing users to choose from different layouts. Use this template to build custom business solutions like inventory, catalog, directory and more.

How We Built This: An Overview

This app was built on several areas of the Wix Blocks editor. Here is how we did it.

Widgets and Design

The Widgets and Design area is where you create the user interface of your widgets, using drag and drop Wix elements. In this area we:

  1. Created the Recipe Feed widget. This widget shows a list of all the recipes.
  2. Created the general structure of the widget: a top cover and a repeater that holds the recipes.
  3. Created two more Design Presets for the widget, based on the first design. The presets are: Mobile Layout and List Layout.
  4. Created the Recipe Lightbox widget. A lightbox is a popup that you can use in Wix sites. This widget shows additional data for each recipe.
  5. Added a button in each item of the Recipes List repeater, to link to that recipe’s lightbox.
  6. In the widget code panel, we added the initRepeater() function, which sets the number of items according to the user's choice and opens the Recipe Lightbox with the relevant data.
See code for Recipe Feed Widget
    import { openLightbox } from 'wix-window-frontend';
    //read more: https://www.wix.com/velo/reference/wix-window-frontend/lightbox

let itemsCount;

$w.onReady(async function () {
    await initRepeater();
});

$widget.onPropsChanged(async (oldProps, newProps) => {
    await initRepeater();
});

//Initialize the repeater data and sets the page size to display a specific number or all items based on user choice.
async function initRepeater() {
    switch ($widget.props.recipesVisibility) {
    case 'specificNumber':
        itemsCount = $widget.props.itemsToDisplay;
        break;
    case 'allItems':
        $w("#recipeDataset").onReady(() => itemsCount = $w("#recipeDataset").getTotalCount());
        break;
    }
    $w("#recipeDataset").setPageSize(itemsCount)
        .catch((err) => {
            let errMsg = err.message;
            let errCode = err.code;
        });

    // Open a lightbox with detailed recipe information when the "Get the Recipe" button of each repeater item is clicked.    
    $w('#recipesRepeater').onItemReady(($item, itemData) => {
        $item('#recipeLearnMore').onClick(async () => {
            await openLightbox('Recipe Lightbox', { recipeData: itemData });
        });
    });
}
See code for Lightbox Widget

import { lightbox } from 'wix-window-frontend';
import wixWindowFrontend from 'wix-window-frontend';

$w.onReady(function () {
    // Get the recipe data passed through the lightbox context
    const receivedData = lightbox.getContext().recipeData;

    // Set the lightbox elements with recipe data
    $w('#recipeTitle').text = receivedData.title;
    $w('#recipeAuthor').text = receivedData.authorName;
    $w('#recipeDuration').text = receivedData.duration.toString();
    $w('#recipeDifficulty').text = receivedData.difficulty;
    $w('#recipeRating').value = receivedData.rating;
    $w('#recipeDescription').text = receivedData.description;
    $w('#recipeIngredients').html = receivedData.ingredients;
    $w('#recipeInstructions').html = receivedData.instructions;
    $w('#recipeImage').src = receivedData.image;

    //Close the lightbox when the close button is clicked
    $w('#XButton').onClick(() => {
        wixWindowFrontend.lightbox.close();
    })
});

Databases

CMS database collections in Blocks let you store data in an app and on a site. In this area, we created a database collection that contains all the recipes. We:

  1. Added a collection to hold the recipe data (name, image, etc).

  2. Connected the repeater elements to the collection fields. This is a way to present dynamic data without code

    See how it's done
    1. Click the repeater.
    2. Click on the Connect to CMS icon in the action bar.
    3. Select the dataset.
    4. Select the field to connect to each element in the repeater (for example: the Image field to the recipe image.

    Connecting Repeater

App Dashboard

The app dashboard is used as the backoffice of this app, to allow site builders to manage the recipes collection. In this area, we:

  1. Created a dashboard page for the app.
  2. Added a multi-state box to the dashboard page, with two states:
    • Form, for adding another recipe
    • Recipes, for managing the list in a repeater that displays the preview data.
  3. To connect the form fields, we created a dataset in a “write” mode and connected it to the input elements in the state as described in the Databases step.
  4. Added editing actions to the form buttons, Submit for the Save button, and Delete for the Cancel button.
  5. To connect the Recipe Feed, we created a dataset in a “read & write” mode and connected it to the repeater fields as described in the Databases step.
  6. Added a Delete editing action to the trash buttons.
  7. Added code to manage the navigation between the states.
See dashboard code
// Handle navigation between 'recipes' and 'form' states
$w.onReady(async function () {
    $w('#addButton').onClick((e) => {
        $w('#multiStateBox1').changeState('form');
    })
    $w('#cancelBtn').onClick((e) => {
        $w('#multiStateBox1').changeState('recipes');
    })
    $w('#saveBtn').onClick((e) => {
        $w('#multiStateBox1').changeState('recipes');
    })
});

Panels tab

Custom panels let site builders customize widget settings. In our case, the settings include the number of recipes to present. In this area, we:

  1. Created a Custom Panel for managing the widget, named Recipes List Settings.
  2. Added a radio button to determine whether to show all or some of the recipes.
  3. Added a slider to set the number of recipes to show, in case the user wants to show only some of the recipes.
  4. Added code to handle the radio button and slider.
  5. Added a button connecting to the dashboard page, and code to open the dashboard URL from the button.
See panel code
import wixWidget from 'wix-widget';
import wixEditor from 'wix-editor';
import wixApplication from 'wix-application';

$w.onReady(async function () {
    //Fetch the current widget properties 
    const props = await wixWidget.getProps();
    //Loads the panel element with the current widget properties values
    $w('#recipesVisibilityRadioButton').value = props.recipesVisibility;
    ($w('#recipesVisibilityRadioButton').value == 'specificNumber') ? $w('#recipesSlider').expand(): $w('#recipesSlider').collapse();
    $w('#recipesSlider').value = props.itemsToDisplay;

    //Handle value changes in the panel elements
    $w('#recipesSlider').onChange(async event => {
        await wixWidget.setProps({ itemsToDisplay: $w('#recipesSlider').value });
    });
    $w('#recipesVisibilityRadioButton').onChange(async event => {
        $w('#recipesVisibilityRadioButton').value == 'specificNumber' ? $w('#recipesSlider').expand() : $w('#recipesSlider').collapse();
        await wixWidget.setProps({ recipesVisibility: $w('#recipesVisibilityRadioButton').value });
    });
    // Open dashboard page from the 'Manage Recipes' button
    const appInstance = await wixApplication.getDecodedAppInstance();
    $w('#manageRecipesButton').onClick(() => {
        wixEditor.openDashboardPanel({ url: `app/${appInstance.appDefId}` });
    });
});

Configuration tab

In the Configuration area, we:

  1. Changed the name of the widget’s main action button to Manage Recipes.

  2. Connected this action button to the dashboard page.

  3. Added another main action button, and named it Settings.

  4. Connected this action button to the Recipes List Settings panel.

    See how it looks

    Connect Button to Dashboard

Installation Settings

The app and widget installation settings let you configure various aspects of the installation process. In this area, we:

  1. Defined the Recipe Feed widget to be automatically added to the current page on a site.

  2. Defined the Recipe Lightbox widget to be added as a lightbox, and set its default presets for desktop and mobile.

  3. Experience tip - preset visibility: By default, all design presets are shown in a site's Add + panel. To give users a better experience, we removed irrelevant presets from this panel and left them only in the presets panel.

  4. Added preset images. Make sure to change these images to your own if you change the appearance of the app.

    See how it looks

    Connect Button to Dashboard