首頁  >  問答  >  主體

在Vuejs中,當元素被點擊時,切換元素的類別(或更改樣式)

我取得資料的方式有點複雜。我有“tweets”數組,其中存儲數據,每條推文都是一張卡片,單擊卡片時我成功地更改了樣式(markTweet 函數),但每條推文也有回复,顯示與推文相同(每個回覆都有自己的回覆)卡片)。我從伺服器取得資料的方式:

let replies = []
for(const tweet of tweets) {
    let reply = await SQL('SELECT * FROM tweet_replies WHERE tweet_replies.conversation_id = ?', tweet.tweet_id)
    replies.push(reply)
}
    
const data = {
    tweets: tweets,
    page: parseInt(currentPage),
    numberOfPages: arr,
    replies
}

然後我在 vue 中有元件。您可以看到回覆儲存在每條推文中的 tweets 陣列中,作為 tweetReplies。 在markReply函數中,我成功地將id加入到陣列中。

<template>
  <div class="container-full">
    <div class="tweets-container">
      <div
        v-for="(tweet, i) in tweets"
        :key="tweet.id"
      >
        <div
          class="tweet-card"
          :class="{ selected: tweet.isSelected }"
          @click="markTweet(tweet.tweet_id, i)"
        >
          <div class="text">
            <p
              v-html="tweet.tweet_text"
            >
              {{ tweet.tweet_text }}
            </p>
          </div>
        </div>
        <div class="replies">
          <div
            v-for="(reply, index) in tweet.tweetReplies"
            :key="reply.tweet_id"
            @click="markReply(reply.tweet_id, index)"
          >
            <div class="tweet-card tweet-reply">
              <div class="text">
                <p>
                  {{ reply.tweet_text }}
                </p>
              </div>
            </div>
          </div>
        </div>
      </div>
    </div>
  </div>
</template>

<script>
import axios from 'axios'
import { getUserToken } from '@/auth/auth'
import moment from 'moment'
import { BFormTextarea, BButton, BFormSelect } from 'bootstrap-vue'

export default {
  components: { BFormTextarea, BButton, BFormSelect },
  data() {
    return {
      tweets: [],
      tweetActionIds: [],
      categories: [],
    }
  },
  beforeMount() {
    this.getTweets()
  },
  methods: {
    getTweets() {
      this.tweets = []
      const API_URL = `${this.$server}/api/twitter/tweets`

      const params = {
        token: getUserToken(),
        page: this.$route.query.page,
        newCurrentPage: newCurrent,
      }
      axios.post(API_URL, null, { params }).then(res => {
        this.currentPage = res.data.page
        this.numberOfPages = res.data.numberOfPages

        if (res.data) {
          res.data.tweets.forEach(tweet => {
            const tweetData = {
              id: tweet.id,
              tweet_id: tweet.tweet_id,
              tweet_text: htmlText,
              tweet_text_en: htmlTextEn,
              twitter_name: tweet.twitter_name,
              twitter_username: tweet.twitter_username,
              added_at: moment(String(tweet.added_at)).format(
                'MM/DD/YYYY hh:mm',
              ),
              URL: tweet.URL,
              isSelected: false,
              tweetReplies: [],
            }
            this.tweets.push(tweetData)
          })
          res.data.replies.forEach(reply => {
            reply.forEach(r => {
              this.tweets.forEach(tweet => {
                if (tweet.tweet_id === r.conversation_id) {
                  tweet.tweetReplies.push(r)
                }
              })
            })
          })
        }
      })
    },
    markTweet(tweetId, i) {
      const idIndex = this.tweetActionIds.indexOf(tweetId)
      this.tweets[i].isSelected = !this.tweets[i].isSelected
      if (this.tweetActionIds.includes(tweetId)) {
        this.tweetActionIds.splice(idIndex, 1)
      } else {
        this.tweetActionIds.push(tweetId)
      }
    },
    markReply(replyId) {
      const idIndex = this.tweetActionIds.indexOf(replyId)
      if (this.tweetActionIds.includes(replyId)) {
        this.tweetActionIds.splice(idIndex, 1)
      } else {
        this.tweetActionIds.push(replyId)
      }
    },
  },
}
</script>

我嘗試在資料中新增replySelected ,然後當在markReply 中觸發點擊時,我將replySelected 更改為true,但隨後選擇了推文的每個回复,這不是我想要的。

P粉029327711P粉029327711189 天前402

全部回覆(2)我來回復

  • P粉024986150

    P粉0249861502024-04-01 15:42:07

    您可以在Nikola 的答案的基礎上構建,只需檢查它是否在tweetActionIds 數組中,即可繞過向每條推文添加isSelected 的額外步驟,然後執行相同的操作並透過回覆保持乾淨

    {{ tweet.tweet_text }}

    {{ reply.tweet_text }}

    {{tweetActionIds}}
    const app = Vue.createApp({
      data() {
        return {
          tweets: []
          tweetActionIds: [],
          categories: [],
        }
      },
      methods: {
        markTweet(tweetId, i) {
          const idIndex = this.tweetActionIds.indexOf(tweetId)
          if (this.tweetActionIds.includes(tweetId)) {
            this.tweetActionIds.splice(idIndex, 1)
          } else {
            this.tweetActionIds.push(tweetId)
          }
        },
        markReply(replyId) {
          const idIndex = this.tweetActionIds.indexOf(replyId)
          if (this.tweetActionIds.includes(replyId)) {
            this.tweetActionIds.splice(idIndex, 1)
          } else {
            this.tweetActionIds.push(replyId)
          }
        },
        isSelected(tweet) {
          return this.tweetActionIds.includes(tweet.tweet_id);
        }
      },
    })

    回覆
    0
  • P粉245003607

    P粉2450036072024-04-01 10:49:56

    如果我理解正確,請嘗試以下程式碼片段:

    const app = Vue.createApp({
      data() {
        return {
          tweets: [{id: 1, tweet_id: 1, isSelected: true, tweet_text: 'aaa', tweetReplies: [{tweet_id: 11, tweet_text: 'bbb'}, {tweet_id: 12, tweet_text: 'ccc'}]}, {id: 2, tweet_id: 2, isSelected: false, tweet_text: 'ddd', tweetReplies: [{tweet_id: 21, tweet_text: 'eee'}, {tweet_id: 22, tweet_text: 'fff'}]}],
          tweetActionIds: [],
        }
      },
      methods: {
        markTweet(tweetId, i) {
          const idIndex = this.tweetActionIds.indexOf(tweetId)
          this.tweets[i].isSelected = !this.tweets[i].isSelected
          if (this.tweetActionIds.includes(tweetId)) {
            this.tweetActionIds.splice(idIndex, 1)
          } else {
            this.tweetActionIds.push(tweetId)
          }
        },
        markReply(replyId) {
          const idIndex = this.tweetActionIds.indexOf(replyId)
          if (this.tweetActionIds.includes(replyId)) {
            this.tweetActionIds.splice(idIndex, 1)
          } else {
            this.tweetActionIds.push(replyId)
          }
        },
        checkReply(r) {
          return this.tweetActionIds.includes(r) ? true : false
        }
      },
    })
    
    app.mount('#demo')
    .selected {color: red;}
    sssccc
    

    {{ tweet.tweet_text }}

    {{ reply.tweet_text }}

    {{tweetActionIds}}

    回覆
    0
  • 取消回覆