【问题标题】:How to change text color of td in Vue conditionally如何有条件地更改Vue中td的文本颜色
【发布时间】:2021-07-21 14:40:43
【问题描述】:

我正在使用这样的 json 文件中的数据:

{"USD": {"7d": 32053.72, "30d": 33194.68, "24h": 31370.42}, "AUD": {"7d": 43134.11, "30d": 44219.00, "24h": 42701.11}, "RUB": {"7d": 2451451.45, "30d": 2465896.74, "24h": 2398589.80},  "JPY": {"7d": 3537735.55, "30d": 3664620.47, "24h": 3472632.46}, "BRL": {"7d": 167555.18, "30d": 169473.27, "24h": 163054.93}, "ILS": {"7d": 108658.72, "30d": 111663.67, "24h": 106988.58}, "GBP": {"7d": 23257.66, "30d": 23838.55, "24h": 22923.17}, "PLN": {"7d": 124869.61, "30d": 127872.57, "24h": 122668.16}, "CAD": {"7d": 40425.62, "30d": 41444.76, "24h": 39827.13}, "EUR": {"7d": 27187.74, "30d": 27955.81, "24h": 26659.79}}

我将其显示在表格中。我计算 7 天和 30 天的百分比变化以及该百分比变化是负数还是正数。如果变化是负面的,我想把文本涂成红色,如果是正面的,我想把它涂成绿色,这就是我检查变化是积极的还是消极的:

 // Checking whether the change is positive or negative
          
          if(item['7d'] > item['30d']) {
            this.isPositive = true
          } else if (item['7d'] < item['30d']) {
           this.isNegative = true
          }

到目前为止,我使用三元运算符的逻辑不起作用,并且我的 td 文本没有变成红色或绿色。为什么以及如何实现这一目标?这是我的完整代码:

<template>
<div>
 <v-data-table
      :headers="headers"
      :items="bitcoinInfo"
      :hide-default-footer="true"
      class="primary"
    >
      <template #item.thirtyDaysDiff="{ item }">
        <td :class="isPositive ? 'positive' : 'negative' ? isNegative : 'negative'">{{ calculateThirtyDayDifference(item) }}%</td>
      </template>
      <template #item.sevenDaysDifference="{ item }">
       <td :class="isPositive ? 'positive' : 'negative' ? isNegative : 'negative'">{{ calculateThirtyDayDifference(item) }}%</td>
      </template>
    </v-data-table>
</div>

</template>

<script>
import axios from 'axios';

  export default {
    data () {
      return {
        bitcoinInfo: [],
        isNegative: false,
        isPositive: false,
        headers: [
          {
            text: 'Currency',
            align: 'start',
            value: 'currency',
          },
          
          { text: '30 Days Ago', value: '30d' },
          { text: '30 Day Diff %', value: 'thirtyDaysDiff'},
          { text: '7 Days Ago', value: '7d' },
          { text: '7 Day Diff %', value: 'sevenDaysDifference' },
          { text: '24 Hours Ago', value: '24h' },
        ],
      }
    },

    methods: {

  
      getBitcoinData() {
        axios
      .get('data.json')
      .then((response => {

      var convertedCollection =  Object.keys(response.data).map(key => {
            return {currency: key, thirtyDaysDiff: 0, sevenDaysDifference: 0,  ...response.data[key]}
          })
          this.bitcoinInfo = convertedCollection
          
      }))
      .catch(err => console.log(err))
        },

       
        calculateThirtyDayDifference(item) {

         
         let calculatedPercent = 100 * Math.abs((item['7d'] - item['30d']) / ((item['7d'] + item['30d']) / 2));

          // Checking whether the change is positive or negative
          
          if(item['7d'] > item['30d']) {
            this.isPositive = true
          } else if (item['7d'] < item['30d']) {
           this.isNegative = true
          }

      return Math.max(Math.round(calculatedPercent * 10) / 10, 2.8).toFixed(2);
       },

       calculateSevenDayDifference(item) {

         let calculatedPercent = 100 * Math.abs((item['24h'] - item['7d']) / ((item['24h'] + item['7d']) / 2));
      return Math.max(Math.round(calculatedPercent * 10) / 10, 2.8).toFixed(2);
       }
      },
        
      mounted() {
        this.getBitcoinData()
      }
  }

</script>

<style>
.negative {
  color: red;
}

.positive {
  color: green;
}

</style>

