Implementing dynamic components in Vuejs by passing props from objects

I have developed a dashboard application that allows users to customize their dashboard by adding widgets in any order. While the functionality is working fine, I am looking to address some technical debt and clean up the code.

Let's simplify things by considering a dashboard that can display two widgets: Clock and Weather. These widgets require data from the dashboard record and can be arranged in any order on the page.

The current setup includes:

data () {
    return {
      widget1: 'Clock',
      widget2: 'Weather',
      widgetData: {
        weather: {
          long: '12.23.34',
          lat: '23.34.45'
        },
        Clock: {
          timeFormat: '24Hour',
          dateFormat: 'US'
         }
      }
    }
}

For rendering them in the HTML:

<component v-bind:is="this.widget1" :widgetData="widgetData"></component>

<component v-bind:is="this.widget2" :widgetData="widgetData"></component>

Now, I want to achieve the following:

<!-- if this.widget1 is Clock then :widgetData should equal widgetData.Clock -->

<component v-bind:is="this.widget1" :widgetData="widgetData.this.widget1"></component>

<!-- if this.widget2 is Weather then :widgetData should equal widgetData.Weather -->

<component v-bind:is="this.widget2" :widgetData="widgetData.this.widget2"></component>

This way, this.widget1 will fill both the :is attribute and navigate into the :widgetData object without passing the entire object to each component.

While my example focuses on two widgets, a real-world scenario could involve up to nine widgets.

I have tried various approaches like:

:widgetData="widgetData.{{this.widget1}}"
:widgetData="widgetData.${this.widget1}"

Any suggestions?

Answer №1

If you're looking for a solution, consider implementing a function that can take the widget type as input and provide the desired data in return.

:widgetData="getWidgetData(this.widget1)"

...

method: {
  getWidgetData(widgetType) {
    if (widgetType == "Clock") {
      return clockData;
    }
    if (widgetType == "Weather") {
      return weatherData;
    }
  }
}

This approach will be particularly beneficial as your system grows more complex than just a simple array structure.

Answer №2

Feeling content with manually coding the numerical values:

:widgetData="widgetData[widget1]"

and similar tasks

Answer №3

Personally, I would approach this situation with a slight adjustment. Instead of directly calling the widget component for each instance, I recommend utilizing the object you have created. For example:

data () {
    return {
      widgetData: {
        Weather: {
          long: '12.23.34',
          lat: '23.34.45'
        },
        Clock: {
          timeFormat: '24Hour',
          dateFormat: 'US'
         }
      }
    }
}

In this setup, the keys in your object represent the widget type and the values hold the corresponding data. You can then loop through this object like so:

<div v-for="(value, key) in widgetData">
  <component :is="key" :widgetData="value" />
</div>

If you prefer to skip the wrapper div, you could also use the component directly:

<component v-for="(value, key) in widgetData" :is="key" :widgetData="value" />

-- If adjusting the order is a requirement, you might want to tweak your data structure slightly. By using an array where the index indicates the desired order of widgets:

