Как сделать Слайдер, который обновляется на основе прогресса анимации Lott ie (React-Native) - PullRequest
1 голос
/ 25 марта 2020

Я пытаюсь заставить ползунок обновить свою позицию, основываясь на значении прогресса анимации Лотта ie. Ползунок может контролировать прогресс Lott ie, но он не обновляет свою позицию, если я нажимаю кнопку «Play Lott ie». Как я могу получить доступ компонентов к значению Прогресса Lott ie и обновлять его в зависимости от значения Прогресса? Я хочу, чтобы это значение было опубликовано c или доступно из других компонентов. Кажется, что значение Progress недоступно внешним компонентам. Я попытался добавить addListener, но он ничего не делает. Я новичок в реакции-родной и кодирования в целом. Я осматривал StackOverflow в течение многих дней и ничего не смог найти.

export default class HomeScreen extends React.Component {
    constructor(props) {
        super(props);
        this.playLottie.bind(this);
        this.playLottie.bind(this);
        this.pauseLottie.bind(this);
        this.state = {
            progress: new Animated.Value(0),
            pausedProgress: 0
        };
        this.state.progress.addListener(({ value }) => this._value = value); // I tried to use a Listener so that components can Listen to the Progress of the lottie animation...
    }

    playLottie = () => {
        Animated.timing(this.state.progress, {
            toValue: 1,
            easing: Easing.linear,

        }).start;
    }

    //Shows real-time value of the Slider. Console output works too, updates when I use slider in realtime.
    realProgress = (value) => {
        console.log("realProgress", value);
        this.setState({ pausedProgress: value });
    };

    //Used by Slider, sets Progress of Lottie
    setProgress = (value) => {
        this.state.progress.setValue(value);
        console.log("setProgress", value)
    };

    render() {
        return (

            <View style={styles.container}>
                <ScrollView style={styles.container} contentContainerStyle={styles.contentContainer}>
                //The Lottie Animation:
                <LottieView
                        ref={animation => { this.animation = animation; }}
                        source={require('../assets/lottie-animations/animation.json')}
                        style={{ height: 400, width: '100%' }}
                        loop={false}
                        progress={this.state.progress}
                />

                <Button
                    onPress={this.playLottie}
                    title="Play Lottie"
                />
                <Button
                    onPress={this.pauseLottie}
                    title="Pause Lottie"
                    />

                //The slider that controls the progress of the Lottie Animation:
                <Slider
                    style={{ width: '100%', height: 40 }}
                    minimumValue={0}
                    maximumValue={1}
                    onValueChange={(value) => this.setProgress(value)}
                />

                //Tried using Text to display the real-time value of the Lottie animation progress. Doesn't display any numbers.
                <Text>{'Slider Position: '}{Slider.onValueChange}</Text>

                </ScrollView>
            </View>

        );
    }
}

Соответствующие зависимости:

"dependencies": {
    "expo": "~36.0.0",
    "lottie-react-native": "^3.3.2",
    "react": "~16.9.0",
    "react-lottie": "^1.2.3",
    "react-native": "https://github.com/expo/react-native/archive/sdk-36.0.0.tar.gz",
  },

Экспо версия: 3.13.8 Windows 10

1 Ответ

0 голосов
/ 27 марта 2020

Использовать императивный API намного проще.

Конструктор

  constructor(props) {
    super(props);

    this.state = {
      progress: 0,
    }
  }

Используйте компонентDidMount для тестирования. play(startFrame, EndFrame). Вам необходимо узнать номер конечного кадра анимации для использования с ползунком. Продолжайте изменять конечный кадр до тех пор, пока он не будет воспроизведен до конца - это ваш номер.

  componentDidMount() {
    // Or set a specific startFrame and endFrame with:
    // this.animation.play(0, 100);
  }

Функция стрелки, которая возвращает значение и изменяет состояние прогресса. Вы можете установить частоту кадров анимации для запуска и остановки на одном кадре.

  animateIt = (value) => {
    //this.animation.reset();
    this.setState({progress: value})
    this.animation.play(value, value);
  }

Ваш лот ie компонент

  <LottieView
    ref={animation => {
      this.animation = animation;
    }}
    style={{ height: 400, width: '100%' }}
    source={require('../assets/lottie-animations/animation.json')}
  />

Ваш ползунок устанавливает максимальное значение равным последнему кадр анимации. В моем случае это было 40. Также ползунок вызывает функцию стрелки и возвращает значение.

  <Slider
      style={{ width: '100%', height: 40 }}
      minimumValue={0}
      maximumValue={40}
      onValueChange={(value) => this.animateIt(value)}
  />
...