LoopKit
Product Carousel, Slider & Card Builder for WooCommerce
v1.0.0 · handbook

LoopKit Handbook

One Elementor widget that turns your WooCommerce catalogue into a carousel. Everything is configured on the widget, in the editor — there is no settings page and no shortcode. The one LoopKit page in your admin menu is there to help you get started, and has nothing to configure.

Install

LoopKit needs WooCommerce and Elementor. It will not activate without them, and tells you which one is missing.

Minimum versions. Newer is fine; LoopKit is tested on current releases.
RequirementMinimumNotes
WordPress6.0Multisite supported
WooCommerce7.0HPOS declared
Elementor3.15Free version is enough
PHP7.4Clean on 8.4

Install from Plugins → Add New, or upload the zip. Activate WooCommerce and Elementor first — LoopKit declares them as required plugins, so WordPress will refuse to activate it before they are running.

The LoopKit page

Admin menu → LoopKit. Administrators only.

After activation, a LoopKit item appears in the admin menu. It is a single information page, not a settings screen: carousels are always configured on the widget.

Quick start

A button to your Pages list, and three screenshots showing where the widget is, how the card is shaped, and what visitors see.

Included, free

What the free version does, in brief.

Free and Pro

A comparison table. Pro is marked Coming soon, with a link to hear when it launches. Nothing is for sale yet, and nothing in the free version is locked.

Tested themes

Storefront, Astra, Hello Elementor, GeneratePress and Kadence.

Changelog

Read from the plugin's own readme, so it always matches the version installed.

Help and details

Links to this handbook and to support, plus the installed LoopKit, WooCommerce, Elementor and WordPress versions — useful to paste into a support request.

The welcome notice

Once, after activation, administrators see a short notice on the Plugins screen and the Dashboard with Get started and Dismiss. It goes away for good as soon as you dismiss it or open the LoopKit page, and it is remembered per user. There is no redirect on activation, and no other notice anywhere in wp-admin.

The Plugins screen also gets a Get started link under LoopKit. Uninstalling the plugin removes the record of who dismissed the notice.

Add a carousel

Edit any page with Elementor, search the widget panel for Product Carousel, and drag it onto the canvas. It renders immediately using recent products and the Classic preset — there is nothing to configure before you see something.

Changes appear as you make them. Style, card layout, motion and carousel behaviour redraw in the canvas with no page reload and no server request. Only a change to the product query itself fetches anything, and your previous products stay on screen while it does.

Products

Content tab. Decides which products appear and in what order.

Source

Six sources. Everything except Manual selection takes the filters below it.

Recent productsrecent

Newest first, by publish date.

Featured productsfeatured

Products you starred in WooCommerce.

On saleon_sale

Anything with an active sale price, including variable products where only one variation is reduced.

Best sellingbest_selling

By WooCommerce's total sales count.

Top ratedtop_rated

By average review rating.

Manual selectionmanual

Pick products by hand. They appear in the order you choose them, and the filters are hidden because they no longer apply.

Filters and limits

Products to show

1 to 100. This is how many the carousel holds in total, not how many are visible at once — visible count is Columns, under Layout.

Order by / Order

Date, title, menu order, price, popularity, rating, or random. Ties are broken by product ID, so the same query always returns the same order.

Categories / Tags

Leave empty for the whole catalogue. Choosing several matches products in any of them.

Product types

Simple, variable, grouped, external. Empty means all types.

Hide out of stock

Off by default, so out-of-stock products still appear — pair it with the stock badge if you would rather show them as unavailable than hide them.

Respect catalog visibility

On by default. Leave it on so products you hid from the catalogue stay hidden here too.

Only products with an image

Skips products with no featured image, instead of showing WooCommerce's placeholder.

Card

Content tab. Decides what each product card contains.

Two ways to build one

Card layout chooses between them. Start from a preset gives you one of eight ready arrangements. Build it myself opens the Card Builder, where you assemble the card yourself.

Elements and zones

A card holds up to eight elements, and each one sits in one of three zones:

Image area

The top of the card. Badges sit over the image here.

Content area

Below the image. Text and buttons stack in the order you set.

Hover overlay

Hidden until someone hovers the card — or reaches it with the keyboard. Good for an add-to-cart button you want out of the way until it is wanted.

The eight elements are image, sale badge, stock badge, title, price, rating, short description and add to cart. Drag a row to reorder it. Each row has its own options once you choose its element — the title gets an HTML tag and a word limit, the image gets a size and a hover flip, the sale badge chooses between a word and a discount percentage, and the rating can show an empty row for products nobody has reviewed yet.

