Utilize Vue to activate updates by customizing a d3 event

Summary: I am working on a Vue.js app where multiple components need to update after a property change triggered by a d3 event dispatch. However, only the last component seems to react.

In my app, there is a component called Loc that contains 23 d3 visualizations in separate Chart components, each of which has 47 data points represented by <a> tags.

Each hover over a <a> tag must trigger a unique Semantic-UI popup defined in a Tip component.

In theory, there should be (47 * 23) instances of the Tip component, but only (47 * 1) are actually being rendered and mounted, despite the existence of 23 instances of the Chart component with a renderComplete function defined in the data.

The structure of the pseudo-app can be visualized like this:

<Loc>
  <Chart v-for="..."> 
    <svg :id=uuid></svg>
    <div v-if="renderComplete">
      <Tip v-for="...">

Each d3 visualization triggers a custom completed event once it finishes rendering.

The issue lies in the fact that while all visualizations render successfully, only the Tip components in the final Chart instance out of 23 are displayed. The first 22 instances fail to render properly. Console output confirms that the event is dispatched and listener executed 23 times as expected.

I have tried various approaches such as making renderComplete a computed property and moving the event listener declaration to the created hook, but without success. Any insights or suggestions would be greatly appreciated. Thanks!

Answer №1

I finally pinpointed the issue. It turned out to be a facepalm-worthy mistake.

The problem stemmed from loading the module containing the d3 functions using require, which led to only a single instance being created. Reusing it multiple times caused its state to reset each time. This resulted in referencing the singleton with the state attributes from the final iteration when post-processing the first Chart instance on renderComplete.

To resolve this issue, I decided to refactor the d3chart.js into an es6 class, instantiate it with new, and no longer bind it in the component declaration:

The previous approach

In the Chart usage declaration within Loc:

<component :is="Chart" :myprop="myprop"></component>

and in the Loc definition:

data() {
  return {
    myprop: require('@/viz/d3chart.js')
  }
}

The new approach

<component :is="Chart"></component>

and

import myprop from '@/viz/d3chart.js'
... 
data() {
  return {
    myprop: new myprop()  
  }
}

Thank you for guiding me through this!

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

Cross-building targets for Node modules for deployment on npm platform

I'm working on an ES6 module that needs to be compatible with different environments. I'm not sure whether to use webpack or rollup for building, and how to target specific environments. Building for Different Environments ES6 environments like ...

Beta version of Bootstrap 4 - Enhancing User Experience with ScrollSpy Feature

I've encountered an issue getting my anchors to smooth-scroll to the target text. Despite trying jQuery solutions from various sources, nothing seems to work inexplicably. Even ScrollSpy doesn't seem to do the trick. I'm currently working w ...

What is the best way to display data from the Nuxt.js store?

I am new to Nuxt JS and following a tutorial on the Nuxt website. I created a store in store/index.js. export const state = () => ({ mountain: [], }) export const mutations = { addMountain(state, mountain) { state.mountain.push(mountain) }, } ...

In the context of a controller, a directive with an isolate scope does not automatically update when a new element is added

I am currently working on implementing a basic recent searches list feature on my website. The idea is that when the user clicks on the search button, two inputs are combined and added to an array named "recentSearchItems". However, despite updating this a ...

Alert: An invalid value of `false` was received for the non-boolean attribute `className`. To properly write this to the DOM, please provide a string instead: className="false" or use a different

While many have tried to address this issue before, none of their solutions seem to work for me... The error I am encountering is: If you want to write it to the DOM, pass a string instead: className="false" or className={value.toString()}. If ...

Reactivity in Vue 3 with globalProperties

When attempting to migrate a Vue 2 plugin to Vue 3, I encountered an issue in the install function. In Vue 2, I had code that looked like this: install(Vue, options) { const reactiveObj = { // ... }; Vue.prototype.$obj = Vue.observable(reactiveO ...

Multiple buttons in a single field

I am attempting to replace a Dropdown list with a series of buttons that will streamline the choices previously displayed by the dropdown list. Specifically, we are using graphic png files for the types of buttons. We experimented with checkboxing and ra ...

I'm looking to add a price ticker to my html webpage. Does anyone know how to do this?

PHP Code <?php $url = "https://www.bitstamp.net/api/ticker/"; $fgc = file_get_contents($url); $json = json_decode($fgc, true); $price = $json["last"]; $high = $json["high"]; $low = $json["low"]; $date = date("m-d-Y - h:i:sa"); $open = $json["open"]; ...

Updating the database with values dynamically using ajax without the need to refresh or change the current page

My current challenge involves adding records to a database table without the need to reload the page. I've implemented ajax for this purpose, but have been receiving an unexpected response (201) from the server (alert("Error occurred !")). Despite spe ...

Can we split the PHP Photo Gallery into a second page after displaying 12 images?

I recently developed a simple PHP photo gallery for my website that pulls data from a MySQL database. By using a while loop, I am able to display three images (from ID 1 to 3) in a single row, continuing this pattern until a total of 12 images are shown. ...

<Select> Placeholder customization

For my react project, I am utilizing material-Ui and I am looking to have a placeholder that stands out by having grey text instead of black when compared to the selected item. <Select name="answer" value={values.answer} onChange={handleChange} onBlur= ...

Leverage information stored in an array within the HandsonTable Angular directive

Some of my columns in a HandsoneTable created using Angular directives are not rendering when I try to use an array as the data source with common array notation (name[0]). I'm unsure if this is supposed to work like this or if I am doing something wr ...

Why is Validators.pattern not functioning in production when it works perfectly in my local development environment for Angular?

Why is Validators.pattern not working in the production environment but functioning fine in my local development setup? I implemented Validators.pattern and '*ngIf="email.errors.pattern"' for email validation on an existing form. Every ...

How to Extract the onClick Event Value from a Table Data (td) Element in C

I'm working on an HTML table with the following code: <table class="window" style="margin-top: 15px; text-align: center;"> <tr id="NavMonth"> <td id="m1" onclick=""> Jan </td> ...

"Exploring the World of ASP.NET VB: A Beginner's Guide to

Attempting to call a web service using JS from an ASP.NET website (VB) client side. Although familiar with web services, setting one up is new territory for me. Looking to implement async updates and queries. Any assistance, examples, or best practices wou ...

Using Google Earth or Cesium to display moving shapes on a map

I'm feeling quite puzzled at the moment and could really use some advice. My goal right now is to achieve a Satellite view of a random building, complete with the typical RoadMap/3D effect found on Google Maps: I also want to incorporate three.js to ...

Is it possible to create a fixed position shader background in three.js?

Trying to incorporate a pixel shader as a background in three.js without affecting the camera rotation with OrbitControls. Most implementations use a 2D plane, but I want it to remain fixed in the scene. Is there a way to achieve this with two separate can ...

What is the best way to replace an image in a div using Angular?

After studying an example of a directive here, I noticed that they used <a href="#" ... to insert a new image into the container div. I attempted to replicate this functionality in my own directive, but clicking on my images does not change the content ...

The issue of asynchronous nested callbacks not functioning properly within each iteration of a for loop in Node.js

I have been using the code snippets below to retrieve followers of a specific user stored in mongodb. Here is an example of a saved user JSON: { "_id":{ "$oid":"5440f606255cd4740e88ed21" }, "username":"test2", "email":"test2%40gmail.com", " ...

My Vue build failed to incorporate the necessary function for outputting the .js file

While functioning properly in development mode, the build process seems to be excluding the setupToken function (from @/api.js) from the app.js output file. // App.vue //... import { setupToken } from '@/api export default { mounted () { this.se ...