data () {
    return {
      widgetData: [
       { type: "Weather",
         data: {
          long: '12.23.34',
          lat: '23.34.45'
        },
        { type: "Clock",
          data: {
          timeFormat: '24Hour',
          dateFormat: 'US'
         }
      }
    ]
}

In this scenario, the component binding would look something like this:

<component v-for="widget in widgetData" :is="widget.type" :widgetData="widget.data" />

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

The technique for handling intricate calls in node.js

My goal is to create a social community where users are rewarded for receiving upvotes or shares on their answers. Additionally, I want to send notifications to users whenever their answers receive some interaction. The process flow is detailed in the com ...

Programming the tab pages within Chrome

By using JavaScript, I successfully opened a new tab at www.blogger.com from the Main.html page. <script> window.open("https://www.blogger.com"); </script> I am now on the blogger page. My goal is to automatically scroll to the end of the bl ...

Storing property data outside of the render method in ReactJS is key for efficient

I have encountered an issue while attempting to map data outside of the render method in my function and return it within the render. The mapping error is causing confusion as I am uncertain about its underlying cause. Below is the function responsible fo ...

Is there a way to duplicate an image a specified number of times depending on a given output value?

As a beginner in coding, I am looking to learn how to dynamically insert multiple images based on input and output values. Currently, my code for basic addition looks like this: <form oninput="x.value=parseInt(a.value)+parseInt(b.value)"> <inpu ...

I am receiving an undefined response from Cheerio when attempting to fetch JSON data

My goal is to create a web scraper and I have successfully downloaded the HTML. Now, with this code snippet, I am attempting to extract the title from my HTML: fs.readFile(__filename.json , function (err, data) { if(err) throw err; const $ = cheerio.load ...

A Nuxt plugin that integrates a separate website into the serverMiddleware

The concept Imagine having a main Nuxt website just like any other. Now, think about adding my module to your project. This module will then introduce a subdomain "admin.example.com" to your project, creating a fully functional Nuxt-based website that ope ...

HTML pages are free from any visible banner ads

There is a file named banners.js function addEvent(object, evName, fnName, cap) { if (object.attachEvent) object.attachEvent("on" + evName, fnName); else if (object.addEventListener) object.addEventListener(evName, fnName, cap); } ...

Determining the top element displayed in a div: A guide

Looking for an answer on how to determine the top visible element while scrolling? You may find some insights in this post: (Check if element is visible after scrolling). My scenario is slightly different - I have a scrollable div containing multiple ele ...

Enhance your Sails.js model by incorporating a custom instance method as a new property

As a JavaScript programmer still learning the ropes, I encountered a challenge while working with Sails.js and creating a model. Here is what I have so far: module.exports = { tableName: 'FOO_TABLE', attributes: { FOO: 'st ...

Generating React components dynamically can bring flexibility and efficiency to the

Looking for a solution to dynamically render different components based on the arguments passed with data. While using regular or React.createElement(Item) works fine, all other options seem to fail. http://jsfiddle.net/zeen/fmhhtk5o/1/ var React = windo ...

The server mistakenly sent the resource as a Stylesheet even though it was interpreted differently

Dear Fellow Coders, Could anyone lend a hand? I encountered this issue on my website after uploading it to my FTP: "Resource interpreted as Stylesheet but transferred with MIME type text/plain" </head> <body> <div class= "navbar navbar ...

Modifying arrays in ReactJS

Having trouble editing my array list, need some help. I can update a single input value successfully, but struggling with updating the entire array. Any suggestions on why the method isn't working and how to edit the array? When I try to store data ...

Stop angular schema form's destroyStrategy from deleting any data

After upgrading my Angular app from version 0.8.2 to 0.8.3 of Angular Schema Form (ASF), a significant bug emerged. The application features multi-page forms that utilize prev/next buttons for navigation. A condition is implemented to display only relevan ...

Using Vuejs to dynamically render a select dropdown based on the initial selection made in the first dropdown menu

I am facing an issue with two drop-down menus. The second menu's choices need to be filtered and displayed based on the selection made in the first drop-down. The RoomID value from the first drop-down is used to filter an array of objects for the seco ...

Tips for transferring information from a parent to a child controller in Angular using the $broadcast method?

I am trying to send an id argument to a child controller using Angular's $broadcast method, but despite my best efforts with the code below, I can't seem to make it work. Any suggestions on what might be incorrect in my implementation? ParentCtr ...

When the parent component in React JS rerenders, the props are not automatically passed down to the child

I have come across similar questions in the past, but I have not found any answers that directly address the issue I am facing in my scenario. In my case, there is a parent component that passes a property to a child component's state. Depending on t ...

Sustain unbroken websocket connection with Discord using Node.js

I've been working on developing a Discord bot using the raw API, but I've encountered an issue where the bot stops functioning after some time. I suspect that this is due to neglecting to maintain the websocket connection. How can I ensure that ...

Get only the text content from a hyperlink using Tinymce-4

Within tinymce.activeEditor, I currently have this line of innerHTML code (part of a ul-list): <li><a href="#">Important words</a></li> When I place the caret within the sentence "Important words," and click a button with the foll ...

React does not accept objects as valid children. If you want to render a group of children, make sure to use an array instead

I am in the process of developing a system for document verification using ReactJS and solidity smart contract. My goal is to showcase the outcome of the get().call() method from my smart contract on the frontend, either through a popup or simply as text d ...

Error: It is not possible to access the 'map' property of an undefined value 0.1

I'm currently experimenting with React.js and I encountered an error that's giving me trouble. I can't seem to pinpoint the root cause of this issue. Shout out to everyone helping out with errors: TypeError: Cannot read property 'map ...