Hiding an element on some devices

Every row has a Hide on switch for each device your site uses — Desktop, Tablet and Mobile, plus any custom breakpoints you have turned on in Elementor. A short description that helps on a wide screen can disappear on a phone, while the rest of the card stays.

In the editor, a hidden element works like every other hidden Elementor element: preview that device and it stays in place, faded and striped, so you can still select and edit it. Turn off Elementor's Show hidden elements in the responsive bar to see the card exactly as visitors will.

An element can only appear once

A card cannot hold two prices or two images. If you add a second row with the same element, the extra one is ignored rather than rendered twice.

How presets work

A preset is a saved arrangement of elements — not a skin, and not a template.

Picking a preset sets which elements the card holds and which zone each one sits in. It does not set any colours, fonts or spacing. Those always come from the Style tab, which is why a preset takes on your site's design rather than dropping a stranger's design into your page.

Presets and hand-built cards run through exactly the same renderer, so a preset can never do something the Card Builder cannot. Switching between them changes the arrangement and nothing else.

What each preset contains, and which zone each element sits in.
PresetImageSaleStockTitlePriceRatingDescriptionCart
ClassicII—CCC—C
MinimalI——CC———
OverlayII—CC——H
CompactI——CC———
EditorialI——CC—C—
PromoIIICC——C
ReviewedI——CCC—C
ShowcaseI——CC—HH

I image areaC content areaH hover overlay— not in this preset

A few presets also set an element option: Compact trims the title to four words, Editorial uses an h2 title and an 18-word description, Promo shows the discount as a percentage and badges only low or out-of-stock products, Reviewed shows the rating even with no reviews, and Showcase flips to the gallery image on hover.

Starting from a preset, then changing it

Switch Card layout to Build it myself. The Card Builder opens with its own list, which you can edit freely. Your preset choice is remembered, so you can switch back at any time without losing it.

Saving your own preset

Built a card you want to reuse? Under the Card Builder, type a name into Save this card as a preset and press Save preset. It joins the Preset list at once, for every carousel on the site, with no page reload. Saving again under the same name replaces it.

To remove one, choose it under Preset and press Delete this saved preset. Carousels that used it switch to Classic. The eight built-in presets cannot be deleted.

Saved presets are shared. Because a change reaches pages other people wrote, saving or deleting one needs an Editor or Administrator account. A site can keep up to 50.

Layout

Content tab. How many cards fit, and how far apart they sit.

Columns

1 to 8, set per device. Defaults are 4 on desktop, 3 on tablet, 1 on mobile. Changing it never reloads or rebuilds the carousel — it is a CSS value, so it updates instantly and follows your own Elementor breakpoints.

Gap

Space between cards, per device, in px or rem.

Accessible label

Names the carousel for screen reader users — "Best sellers", "New arrivals". Defaults to "Products". Give every carousel on a page a different one, so they can be told apart.

Motion

Content tab. Hover behaviour and entrance.

Hover effect

Zoom image, lift card, tilt, overlay fade, slide content up, or draw a border. Each has its own control for how far it goes. Every effect also runs on keyboard focus, so it is never mouse-only.

Easing

Smooth, snappy, gentle, standard, overshoot or linear — plus Custom, which takes any CSS easing value, such as cubic-bezier(.34,1.56,.64,1).

Hover duration

How long hover effects take, 0 to 1200ms.

Entrance stagger

Delay between each card as the carousel scrolls into view. Zero reveals them together.

All of it switches off for visitors who ask for reduced motion. If someone has set that preference in their operating system, hover effects, the stagger and autoplay all stop — you do not need to configure anything.

Style tab

Eight sections, in the order they appear. Every colour and font can come from your Elementor Global Colors and Global Fonts, so a carousel matches the site by default.

Card

Background, content padding, space between elements, corner radius, border, shadow, and the hover overlay colour.

Image

Shape is square by default, so every card is the same height whatever shape your photographs are — a catalogue shot at mixed sizes would otherwise produce a ragged row. Landscape, wide and portrait are there too, and Original proportions lets each image keep its own.

Fit then decides what happens to images that are not that shape: Fill the shape crops them, Fit inside letterboxes them. Choose fit-inside for products photographed on white, where cropping would cut the product. Background fills the letterboxed area and sits behind transparent PNGs. Inset adds padding so the image sits inside the card rather than running to its edges, and there is a corner radius and border for the image itself.

