How do I add a like button (save to favorites button) inside repeater?

I have my data on a dynamic page with repeater. I want to add a heart icon that users can click and save the item from repeater as favorite. I also want to add a heart counter to show which users have clicked it, something like how this forum’s heart button works.
I started with modifying the Wix tutorial - ’ Corvid Tutorial: Adding a Wishlist to a Wix Stores Site ’ and was able to get it running in a broken way.
My problem is when I load the page, all items show clicked heart state. How do I change this to show full heart for only the items that user have added to favorite?

I think I am going wrong somewhere in this section of code:
$w.onReady( function () {
//TODO: write your page related code here…
checkWishlist()
});

as

ync function checkWishlist() {
if (wixUsers.currentUser.loggedIn) {
let wishListResult = wixData.query( “Wishlist” )
.eq( “product” , product._id)
.eq( “userId” , user.id)
.find();
$w( “#listRepeater” ).forItems( [wishListResult], ($item, itemData, index) => {
$w( ‘#inWishList’ ).show( ‘fade’ , {duration: 100 });
})
}
else {
$w( ‘#notInWishList’ ).show( ‘fade’ , {duration: 100 });
}
}

Here is my complete code:

import wixData from ‘wix-data’ ;
import wixUsers from ‘wix-users’ ;

let product;
let user = wixUsers.currentUser;

$w.onReady( function () {
//TODO: write your page related code here…
checkWishlist()
});

async function addToWishlist() {
let wishListItem = {
“video” : product._id,
“User Id” : user.id
};

let result = await wixData.insert( “Wishlist” , wishListItem);
}

export function notInWishList_click_1(event,$w) {
//Add your code for this event here:
product = $w( ‘#dynamicDataset’ ).getCurrentItem();
if (user.loggedIn) {
addToWishlist();
$w( ‘#notInWishList’ ).hide( ‘fade’ , {duration: 100 });
$w( ‘#inWishList’ ).show( ‘fade’ , {duration: 100 });
}
else
$w( ‘#loginMessage’ ).show();
}

async function removeFromWishlist() {
let wishListResult = await wixData.query( “Wishlist” )
.eq( “video” , product._id)
.eq( “User Id” , user.id)
.find();

if (wishListResult.length > 0 ) {
$w( ‘#notInWishList’ ).show( ‘fade’ , {duration: 100 });
$w( ‘#inWishList’ ).hide( ‘fade’ , {duration: 100 });
await wixData.remove( “Wishlist” , wishListResult.items[ 0 ]._id)
}
}

export function inWishList_click(event,$w) {
//Add your code for this event here:
product = $w( ‘#dynamicDataset’ ).getCurrentItem();
if (user.loggedIn)
removeFromWishlist();
}

async function checkWishlist() {
if (wixUsers.currentUser.loggedIn) {
let wishListResult = wixData.query( “Wishlist” )
.eq( “product” , product._id)
.eq( “userId” , user.id)
.find();
$w( “#listRepeater” ).forItems( [wishListResult], ($item, itemData, index) => {
$w( ‘#inWishList’ ).show( ‘fade’ , {duration: 100 });
})
}
else {
$w( ‘#notInWishList’ ).show( ‘fade’ , {duration: 100 });

I have tried many different things but I dont know how do I do this for a repeater. Any idea how I can achieve this?
Thank you in advance and any pointers are appreciated.

Hi,

I was able to locate a similar post here and one of our examples you can use as reference.

Have you tried using onItemReady() yet? What have you tried so far? You can also try storing the “like” as a value in a database collection based on the user that clicked on it and then query the relevant field from the collection to show or hide the icon.

Hope this helps!

Thank you for your answer.

  1. First Link - I have already achieved this. My like button works if it is not connected to users. i.e If I let my like button be an indefinite counter. In this case a user can like it more than once. But that’s not what I want.
    2)Second link - This example does not use a repeater. This works if your repeater item opens as a new window. I have this working as well. But again, not what I need.
    3)Third Link - Yes I have tried onItemReady for repeater. And I think I am doing something wrong in the code. I dont know how to selectively update specific items. I did try forEachItem and forItems using this https://www.wix.com/corvid/forum/community-discussion/liking-posts-in-repeater-comprehensive
    and corvid wishlist tutorial but did not succeed.

if (itemData.likes) {
if (itemData.likes.includes( wixUsers.currentUser.id )) {
$w(“#emptyHeart”).hide();
$w(“#emptyHeart”).collapse();
$w(“#fullHeart”).show();
$w(“#fullHeart”).expand();
}
}
This section goes in the onItemReady event of repeater. How do I make the above snippet use the results of the query from my original code since that collection is where my wishlist data is stored)
let wishListResult = wixData.query( “Wishlist” )
.eq( “product” , product._id)
.eq( “userId” , user.id)
.find();

I am new at JavaScript so I may be way off with my logic here. Any ideas?

Hi there, I’ve come across this as I’m looking to add same function.
Did you find a solution? Cheers

I have an old tutorial on this …