Access elements by class name when clicked and retrieve information

Within my template, there are numerous links like this:

<a href="javascript:void(0);" class="add_to_cart" data-slug="{{ product.slug }}">Add</a>

I am trying to click on a link and retrieve the specific data-slug associated with it. I attempted to achieve this using JavaScript by selecting all the links.

var add_to_cart = document.getElementsByClassName('add_to_cart');

Next, I used a for loop:

for(var i = 0; i < add_to_cart.length; i++) {
    product_slug = add_to_cart[i].getAttribute('data-slug')

    add_to_cart[i].onclick = function() {
        console.log(product_slug)
    }
}

However, when clicking on a link, the console.log always displays the data-slug of the last link in the template. How can I correct this behavior to retrieve the data-slug of the clicked item? Your assistance is greatly appreciated.

Answer №1

The issue with your for loop is that the value of product_slug gets set when the loop executes. Since product_slug is a var, it keeps getting overwritten with each iteration of the loop. As a result, when the click listener is triggered, product_slug will hold the same value it had during the last iteration of the loop.

When you use var, the variable has function scope, meaning it's defined within the function.

On the other hand, using let or const creates a variable with block scope, which means it's defined within the block (enclosed by curly braces {}).

To learn more about the concept of scope, check out this resource on scope.

To resolve this issue, consider using let instead.

for(var i = 0; i < add_to_cart.length; i++) {
    let product_slug = add_to_cart[i].getAttribute('data-slug')
    add_to_cart[i].onclick = function() {
        console.log(product_slug)
    }
}

Answer №2

When iterating through a for loop to define a variable that is repeatedly written, the outcome may show the same value each time due to n events displaying the result.

To resolve this issue, you can access the current target of the onclick event and show its data-slug attribute instead.

Revise your for loop as follows:

var add_to_cart = document.getElementsByClassName('add_to_cart');
for(var i = 0; i < add_to_cart.length; i++) {

    add_to_cart[i].onclick = function(evt) {
        console.log(evt.target.getAttribute('data-slug'));
    }
}

Answer №3

If you're looking to access the target of a click event, you can do so by using the .target attribute of the initial argument in the event handler.

Take, for instance, this code snippet which attaches an event handler to all elements with the class add_to_cart on the webpage and outputs the slug to the console upon their activation:

let add_to_cart_buttons = document.querySelectorAll('.add_to_cart');

add_to_cart_buttons.forEach(function(node) {
  node.addEventListener('click', (e) => console.log(e.target.dataset.slug));
});

CORRECTION: I apologize for my previous misunderstanding regarding your second block of code. Your use of document.getElementsByClassName is indeed appropriate.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Panini fails to load JSON files