【问题讨论】:

    标签: javascript vue.js vuetify.js


    【解决方案1】:

    你的代码有很多问题,我什至不知道要开始......

    1. 您以错误的方式使用Conditional (ternary) operator。它的形式为condition ? expression_for_true : expression_for_false

    2. 在模板中使用方法calculateThirtyDayDifference,同时它改变了一些数据(isNegative 和isPositive)。 千万不要这样做!这会导致无限渲染循环。

    在大多数情况下,您不需要从模板中调用任何method - 因为模板被多次渲染,所以效率非常低。如果您有一些数据并且需要导出更多数据(计算一些东西),那么更好的解决方案是使用 computed 并提前准备所有您需要的数据

    1. v-data-table (docs) 的项目槽已呈现 &lt;td&gt;,因此您的代码将在 td 内呈现 td - 例如改用 span

    const data = JSON.parse('{"USD": {"7d": 32053.72, "30d": 33194.68, "24h": 31370.42}, "AUD": {"7d": 43134.11, "30d": 44219.00, "24h": 42701.11}, "RUB": {"7d": 2451451.45, "30d": 2465896.74, "24h": 2398589.80},  "JPY": {"7d": 3537735.55, "30d": 3664620.47, "24h": 3472632.46}, "BRL": {"7d": 167555.18, "30d": 169473.27, "24h": 163054.93}, "ILS": {"7d": 108658.72, "30d": 111663.67, "24h": 106988.58}, "GBP": {"7d": 23257.66, "30d": 23838.55, "24h": 22923.17}, "PLN": {"7d": 124869.61, "30d": 127872.57, "24h": 122668.16}, "CAD": {"7d": 40425.62, "30d": 41444.76, "24h": 39827.13}, "EUR": {"7d": 27187.74, "30d": 27955.81, "24h": 26659.79}}')
    
    new Vue({
      el: '#app',
      vuetify: new Vuetify(),
      template: `
      <v-app>
        <v-main>
          <v-container>
            <v-data-table :headers="headers" :items="rowsToDisplay" :hide-default-footer="true" class="elevation-1">
              <template #item.thirtyDaysDiff="{ item }">
                <span :class="item.thirtyDaysDiffClass">{{ item.thirtyDaysDiff }}%</span>
              </template>
              <template #item.sevenDaysDiff="{ item }">
                <span :class="item.sevenDaysDiffClass">{{ item.sevenDaysDiff }}%</span>
              </template>
            </v-data-table>
          </v-container>
        </v-main>
      </v-app>
      `,
      data() {
        return {
          bitcoinInfo: data,
          headers: [{
              text: 'Currency',
              align: 'start',
              value: 'currency',
            },
    
            {
              text: '30 Days Ago',
              value: '30d'
            },
            {
              text: '30 Day Diff %',
              value: 'thirtyDaysDiff'
            },
            {
              text: '7 Days Ago',
              value: '7d'
            },
            {
              text: '7 Day Diff %',
              value: 'sevenDaysDiff'
            },
            {
              text: '24 Hours Ago',
              value: '24h'
            },
          ],
        }
      },
      methods: {
        calculateDifference(a, b) {
          let calculatedPercent = 100 * Math.abs((a - b) / ((a + b) / 2));
          return Math.max(Math.round(calculatedPercent * 10) / 10, 2.8).toFixed(2);
        },
        getDiffClass(a, b) {
          return a > b ? 'positive' : a < b ? 'negative' : ''
        }
      },
      computed: {
        rowsToDisplay() {
          return Object.keys(this.bitcoinInfo)
            .map(key => {
              return {
                currency: key,
                ...data[key]
              }
            }).map((item) => ({
              ...item,
              thirtyDaysDiff: this.calculateDifference(item['7d'], item['30d']),
              thirtyDaysDiffClass: this.getDiffClass(item['7d'], item['30d']),
              sevenDaysDiff: this.calculateDifference(item['24h'], item['7d']),
              sevenDaysDiffClass: this.getDiffClass(item['24h'], item['7d']),
            }))
        }
      }
    })
    .negative {
      color: red;
    }
    
    .positive {
      color: green;
    }
    <link href="https://fonts.googleapis.com/css?family=Roboto:100,300,400,500,700,900" rel="stylesheet">
    <link href="https://cdn.jsdelivr.net/npm/@mdi/font@4.x/css/materialdesignicons.min.css" rel="stylesheet">
    <link href="https://cdn.jsdelivr.net/npm/vuetify@2.x/dist/vuetify.min.css" rel="stylesheet">
    
    <script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.6.14/vue.js"></script>
    <script src="https://cdn.jsdelivr.net/npm/vuetify@2.x/dist/vuetify.js"></script>
    
    <div id="app">  
    </div>

    【讨论】:

      【解决方案2】:

      尝试改变:

      :class="isPositive ? 'positive' : 'negative' ? isNegative : 'negative'"
      

      到:

      :class="isPositive ? 'positive' : 'negative'"
      

      和:

      if(item['7d'] > item['30d']) {
        this.isPositive = true
      } else {
        this.isPositive = false
      }
      

      【讨论】:

      • 颜色现在改变了,但如果item['7d'] &gt; item['30d'] 不正确并且item['7d'] &lt; item['30d'] 然后我的数据停止加载,我得到have an infinite update loop in a component render function
      猜你喜欢
      • 2019-07-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-09-15
      • 1970-01-01
      • 2020-04-08
      • 2016-12-12
      • 1970-01-01
      相关资源
      最近更新 更多