Velo: Automatically Make All Repeaters Clickable Without Hardcoding IDs?

Hi everyone,

Right now I’m using Velo code to make multiple repeaters clickable so that the entire container inside each repeater item links to a dynamic product page.

Here’s the approach I’m using:

import wixLocation from 'wix-location';

$w.onReady(function () {

    function makeRepeaterClickable(repeaterId, containerId) {
        $w(repeaterId).onItemReady(($item, itemData, index) => {

            const productUrl = `/product-page/${itemData.slug}`;

            $item(containerId).onClick(() => {
                wixLocation.to(productUrl);
            });

        });
    }

    // Apply to multiple repeaters
    makeRepeaterClickable("#repeater2", "#productContainer");
    makeRepeaterClickable("#repeater3", "#clickArea");

});

This works fine, but I’m wondering:

:backhand_index_pointing_right: Is there a true drag-and-drop solution for this?

Ideally, I’d love a way to:

  • Make the entire repeater item clickable

  • Link directly to the dynamic page

  • Avoid writing custom code for each repeater

  • Avoid manually mapping repeater IDs

Is there a built-in dataset connection method, hidden setting, or best practice pattern I’m missing?

Would appreciate any insight from anyone who’s solved this more elegantly.

Thanks!

Currently, repeater items don’t have a link capability, but do support onClick events, which is why code is the only viable solution here.

You could do some recursive loop that goes through the page, and checks all levels of components for Repeaters, and return their IDs.

Something like:

$w.onReady(async () => {
    const repeaterIds = await getAllRepeaterIds($w("#page1").children)

	console.log("repeaterIds", repeaterIds)
});

/**
 * Recursively finds all Repeaters on the page or within a specific container.
 * @param {Array} elements - The array of children to search (usually $w('#page1').children)
 * @returns {Array<string>} - An array of IDs for all found repeaters.
 */
function getAllRepeaterIds(elements) {
    let repeaterIds = [];

    elements.forEach(element => {
        // Check if the current element is a Repeater
        if (element.type === "$w.Repeater") {
            repeaterIds.push(element.id);
        }

        // If the element has children, recurse deeper
        if (element.children && element.children.length > 0) {
            repeaterIds = repeaterIds.concat(getAllRepeaterIds(element.children));
        }
    });

    return repeaterIds;
}