Currently, I am utilizing Zurb Foundation for Emails and my goal is to develop a straightforward multi-language email export system. This system will be driven by a data/lang.json file structured as follows: { "en": { "hello": "hello", " ...

The error message appeared as a result of the bluebird and mongoose combination: TypeError: .create(...).then(...).nodeify is

Recently, I encountered an issue while attempting to integrate bluebird with mongoose. Here's the scenario: I wrote some test code using bluebird without incorporating mongoose, and it worked perfectly. The code looked something like this: A().then( ...

Personalized version of a migration tool for deployment on the Heroku platform

When working with the package fork that I am currently dealing with, I noticed that there is no manage.py available. This means I can't simply run a manage.py makemigrations command when adding new fields to a model. Is there anyone who can provide as ...

Is it possible in TypeScript to convert a nested ternary into a standalone statement?

I encountered an error while working with the code snippet provided below. As I am relatively new to nested ternary operations, I would appreciate any assistance you could provide. Here is the example code: get notEmptyProduct(): string[] { return th ...

Mutex in node.js(javascript) for controlling system-wide resources

Is there a way to implement a System wide mutex in JavaScript that goes beyond the usual mutex concept? I am dealing with multiple instances of a node.js cmd running simultaneously. These instances are accessing the same file for reading and writing, and ...

Remove items from an array using JavaScript

My array, results = [duplicate, otherdup], holds a list of duplicates. Within my regular array, original_array = [duplicate, duplicate, duplicate, otherdup, otherdup, unique, unique2, unique_etc], how can I iterate through the results array and remove dup ...

Issue with Django query not being successfully transferred to AJAX in JSON structure

Trying to populate a textfield with its corresponding database value using Django and AJAX. The objective is for the textfield to automatically update when the dropdown value changes. However, encountering an error in console: SyntaxError: Unexpected to ...

Assigning initial values within the created() method using Vuex

I have a scenario where I need to set a default value for a state property when a component is initialized. Specifically, I want the user's preferred language prefLang to be derived from navigator.language if they haven't specified it through use ...

[ERROR_HTTP_HEADERS_ALREADY_SENT]: Headers can't be set once they have been sent to the client, expressjs

Whenever I attempt to insert data into my MySQL database using the express router function, I encounter an error. It appears that my server is trying to send a response twice, but I am unsure of where the issue lies. Here is the error message: throw err; / ...

I am encountering challenges with React.js implemented in Typescript

Currently, I'm grappling with a challenge while establishing a design system in ReactJS utilizing TypeScript. The issue at hand pertains to correctly passing and returning types for my components. To address this, here are the steps I've taken so ...

Ways to switch the class of the nearest element

When an image within the .process class is clicked, I am using the following code to toggle the class of .process-info to .process--shown. The code successfully toggles the class; however, it affects all elements on the page with the class of .process-inf ...

What is the best approach for retrieving the value of a deeply nested JSON object?

Currently, I am developing an application in JavaScript and I have encountered a JSON object. Here is a simplified version of the JSON object: { "data": [ "user": { "pictures"{ "sizes"[ 0: { "link": "http://www" ...

Is it possible to use file upload for sending via Ajax's POST method?

Let's talk about the scenario at hand Here's what happens in a single form: 1) The user clicks on the 'browse' button, which opens a dialog to select an image file for uploading. Example: input id='img_upload' name="ufile" ...

Count the occurrences of different fields in a document based on a specified condition

Seeking a way to extract specific values and calculate the frequency of those values in a collection based on a certain key's ID. Consider this example of a single document from a Game Logs collection: { "_id": "5af88940b73b2936dcb6dfdb", "da ...

Using JavaScript or TypeScript to locate the key and add the value to an array

My dilemma involves an object structured as follows: [{ Date: 01/11/2022, Questionnaire: [ {Title: 'Rating', Ans: '5' }, {Title: 'Comment', Ans: 'Awesome' } ] }, { Date: 01/11/2022, Questionnaire ...

How can one retrieve the parent object from an admin TabularInline in Django admin?

To effectively filter the dropdown Fk fields within the inline object based on its parent, I need to access the parent object of an item. Below is a snippet of my code: models.py class Match(models.Model): date_time = models.DateTimeField() home_ ...

Dealing with errors in Vue components: What you need to know

Recently, I encountered an issue where a bug appeared in Chrome but worked fine in Firefox. The problem was with an upload component that looked like this: <input type="file" v-on:change="upload($event)"/> upload(e) { this.name ...

"Using JavaScript to extract a portion of the URL and perform a redirect

I am attempting to extract a specific part of the URL and then redirect to that particular section. Essentially, what I want is for a script to generate a link that will be opened. This link would appear as . My goal now is to extract the portion of the ...

Should one consider using Eval?

I encountered a scenario where I needed to dynamically retrieve the object value from an array that contained object keys retrieved from an API. I opted for a solution that involved using the eval function. class App extends React.Component { constru ...

Angular.js - index template fails to execute controller, but other templates work flawlessly

I am facing a strange issue with my Angular application that uses ngRoute. I have set up different controllers for each template in the routes.js file: routes.js: angular.module('PokeApp', ['ngRoute']) .config(function($routeProvide ...