React簡易版老虎機

九成Zero發表於2019-02-22

一、碎碎念

一直很忙很少有空寫點東西,難得閒下來,還是記錄下作為懷念。關於React看過文件,很多東西還在摸索中。沒想到來到掘金的第一篇文章既然是關於React的,覺得不錯的點個贊,哪裡需要改進還望各路大大指點!。

二、附錄

三、讀前思考,如下圖換做你需要考慮哪些地方?

React簡易版老虎機

四、實際中至少要注意到以下幾點:

  • 1、使用者是否有資格參與?(抽獎剩餘次數,是否繫結手機號,實名認證等…)

  • 2、點選開始啟動轉盤,同時要做到幾點:

    • 1):禁止使用者再次再次點選開始按鈕
    • 2):剩餘次數要減少一次
    • 3):動畫要由快到慢的緩慢去執行
  • 3、何時停下?(由介面控制如:禮物id),既然由介面控制又會出現:

    • 1):介面正確返回禮物id在客戶端禮物列表中存在,正常邏輯
    • 2):介面正確返回但是禮物id在客戶端列表中不存在
    • 2):介面超時
    • 3):介面返回錯誤
  • 4、如果沒有抽獎限制(只要有次數就能抽獎),至於是先從介面拿要停下的結果還是一邊啟動轉盤同時去拿結果,根據實際應用中適當處理

  • 5、轉盤停止需要一個彈框告訴使用者中了什麼

  • 6、轉盤未停止再次點選需要給使用者提示資訊

  • 7、如果沒資格(沒次數,沒認證…)也需要給使用者提示資訊

五、伴隨著上面的問題簡單分析:這裡只展示部分程式碼

  • 1、初始化元件狀態和部分引數,React中是當前元件的狀態(state)變化就會觸發render重新渲染元件

    this.state = {
        giftList: getGift(),
        // 一圈的總長度,禮物總數量
        stepCount: getGift().length,
        // 剩餘抽獎次數,介面返回
        myCount: 5,
        // 轉動啟用位置預設:1,動態,可設定(>=1&&<=stepCount)
        activeIndex: 1,//這裡從1開始對應陣列的下標0
        // 最終要停下的位置:介面返回(>=1&&<=stepCount)
        endStopIndex: 14,
        // 抽獎是否正在進行中
        isDrawing: false,
        // 轉速   分別為最後0,1,2,3,4,5圈的轉速
        speed: [336, 168, 84, 42, 42, 42],
        // 抽獎結果的禮物名字
        showDialog: false,
        gotGift: null,
        // 訊息提示框
        message: null,
        messageType: null,
        animationName: null,
    };

複製程式碼

2、點選開始獲得停下的位置,需要重置的當前狀態。實際中要:從介面獲取禮物id,根據id獲得對應禮物和要停下的位置(1-18)。其實點選開始的時候就知道獲得哪個禮物了~

    
    let {endStopIndex} = 17;
    let myCount = this.state.myCount - 1;
    // 開啟轉盤,當前抽獎狀態設定為true正在抽獎中,並準備啟動動畫:startRun
    this.setState({isDrawing: true, endStopIndex, myCount}, this.startRun);
    
複製程式碼

3、準備轉動,呼叫只移動一步的方法

    
    startRun() {
        // 總共需要轉的圈數
        let leftRound = this.state.speed.length - 1;
        this.addOneStep({isContinue: true, leftRound})
    }

複製程式碼

4、移動一步的同時需要重置選中狀態,那如何再移動一步?定時器遞迴呼叫該移動一步的方法,注意引數變化(特別是如何讓動畫由快緩慢的變慢),當最後一圈的時候在停在要停的位置。最主要的一部分!


    /*
    * 每次增加一步,滿一圈,總圈數-1同時速度變慢,直到最後一圈停在指定位置
    * 直到知道結果,慢慢變慢速度,停在結果那;
    * 轉盤停到結果值時,重置初始值({isDrawing:false});
    * 
    * Function addOneStep
    * 獎品位置移動一步
    * @isContinue   {Booleans}  是否應該繼續這個定時器
    * @leftRound        {Number}    剩餘幾圈  3代表一個無限大的值,因為還不知道結果
    */
    addOneStep = (params) => {
        let {activeIndex, stepCount, speed} = this.state;
        let {isContinue, leftRound} = params;
        activeIndex += 1;
        if (isContinue) {
            // 如果到超過獎品個數,重置為1
            if (activeIndex > stepCount) {
                console.log(`轉了${leftRound}圈`);
                // 圈數減少的同時轉動的速度要變慢!!!!!!
                leftRound -= 1;
                activeIndex = 1;
            }
            // 如果已經到最後一圈了  且  已經到了指定要中獎的位置了  就不需要繼續了
            if (leftRound === 0 && activeIndex === this.state.endStopIndex) {
                console.log(`現在停在:${this.state.endStopIndex}`);
                isContinue = false;
            }
            this.setState({activeIndex});
            const nextParams = {
                isContinue,
                leftRound,
            };
            this.timer = setTimeout(() => {
                this.addOneStep(nextParams)
            }, speed[leftRound]);//下一次移動的一步的速度
        } else {
            clearTimeout(this.timer);
            this.timer = null;
            let gotGift = this.state.giftList[this.state.endStopIndex - 1];
            this.setState({
                isDrawing: false,
                gotGift,
                showDialog: true,
            });
            this.alertMessage("success")
        }
    }

複製程式碼

5、停下之後抽獎結束,彈框獲得提示資訊告訴使用者中了什麼!

六、友情提示

    1. 有些地方根據實際應用中變化,如禮物個數,開始的位置,轉動速度,轉動圈數等
    1. 鄙人最開始寫的時候動畫由快變慢非常明顯,經高人指點,得出這個有快變慢的緩動效果
    1. DEMO中用了某直播平臺的禮物圖片如有不適請告知。
    1. React質量交流QQ群: 530415177
    1. 前端聯盟小組: https://github.com/jsfront

相關文章