iT邦幫忙

2023 iThome 鐵人賽

DAY 20
0

問題與挑戰

  1. 放下去的時候,因為卡片數增加,需重新微調每張卡片的位置(如果一開始一個蘿蔔一個坑可能會比較好處理,但是無法做到卡片交疊的效果,可能就沒那麼好看,紐時在這裡是把全部卡片展開再重新合上,來過度張數插入的不適感,這涉及到美觀和功能性的平衡)。
  2. 需要判斷卡片是否放在正確的位置,如果不是,則觸發重新排序。

程式碼解釋整理

  • if (!isCurrentAnswerCorrect): 如果答案不正確,則延遲 500 毫秒後觸發重新排序。
  • handleAnimationEnd(): 在動畫結束後,關閉動畫並排序資料。
  • isAnimation: 用於判斷是否正在進行過渡效果,避免干擾。
  • @transitionend="handleAnimationEnd": 在過渡效果結束後,執行 handleAnimationEnd()。

如果資料不正確觸發重新排序


if (!isCurrentAnswerCorrect) {
    setTimeout(() => {
        handleUpdateTimelineTargetPosition(gameStatus.currentStep);
        isAnimation.value = true;
    }, 500);
}

為什麼要使用 setTimeout?我也嘗試使用 Vue 提供的 nextTick 方法,但不會產生過度效果他就更新了。所以為了先讓他畫一次畫面,我使用 setTimeout 處理。

動畫進行中避免再有其他觸發事件干擾過度,使用 isAnimation 判斷是否再進行過度效果,並在 transition 結束時 isAnimation 改為 false 關閉過度效果。

Vue.js 模板

<div
  v-for="(timelineEvent, index) in timelineEvents"
  ...
  :class="isAnimation ? 'transition-transform duration-500' : ''"
  ...
  @transitionend="handleAnimationEnd"
>
  //其他 略 
</div>

動畫效果結束資料排序,並關閉 isAnimation 過度效果

const handleAnimationEnd = () => {
    isAnimation.value = false;
    handleSortedTimelineEvents();
};

因為如果我直接針對 timelineEvents 也就是作答的卡片進行排序,就不會產生過度的效果。所以我是這樣處理這個效果。1. 整理出接下來每張卡片要排序的目標定位,為每一張卡片在 style 上綁定目標訂位,此刻資料本身還是錯誤的排序,但畫面上因為 style 的改變會產生移動的效果。2. 移動到正確位置,瞬間重新排序資料。

更新目標位置的方法

const handleUpdateTimelineTargetPosition = () => {
    const sortedTargetLists = [
        ...timelineEvents.value.map((timelineEvent, index) => {
            return {
                ...timelineEvent,
                transform: timelineEventsStyleRaw.value[index].transform,
                zIndex: index + 10,
            };
        }),
    ].sort((a, b) => a.year - b.year);

    sortedTargetLists.forEach((sortedTargetList, index) => {
        timelineEventsStyleRawAnimationTarget.value[index].transform = sortedTargetList.transform;
        timelineEventsStyleRawAnimationTarget.value[index].zIndex = sortedTargetList.zIndex;
    });
};

目前這就是我使用的方法,但為了控制卡片的位置,我使用了 timelineEventsStyleRaw (原本預設每張卡片的排序位置)和 timelineEventsStyleRawAnimationTarget (暫時性用在動畫效果的排序位置),變得程式可讀性很低,我也正在測試不同改進的可能。

另外也試著使用 gsap 或 Anime.js, Velocity.js 搭配 vue transition hooks,但遇到渲染打架的問題,無法很流暢的執行卡片移動的效果。這個目前還在研究中。也期待之後能讓動畫更順暢。

整理現有解決方案的問題

  • 程式碼可讀性低:使用了 timelineEventsStyleRaw 和 timelineEventsStyleRawAnimationTarget 兩個變數來控制卡片的位置。
  • 動畫效果不流暢:嘗試使用 gsap、Anime.js 和 Velocity.js,但遇到渲染問題。

待改進與研究

  • 正在測試不同的改進方法以提高程式碼的可讀性。
  • 研究如何使用第三方動畫庫(如 gsap、Anime.js、Velocity.js)來實現更流暢的動畫效果。

上一篇
過場動畫製作設計
下一篇
分數回饋與網站分享
系列文
打造紐時風格的時間線小遊戲30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言