Text

Title typography and colour, with a separate hover colour. Price typography and colour, plus a colour for the struck-through original price on sale items.

Rating

Star colour, empty star colour, size and alignment.

LoopKit draws its own stars. WooCommerce renders ratings with an icon font from its own stylesheet, so on a site that dequeues WooCommerce CSS — common on tuned installs — the card would show the sentence "Rated 4.33 out of 5" instead of stars. LoopKit draws them from the same markup, so the rating looks the same whether or not that stylesheet is on the page, and these colour controls always apply.

Screen readers still hear the full sentence: the stars carry it as their label, so nothing is lost by hiding the text.

Badges

Shared typography, then separate background and text colours for the sale badge and the stock badge, plus distance from the card edge and corner radius.

Button

Typography, normal and hover colours, padding, radius, border, and whether the button fills the card width or fits its text.

Short description

Its own section, because it is the one element usually switched off and it needs more room than a colour when it is on: typography, colour, alignment, and space above it.

Navigation

Arrows: size, colour and background, separate colour and background on hover, line thickness, corner radius and a border. Pagination: dot colour, active dot colour, size, the space above the row, and the progress bar's height.

And the focus ring — the outline keyboard users see. You can recolour it to suit your design; it is never removed.

Themes

LoopKit is checked against five reference themes before every release. These are the five, and what "supported" is measured on.

Verified on WordPress 7.1, WooCommerce 11.1.0 and Elementor 4.2.4.
Theme Renders Equal heights Stars draw No side scroll Console clean Version
Storefront4.6.2
Astra4.13.11
Hello Elementor3.5.1
GeneratePress3.6.1
Kadence1.5.2

What each column means

Renders

The carousel appears, initialises, and its arrows and dots work.

Equal heights

Every card in the row is exactly the same height, measured — not eyeballed — including when one product's title wraps to two lines.

Stars draw

Ratings render as stars rather than the sentence "Rated 4.33 out of 5", which is what appears when a theme does not load WooCommerce's stylesheet.

No side scroll

The page is never wider than the window. Themes with edge-to-edge containers are the ones that catch this.

Console clean

No JavaScript errors from LoopKit on load or on interaction.

Other themes are not unsupported. LoopKit prefixes every class, scopes its styles to the widget, and does not depend on WooCommerce's stylesheet. These five are simply the ones checked on every release, chosen because between them they cover the ways a theme usually interferes: its own WooCommerce styling, edge-to-edge containers, and a minimal reset.

Accessibility

Built in, on by default, and not something you configure. This is what ships in the free version.

  • The carousel is a labelled region, announced as a carousel, using the name you set in Accessible label.
  • Each slide is announced with its position — "3 of 12".
  • Slides that are off screen are made inert, so keyboard focus never disappears into a card nobody can see.
  • Arrows and dots are real buttons with proper names, and the current dot is marked as current.
  • Autoplay always comes with a visible pause button, placed before the slides so it can be reached first. This is a WCAG requirement, which is why it cannot be turned off separately.
  • Live-region announcements are silent while autoplay runs, and become polite as soon as the visitor takes control.
  • Escape moves focus out of the carousel, so it can never trap the keyboard.
  • The pagination dots are a single Tab stop. Tab lands on the current dot; the arrow keys move between dots and the carousel follows; Home and End jump to the first and last. A carousel of a hundred products never makes a keyboard user tab through a hundred dots.
  • Focus rings are always visible and inherit your theme's accent unless you recolour them.
  • Each card contains exactly one link — the title, stretched across the whole card. A keyboard user hears the product name once, rather than tabbing through several identical links.

Performance

  • Nothing loads on pages without a carousel. The stylesheet and script are registered against the widget, so a page that does not use it downloads neither.
  • The carousel engine is fetched on demand. Swiper is a separate file that is only requested when a carousel approaches the viewport. A visitor who never scrolls that far never downloads it.
  • No jQuery.
  • Columns, gaps, colours and motion are CSS custom properties, so changing them costs nothing at runtime and nothing in the editor.
  • The carousel measures itself rather than the window, so it lays out correctly in a sidebar, a narrow column or a popup — not only at full page width.

For developers

Filters and actions, all prefixed loopkit_.

Query argumentsloopkit_query_args

Filters the arguments before the product query runs. Receives the arguments and the normalised settings.

Carousel optionsloopkit_carousel_options

