Introduction:
In our continuous effort to support our user community with practical solutions, we’re delighted to share a helpful guide contributed by Daniel Thomas from our community. This guide is for those who are looking to implement a 'like' button system on their Webflow site using Memberstack, without the need for external tools. A special thanks to Daniel for his valuable contribution!
How to Create a Like System with Webflow and Memberstack
Setting Up the Like Button
- Create a CMS Collection List: Start by creating the CMS collection list you want users to 'like' items from. Ensure each CMS item has a 'like' button.
- Assign Class and Custom Attribute to Buttons: Give each 'like' button a class name 'like-button'. Add a custom attribute (`data-cms-item="Unique CMS Item ID"`) to these buttons, linking them to a unique identifier in your Webflow CMS.
- Pre-style and Remove the 'is-liked' Class: Before publishing, pre-style the 'is-liked' class for these buttons and then remove it.
Implementing the JavaScript Code
Daniel provided the following JavaScript code to handle the functionality:
<script>
document.addEventListener('DOMContentLoaded', (event) => {
const memberstack = window.$memberstackDom;
// Get all the like buttons
let likeButtons = document.querySelectorAll('.like-button');
// Add an event listener to each like button
likeButtons.forEach(likeButton => {
let likeButtonLastClickedAt = 0;
likeButton.addEventListener('click', async function () {
// If the last click was less than 500ms ago, ignore this one
const now = Date.now();
if (now - likeButtonLastClickedAt < 500) {
return;
}
likeButtonLastClickedAt = now;
// Optimistically update the UI
const cmsData = this.getAttribute('data-cms-item');
if (this.classList.contains('is-liked')) {
this.classList.remove('is-liked');
} else {
this.classList.add('is-liked');
}
// Get the current member
let member = await memberstack.getCurrentMember();
// If the member is not logged in, redirect to /signup
if (!member || !member.data) {
window.location.href = '/signup';
return;
}
// Get current member's JSON
let memberJson = await memberstack.getMemberJSON();
// Unwrap unnecessary "data" objects
while (memberJson.data) {
memberJson = memberJson.data;
}
// Create the likes array if it doesn't exist
if (!memberJson.likes) {
memberJson.likes = [];
}
// Check if cmsData is already in the array, if not, add it
if (!memberJson.likes.includes(cmsData)) {
memberJson.likes.push(cmsData);
} else {
// If the item is already liked, remove it from the array
memberJson.likes = memberJson.likes.filter(item => item !== cmsData);
}
// Update member's JSON asynchronously
memberstack.updateMemberJSON({ json: memberJson }).catch((error) => {
console.error("Failed to update member JSON: ", error);
// If there was an error updating the JSON, revert the button style
if (this.classList.contains('is-liked')) {
this.classList.remove('is-liked');
} else {
this.classList.add('is-liked');
}
});
});
// Initialise the button state based on the member's likes
(async function initButtonState() {
// Get the current member
let member = await memberstack.getCurrentMember();
// If the member is not logged in, do nothing
if (!member || !member.data) {
return;
}
let memberJson = await memberstack.getMemberJSON();
// Unwrap unnecessary "data" objects
while (memberJson.data) {
memberJson = memberJson.data;
}
let cmsData = likeButton.getAttribute('data-cms-item');
// If the member has already liked the item, style the button as 'is-liked'
if (memberJson.likes && memberJson.likes.includes(cmsData)) {
likeButton.classList.add('is-liked');
}
})();
});
});
</script>
Displaying User Likes on a Separate Page
To showcase user 'likes' on a different page:
- Use JavaScript for conditional visibility in the Webflow CMS list.
- Duplicate your initial CMS list onto a new page, like "Your Likes," ensuring each item has the required custom attribute.
- Implement another JavaScript code snippet (provided by Daniel) to handle the visibility based on user 'likes'.
<script>
document.addEventListener('DOMContentLoaded', async () => {
const memberstack = window.$memberstackDom;
let memberJson = await memberstack.getMemberJSON();
// Unwrap unnecessary "data" objects
while (memberJson.data) {
memberJson = memberJson.data;
}
// Assuming each CMS item has a data attribute 'data-cms-item'
// which matches the names stored in the user's 'likes' array
let cmsItems = document.querySelectorAll('.featured-frequencies-card');
cmsItems.forEach(item => {
let itemName = item.getAttribute('data-cms-item');
// If the user has not liked this item, hide it
if (!memberJson.likes.includes(itemName)) {
item.style.display = 'none';
}
});
});
</script>
Conclusion:
Daniel’s contribution exemplifies the power of community knowledge sharing. We hope this guide helps you enhance your website’s interactivity with a user-friendly 'like' system.
Comments
0 comments
Please sign in to leave a comment.