С возвращением в сериал Lottie Animation. В прошлый раз, когда мы говорили о создании анимации с нуля с помощью Adobe After Effects, вы можете наверстать упущенное в Части первой, если еще не читали ее.

В этой части мы собираемся визуализировать нашу анимацию в приложении React Native, а точнее в приложении Expo. Если вы не слышали о Expo, это оболочка над React Native, которая упрощает процесс установки, обрабатывает сборки приложений и предоставляет множество хорошо документированных API.

Визуализация анимации в приложении

Сначала нам нужно скачать Expo XDE и создать новый пустой проект.

После создания проекта мы можем открыть исходный код приложения в редакторе и найти App.js, который должен содержать следующий код:

import React from 'react';
import { StyleSheet, Text, View } from 'react-native';
export default class App extends React.Component {
  render() {
    return (
      <View style={styles.container}>
        <Text>Open up App.js to start working on your app!</Text>
      </View>
    );
  }
}
const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#fff',
    alignItems: 'center',
    justifyContent: 'center',
  },
});

Если вы посмотрите Документацию Expo по импорту Lottie, вы увидите, что это часть их пространства имен DangerZone API из-за того, что Lottie является альфа-функцией, поэтому нам нужно будет импортировать ее оттуда. Добавьте следующие строки в часть импорта App.js:

import { DangerZone } from 'expo';
const { Lottie } = DangerZone;

Теперь, когда Лотти импортирована, мы можем добавить анимацию в проект. Возьмите анимацию, которую мы создали в части 1, и поместите ее в папку с ресурсами в файловой структуре:

Наконец, все, что нам нужно сделать для отображения анимации, - это настроить ее в компонент Lottie, который мы импортировали выше.

import React from 'react';
import { StyleSheet, Text, View } from 'react-native';
import { DangerZone } from 'expo';
const { Lottie } = DangerZone;
export default class App extends React.Component {
componentDidMount() {
  this.animation.play();
}
render() {
    return (
      <View style={styles.container}>
        <Lottie
          ref={animation => { this.animation = animation; }}
          style={{
            width: 60,
            height: 60,
          }}
          source={require('./assets/data.json')}
        />
      </View>
    );
  }
}
const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#000',
    alignItems: 'center',
    justifyContent: 'center',
  },
});

Если вы запустите код в симуляторе iOS (в Expo XDE выберите устройство ›« Открыть в симуляторе iOS »), вы увидите, что анимация воспроизводится, но не позиционируется правильно, и она останавливается после того, как проигрывает полную анимацию один раз.

Чтобы исправить это, давайте зададим ему несколько стилей и добавим свойство цикла в код:

import React from 'react';
import { StyleSheet, Text, View } from 'react-native';
import { DangerZone } from 'expo';
const { Lottie } = DangerZone;
export default class App extends React.Component {
componentDidMount() {
    this.animation.play();
  }
render() {
    return (
      <View style={styles.container}>
        <View style={styles.animationContainer}>
          <Lottie
            ref={animation => { this.animation = animation; }}
            style={styles.animation}
            source={require('./assets/data.json')}
            loop
          />
        </View>
      </View>
    );
  }
}
const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#348bc1',
    justifyContent: 'center',
    alignItems: 'center',
  },
  animationContainer: {
    width: 60,
    height: 60,
  },
  animation: {
    width: 60,
    height: 60,
  },
});

Примечание: в React, если свойство является логическим и истинно, вам не нужно передавать значение (loop = {true}), вы можете просто дать ему свойство цикла.

Теперь вы можете видеть, что у нас есть красивая центрированная анимация, которая зацикливается:

Это базовая реализация импорта анимации Lottie и ее отображения в приложении React Native Expo, но Lottie может делать гораздо больше, и в качестве быстрого примера давайте добавим переключатель в опору цикла, чтобы мы могли запускать / останавливать анимацию. по запросу, по требованию:

import React from 'react';
import { StyleSheet, Text, View, TouchableOpacity } from 'react-native';
import { DangerZone } from 'expo';
const { Lottie } = DangerZone;
export default class App extends React.Component {
state = {
  loop: true,
}
componentDidMount() {
  this.animation.play();
}
toggleLoop() {
  this.setState({ loop: !this.state.loop });
  if (!this.state.loop) {
   this.animation.play();
  }
}
render() {
    return (
      <View style={styles.container}>
        <View style={styles.animationContainer}>
          <Lottie
            ref={animation => { this.animation = animation; }}
            style={styles.animation}
            source={require('./assets/data.json')}
            loop={this.state.loop}
          />
        </View>
        <TouchableOpacity
          onPress={() => this.toggleLoop()}
        >
          <Text>Toggle Loop</Text>
        </TouchableOpacity>
      </View>
    );
  }
}
const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#348bc1',
    justifyContent: 'center',
    alignItems: 'center',
  },
  animationContainer: {
    width: 60,
    height: 60,
  },
  animation: {
    width: 60,
    height: 60,
  },
});

В приведенном выше коде я импортировал компонент TouchableOpacity из библиотеки React Native, которая является одним из компонентов кнопки React Native. Я также установил состояние по умолчанию, установив для свойства loop значение true, поэтому анимация начнется в зацикленном состоянии. Я связал событие TouchableOpacity onPress с функцией toggleLoop (). Это переключит состояние цикла и воспроизведет анимацию, если снова включить.

Итак, вот оно. Мы создали анимацию с нуля и отрендерили ее в мобильном приложении. В следующий раз мы рассмотрим еще несколько дополнительных функций, которые предлагает Lottie. Если вы хотите увидеть что-то конкретное, оставьте комментарий ниже.