Steer clear of duplicating patterns in vue templates

I have a significant issue with a component that needs to be repeated multiple times in the parent template due to the usage of v-if. The component code is as follows:

<SelectCard
  v-for="(channel, index) in category.visibleChannels"
  :key="index + '-' + channel.id"
  :channel="channel"
  :channel-selected="isSelected(channel.id)"
  :read-more-details="channelInfoDetails"
  @select="onAddChannel"
  @deselect="onRemoveChannel"
  @read-more-changed="setChannelInfoDetails"
/>

The only variation between each render of the template is the array that I loop over.... Here is a simplified version of the problem:

<template>
<div
    ref="channels"
    class="channels"
  >
    <div v-if="showCategories">
      <div
        v-for="category in sliderCategories"
        :key="category.name"
      >
        <h3 v-text="category.name" />
        <div
          v-if="category.showAll"
          class="channel-list show-all"
          :class="channelListSize"
        >
          <ul>
            <SelectCard looping over category.contents  />
          </ul>
        </div>
        <ChannelSlider
          v-else
          :category="category"
          @visible-updated="setVisibleChannels"
        >
          <SelectCard looping over category.visibleChannels  />
        </ChannelSlider>
        <div class="show-all-link">
          <a
            :class="category.showAll?'arrow-up':'arrow-down'"
            class="link"
            @keyup.enter="toggleShowAll(category.name, !category.showAll)"
            @click="toggleShowAll(category.name, !category.showAll)"
            v-text="showAllText(category.showAll)"
          />
        </div>
      </div>
    </div>
    <div v-else>
      <div v-if="showNoSearchResult">
        <SomeComponent with some props/>
      </div>
      <div :class="channelListSize" class="channel-list">
        <ul>
          <SelectCard looping over updatedChannels  />
        </ul>
      </div>
    </div>
    <div
      ref="someref"
      class="someClass"
      :style="{top: channelInfoDetails.top + 'px', position: 'absolute'}"
    >
      <AnotherComponent with some props/>
    </div>
  </div>
</template>

As a result of numerous props in SelectCard code, my template has become extensive.

I am looking for a way to encapsulate SelectCard in a method within the parent code so that I can easily call a function with the desired array. Are there any alternative solutions that could help address this issue?

Answer №1

It seems like finding a simple solution here might be a bit challenging, but there are some options to consider.

One option is to streamline the code by using the object form of v-bind and v-on. You would need to create a method to return the object since your props depend on channel and index. This approach may reduce the code slightly, although it could sacrifice clarity. Another possibility is utilizing the object form of the is attribute.

Alternatively, you could introduce another component and utilize slots for the SelectCard. By doing this, you can pass the SelectCard in as the slot contents and use a computed property to make the array dynamic. One drawback of this approach is the potential complexity of passing data between components.

Another option to explore is converting everything into a render function. While this allows you to achieve what you want without using a template, it may require sacrificing the simplicity of a template depending on the overall complexity of your project.

Answer №2

To consolidate all the logic of the v-if statements, create a computed property that will determine the correct array to pass as props to the SelectCard component. You can achieve this by implementing something similar to the following:

<SelectCard :arr="dataArray"/>
...
computed: {
       dataArray(){
           if (ConditionA){ return Array_A}
           if ....
    }

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

Deactivate "When the viewModel attribute holds the phrase 'some text'"

I came across this answer on Stack Overflow regarding checking for a value in Knockout, but it seems to be outdated. I am attempting to achieve something like this: <li> <span data-bind="text: Subject"></span> <!-- ko if: Subjec ...

Tips for creating a custom axios response depending on the error code returned by the response

I am currently working on implementing a global error handling system in my Vue application. Within my project, I have an api.service.js file that contains the necessary code for Axios setup and various HTTP request functions such as get and post: /** * S ...

javascript close the current browser tab

Can someone please help me with a JavaScript code to close the current window? I have tried the following code but it does not seem to work: <input type="button" class="btn btn-success" style="font-weight: b ...

What are some creative ways to customize v-slot:cell templates?

Currently, I have the following code snippet within a table: <template v-slot:cell(checkbox)="row" style="border-left='5px dotted blue'"> <input type="checkbox" v-model="row.rowSelected" @input="toggleS ...

Evaluating TypeError in CoffeeScript using Jasmine with Backbone.js

Currently, I am following the PeepCode video tutorial on Backbone.js, but I am rewriting all the code in CoffeeScript instead of plain JavaScript. Everything is going well so far, except when I attempt to run Jasmine tests on the code, I encounter some Ty ...

Javascript's asynchronous initiator

Starting a variable synchronously has been a common practice. const x = call_a_sync_function(); However, issues arise when the initiator switches to async. const x = await call_an_async_function(); // SyntaxError: Unexpected reserved word I experimente ...

Enable Sound when Hovering over Video in React Next.js

I am currently facing an issue while trying to incorporate a short video within my nextjs page using the HTML tag. The video starts off muted and I want it to play sound when hovered over. Despite my best efforts, I can't seem to get it working prope ...

Regular expression in JavaScript that specifically matches numbers formatted in the style of JavaScript

My goal is to develop a javascript regular expression that specifically identifies valid Javascript-style numbers. The requirements entail accommodating an optional minus or plus sign before the number, recognizing the decimal dot, and supporting exponent ...

Struggling with my jQuery Ajax call, need some help

I am attempting to create an ajax request that will update the content of my select element. Below is the code for my request : $(function() { $("#client").change(function() { type: 'GET', url: "jsonContacts. ...

The object[] | object[] type does not have a call signature for the methods 'find()' and 'foreach()'

Here are two array variables with the following structure: export interface IShop { name: string, id: number, type: string, } export interface IHotel { name: string, id: number, rooms: number, } The TypeScript code is as shown below ...

Making an AJAX call to a PHP script to add data

Could you assist me in understanding why my code is resulting in a double insert? I have a JavaScript function that makes an AJAX request to a save.php file to insert data into a database. However, each time I submit it, it performs the insertion twice, al ...

Guide to center align fields in Ionic and Angular

I am working on creating a login screen that resembles the image provided. I have managed to set the background image, input fields, and buttons successfully. However, I am encountering a few issues: The width of my input field is taking up the entire spa ...

Unknown and void

undefined === null => false undefined == null => true I pondered the logic behind undefined == null and realized only one scenario: if(document.getElementById() == null) .... Are there any other reasons why (undefined === null) ...

What is the best way to ensure that any modifications made to an item in a table are appropriately synced

Utilizing xeditable.js, I am able to dynamically update the content of a cell within a table. My goal is to capture these changes and send them via an HTTP request (PUT) to the backend in order to update the database. Below is the table that can be edited ...

Fill every empty element with elements from another array

I'm struggling to grasp the concept of arrays. I have two arrays and I want to replace the null elements in one with the elements from the other. Here is what I have currently: var arr1 = [1,2,3,4] var arr2 = [null, 99, null, null] arr2.map((item) = ...

The website no longer uses AJAX calls and does not display any errors, although it used to do so in the past

I've noticed that my website is no longer making the ajax call it used to make before I made some changes to my code. However, I can't seem to figure out what exactly I changed. The function call appears to be correct as it triggers the initial a ...

What is the importance of utilizing clearInterval to restart the timer in ReactJS?

Consider the code snippet provided below: useEffect(() => { const interval = setInterval(() => { setSeconds(seconds => seconds + 1); }, 1000); return () => clearInterval(interval); }, []); What is the purpose of returning ...

I am struggling to see any results display when using the v-for directive in my Vue.js project

I've developed an application where users can leave comments on each other's profile pages, but I'm encountering issues with displaying these comments. Despite using v-for, the output on the screen shows {{ comment.from }} and {{ content.fro ...

Transfer the imageURI to a different HTML page

My mobile app, created using PhoneGap, allows users to select an image from their album. I want to pass that selected image and display it on another HTML page. Does anyone have any suggestions on how to achieve this? Below is the code snippet: selectImag ...

Preventing Excessive Event Triggering in a PhoneGap - Jquerymobile Application

I've created an application using a combination of Phonegap and JqueryMobile. So far, this app has accumulated approximately 15,000 downloads across iOS, Android, and iPhone platforms. Surprisingly, the code remains consistent across all versions. P ...