Repeater elements with variable widths?

I’m pretty sure this isn’t possible, but I thought I’d throw it out there. I have a repeater where…for example, some label could either be one letter, or a huge long word. Like this:

Dog
Cat
Supercalifragilisticexpialidocious
Tree

What I really would like to do is to create a repeater where each repeater element is “just wide enough” for the text that fits in it. I don’t really care if the label element is a text element, or a button (but I couldn’t find a way to make a button “just wide enough” either).

I’m trying to simulate a tab bar. There are a lot of tab items, most of which are narrow, with just a couple that are long. I really don’t want to have all the whitespace around the narrow labels, nor do I want the wide labels to break mid-word and wrap.

I’ve come up with a couple compromises, neither of which I really love…

Idea 1: Set the label text to the first N letters, with an ellipsis and then add a hover that shows a tooltip with the entire word. This is ugly though, because hover doesn’t work on mobile, so I’d like to avoid it if possible.

Idea 2: Don’t use a repeater. Instead, make one text element, then programmatically generate spans and set them in the text element’s html. Basically, write code that generates this:

Dog
Cat
Supercalifragilisticexpialidocious
Tree

Barring that…Has anyone written a custom tab bar that I could look at?

Barring that…In general, there have been several times where I’ve maxed out the functionality of Wix Elements and I’m looking for a few more sophisticated things. I’ve got a few npm packages installed (things like lodash). Are there recommended ones that provide libraries of custom elements? Are there people who write React/Node/Angular/whatever components that can be used in Wix pages?

Cheers
Tracey

You’re right. It can’t be done with repeater (unless you create a repeater of your own using Custom Element).

I’m not sure I fully understand what you’re trying to do, but maybe selection tags is what you really need.

No, I looked at selection tags, and that’s a different feature. All I’m really trying to do is make a menu that looks/behaves like a tab bar. Selection tags aren’t really the way to do that.

Thank you though. If anyone knows of a Github project where people create Wix custom elements, please let me know. I’d love to be able to leverage the work of a community instead of having to reinvent every wheel.

Cheers

I know that Selection Tags are different.
But it’s quite easy to make them look and function as a tab bar.

All you need to do (besides designing) is:

$w("#selectionTags").onChange(() => {
let value = $w("#selectionTags").value.reverse()[0];//this line selects the last clicked value only.
$w("#selectionTags").value = value;
//and show the contents based on the value
}) 

Hm…I hadn’t considered this because it seemed like not what Selection Tags are for.

First…Selection Tags are meant to be an input…meaning, they write data to your database from an input form. This is not what I want. I am not submitting a form. I am asking a user to filter a database query based on the value selected.

Second, they are multi select. A user chooses any number of selection tags, and the selections are written to the form submission table. This is not what I want. I want to be able to pick one chip, and have it set a filter on a dataset…not write anything to a table.

Third, it is the UI layer that determines what the choices are, not the database. This means that if I have multiple UIs that use these chips, I have to set up the Selection Tag values in the UI layer. I want this information to come from the database so I only have to store it once, and it’s always consistent.

Here’s what I’m trying to do:

I have “enums” in my database in the form of reference tables. Those tables contain the only allowable values for a column in my main table. I want choices to come from the list provided by my database. Here’s a hypothetical example, I have two tables: Toys, and Colors. Toys has a MultiRef column to Colors. Colors has rows like Yellow, Orange, Red, Green, Blue, Purple.

In some particular UI (I’m building a search page), The user would say “show me only Blue toys” by clicking on the Blue tab/chip. The Toys dataset would apply the filter on the Toys.colors MultiRef column and filter the search results.

I want basically an enum whose values are displayed as chips. This is not what Selection tags are for. They are for accepting input from a user that conforms to a specific list of choices and writing it to a collection Tags column.

But…I could make this work by not actually connecting the Selection Tags to a database table/column, then programmatically populating the tag values by querying the Colors reference table in dataset.onReady, and then capturing the selection tag value in its change handler and setting a filter in Toys and create a custom change handler that unselected everything before applying the new selection onChange (using your code above). Basically, I would be using the UI capabilities only…not really the whole Selection Tag feature.

I suppose I could do this…Even though it’s not the intended use for Selection Tags, maybe this is not so hacky…I just coded up a quick POC and it works…(code below).

In fact, this could be the solution to another problem I had to HACK to get around…the fact that checkbox layouts are not easily controlled…you get a single row, or a single column…not a grid. So I had to create a pretty complicated (and what I really mean is…HORRIBLE) UI in order to be able to display filter menus that have a lot of choices. The UI is so bad that I had to just hide the whole page on mobile. I think I could rewrite it using this solution.

The only thing I sort of worry about with this solution is that since it’s not really the intended use of Selection Tags, I’m hoping Wix won’t change something that breaks how I’m using it.

But…barring that worry…this works…Thanks!

import wixData from 'wix-data';

$w.onReady(function () {
    $w('#colorsDataset').onReady(() => {
        $w('#colorsDataset')
          .getItems(0, $w('#colorsDataset').getTotalCount()).then((results) => {
  let options = results.items.map((item) => {
    return { label: item.title, value: item._id} });
  options.push({label: 'Show all', value: '-1'});
  $w('#colorSelectionTags').options = options;
 // by default, show all. Dataset is not filtered.
 $w('#colorSelectionTags').value = ['-1'];
 });
 });
});

export function colorSelectionTags_change(event) {
 // sets selection to just the last value - removes multi-select behavior
 let value = $w("#colorSelectionTags").value.reverse()[0];
    $w("#colorSelectionTags").value = [value];

 if (value === '-1') {
        $w('#toysDataset').setFilter(wixData.filter());
 } else {
        $w('#toysDataset').setFilter(wixData.filter().hasSome("color", Object.values([value])));
 }
}

Hi, Selection Tags are not necessarily related to the database.
You can connect them to a dataset but you don’t have to . You can set the options from the page code itself (and you can make it conditional - certain options in one condition and other option in another condition.

let options = [{label: "Option1", value:"option1"},{label: "Option2", value:"option2"}];
$w,onReady(() => {
$w("#selectionTags").options = options;
});