Filters the Swiper options. Also dispatched in the browser as the loopkit/carousel/options event, so you can change them from either side.

Card elementsloopkit_card_elements

Registers an additional card element. Classes must extend LoopKit's element base; anything else is discarded.

Presetsloopkit_preset_templates

Registers a preset. See below.

Slide actionsloopkit_before_slide / loopkit_after_slide

Fire around each slide, passed the WC_Product. Anything you print appears inside the carousel at that position.

Registering your own preset

Presets are data, so the editor can draw yours without asking the server — which is why there is no PHP template to override. Build rows with the helper and return them:

use LoopKit\Card\Card_Schema;
use LoopKit\Render\Preset_Library;

add_filter( 'loopkit_preset_templates', function ( $presets ) {
    $presets['house_style'] = array(
        'label' => __( 'House style', 'my-theme' ),
        'stack' => array(
            Preset_Library::row( 'image', Card_Schema::ZONE_IMAGE ),
            Preset_Library::row( 'title', Card_Schema::ZONE_CONTENT, array( 'tag' => 'h2' ) ),
            Preset_Library::row( 'price' ),
            Preset_Library::row( 'add_to_cart', Card_Schema::ZONE_HOVER ),
        ),
    );

    return $presets;
} );

Your preset then appears in the Preset dropdown alongside the built-in eight, and renders in the editor canvas exactly as it will on the page.

Presets saved from the panel reach the library through this same filter, at priority 5, so a filter at the default priority can still see and adjust them. Saved preset names start with saved_.

Custom elements and device hiding

An element registered with loopkit_card_elements gets the Hide on switches for free on the frontend, as long as its markup uses get_element_classes(). In its canvas template, print {{ loopkitItem.hidden }} at the end of the same class attribute so the editor hides it too.

Two Swiper options cannot be overridden. a11y stays off, because Swiper's own accessibility module would label the same controls a second time and contradict LoopKit's labels. watchSlidesProgress stays on, because slide visibility is what decides which slides are inert. Everything else is yours to change.

Troubleshooting

The carousel shows nothing

The query matched no products. Check the source and filters — the most common causes are a category with no published products, Only products with an image combined with a catalogue that has none, and Manual selection with nothing chosen.

Cards are different heights

Cards fill their slide, so a title wrapping to two lines does not shorten its neighbours. If the heights still differ, you are on Style → Image → Shape → Original proportions with photographs of mixed shapes. Switch Shape to square or one of the landscape options and every card will match.

The page scrolls sideways

It should not: arrows set to Outside reserve their own gutter rather than hanging past the carousel, and drop it once the carousel is narrow. If you are seeing a horizontal scrollbar, something else on the page is wider than the viewport — check other sections before the carousel.

I can see more products in the editor than on the page

Products to show is the total the carousel holds; Columns is how many are visible at once. If the editor canvas is wider than your page's content area, it will show more of them at a time.

Autoplay is not moving

If your operating system is set to reduce motion, LoopKit stops autoplay deliberately and shows the rotation control in its stopped state. This is intended. Press the play button to start it for your session, or check your system's motion setting.

Ratings show as a sentence instead of stars

That is what happens when WooCommerce's stylesheet is not on the page — its stars come from an icon font in that file. LoopKit draws its own stars from the same markup, so if you are seeing text, you are on a version before 1.0.0 or the carousel's stylesheet has not loaded. Check that the page is not stripping the loopkit-frontend stylesheet.

Some cards have stars and others have a gap

Products nobody has reviewed have no rating to show. Turn on Show with no reviews on the rating element and unreviewed products get an empty row of stars instead, so every card stays the same height. The Reviewed preset has this on already.

My theme's styles are fighting the carousel

Every LoopKit class begins loopkit-, and the carousel is scoped to the widget wrapper. If a theme rule is winning, target the same element through the Style tab first — Elementor's generated CSS has higher specificity than almost any theme stylesheet, so the control will usually win without custom CSS.

Two carousels on one page behave oddly for screen readers

Give each one a different Accessible label. Two regions with the same name are hard to tell apart.

Where is the settings page?

There isn't one, by design. Everything lives on the widget, so a carousel's configuration travels with the page it is on. The LoopKit page in the admin menu is for getting started, documentation, support and the changelog; it has nothing to configure.

How do I hide the LoopKit menu from a client?

Only accounts that can manage options see it, so an Editor or Shop Manager account never does. To remove it for administrators too, add remove_menu_page( 'loopkit' ); on the admin_menu hook at a priority above 10.