Dimension.get(‘window’).ширина в React Native в соответствии с ориентацией заставки, а не текущей ориентацией?

#ios #ipad #react-native-android

#iOS #iPad #react-native

Вопрос:

Я адаптирую приложение React Native с iPhone на iPad и сталкиваюсь со странной проблемой. Я подозреваю ошибку с RN. Когда пользователь находится в альбомном режиме и запускает приложение, у него будет заставка в альбомном режиме, и с этим проблем нет. Но приложение продолжает распознавать Dimensions.get('window').width ширину ландшафтного режима даже после того, как я заблокировал экран в портретном режиме.

Структура моего приложения выглядит следующим образом. Материнский компонент приложения имеет код, который блокирует приложение в портретном режиме, например, так:

 var Orientation = require('react-native').NativeModules.Orientation;

componentWillMount(){
    Orientation.lockToPortrait();
}

  

Из этого начального компонента другие компоненты загружаются через маршрутизатор react-native-router-flux . Внутри этих компонентов пользовательского интерфейса компоненты были оформлены с использованием API React Native Dimensions. вот так:

 <View style={{ width: Dimensions.get('window').width - 10}} />
  

Это отлично работает на iPhone, потому что iPhone всегда находится в портретном режиме во время запуска приложения. Но на iPad, когда экран пользователя находится в альбомном режиме (во время запуска приложения), все приложение выглядит странно, потому что RN преобразует высоту экрана в ширину экрана. Когда пользователь запускает приложение в портретном режиме, та же проблема не возникнет. Этого не должно происходить, поскольку Dimensions.get('window').width вызываются сразу после того, как приложение уже заблокировано в портретном режиме. Для меня это не имеет смысла…

К сожалению, мне действительно нужно иметь возможность также использовать альбомный режим, поскольку на некоторых экранах я заставляю пользователя переключаться в альбомный режим, выполняя Orientation.lockToLandscape()

Есть какие-либо решения этой проблемы?

Ответ №1:

Я придумал способ, позволяющий быстро заставить мое приложение работать, но я не думаю, что это лучший метод. Я в основном измеряю экран, чтобы узнать, в какой ориентации заблокировано мое приложение. Вот так:

 const getWidth = (percentage: number) => {
  if (Dimensions.get('window').width > Dimensions.get('window').height) {
    return (Dimensions.get('window').height * percentage) / 100;
  }
  return (Dimensions.get('window').width * percentage) / 100;
};

const getHeight = (percentage: number) => {
  if (Dimensions.get('window').width > Dimensions.get('window').height) {
    return (Dimensions.get('window').width * percentage) / 100;
  }
  return (Dimensions.get('window').height * percentage) / 100;
};
  

После этого я могу создавать объекты Stylesheet.create(), которые адаптируются к ориентации экрана. Вот так:

 StyleSheet.create({
fullWidth: {
    width: getWidth(100) - 60,
  }
})
  

вместо:

 StyleSheet.create({
fullWidth: {
    width: Dimensions.get('window').width - 60,
  }
})
  

Ответ №2:

Я использовал это обходное решение, основанное на ответе педросимао:

    Dimensions.addEventListener('change', e => {
  const{width,height}=(e.window)

  const getHeight = (percentage) => {
    if (width > height) {

      this.setState({orientation:'landscape'})
      return ((height * percentage) / 100)
    }else{

      this.setState({orientation:'portrait'})
    }


    return height
  }
  this.setState({width:width,height:height,height2:getHeight(50)})
});
  

конечно, это не сработает, если вы не измените ориентацию хотя бы один раз.
Вы должны использовать некоторое начальное состояние, подобное этому:

          this.state={
           height2:   (Dimensions.get('window').height>Dimensions.get('window').width) ? Dimensions.get('window').height :(Dimensions.get('window').height*50)/100  ,


  }
  

Комментарии:

1. Для последнего вырезанного вы должны сделать что-то вроде этого вместо этого: Math.max(Dimensions.get(‘window’).height, Dimensions.get(‘window’).width);