反应本机自适应字体大小


91

我想问一下如何处理本机句柄或做响应字体。例如,在iphone 4s中,我的fontSize:14,而在iphone 6中,我的fontSize:18。


19
如果有人正在寻找一种完全禁用字体缩放的方法,请使用Text.defaultProps.allowFontScaling=false
CoderDave

1
@CoderDave,这太棒了!
Abdo

如果您要基于屏幕大小而不是确切的fontSize来使用相对fontSize,可以尝试npmjs.com/package/react-native-response-dimensions,它将根据设备的screenSize自动调整字体大小
Dani Akash

Answers:


97

您可以使用PixelRatio

例如:

var React = require('react-native');

var {StyleSheet, PixelRatio} = React;

var FONT_BACK_LABEL   = 18;

if (PixelRatio.get() <= 2) {
  FONT_BACK_LABEL = 14;
}

var styles = StyleSheet.create({
  label: {
    fontSize: FONT_BACK_LABEL
  }
});

编辑:

另一个例子:

import { Dimensions, Platform, PixelRatio } from 'react-native';

const {
  width: SCREEN_WIDTH,
  height: SCREEN_HEIGHT,
} = Dimensions.get('window');

// based on iphone 5s's scale
const scale = SCREEN_WIDTH / 320;

export function normalize(size) {
  const newSize = size * scale 
  if (Platform.OS === 'ios') {
    return Math.round(PixelRatio.roundToNearestPixel(newSize))
  } else {
    return Math.round(PixelRatio.roundToNearestPixel(newSize)) - 2
  }
}

用法:

fontSize: normalize(24)

您可以<Text />通过按预先定义的尺寸在每个组件上使用尺寸来进一步向前迈进。

例:

const styles = {
  mini: {
    fontSize: normalize(12),
  },
  small: {
    fontSize: normalize(15),
  },
  medium: {
    fontSize: normalize(17),
  },
  large: {
    fontSize: normalize(20),
  },
  xlarge: {
    fontSize: normalize(24),
  },
};

22
您在哪里使用了const量表?
Jan Franz Palngipang '17

2
这似乎无能为力。迷你总是=== 12
A.com

14
对于非iOS设备,为什么要减去2?
Parth Tamane

51

我们使用编写的简单,直接,可扩展的utils函数:

import { Dimensions } from 'react-native';
const { width, height } = Dimensions.get('window');

//Guideline sizes are based on standard ~5" screen mobile device
const guidelineBaseWidth = 350;
const guidelineBaseHeight = 680;

const scale = size => width / guidelineBaseWidth * size;
const verticalScale = size => height / guidelineBaseHeight * size;
const moderateScale = (size, factor = 0.5) => size + ( scale(size) - size ) * factor;

export {scale, verticalScale, moderateScale};

为您节省很多时间来做很多事。您可以在我的博客文章中了解更多信息


编辑:我认为将这些功能提取到自己的npm包中可能会有所帮助,我也将其包含ScaledSheet在该包中,该包是的自动缩放版本StyleSheet。您可以在这里找到它:react-native-size-matters


谢谢,使用此实用程序的最佳方案是什么?我的意思是在哪里使用scale,verticaleScale和mediumScale?
Pir Shukarullah Shah,

4
由于imo缩放比例不应该是线性的,因此我几乎在需要缩放的所有内容(例如fontSize,页边距,图像和Svg大小)上都使用mediumScale,因为imo缩放比例不是线性的,但这是个人喜好问题。如果您想获得线性结果,则主要使用比例尺,并在诸如容器高度之类的东西上使用verticalScale。
nirsky

16

因为当前反应式单位不提供响应式单位,所以我想您最好的选择是检测屏幕尺寸,然后用其推断设备类型并有条件地设置fontSize。

您可以编写类似以下的模块:

function fontSizer (screenWidth) {
  if(screenWidth > 400){
    return 18;
  }else if(screenWidth > 250){
    return 14;
  }else { 
    return 12;
  }
}

您只需要查询每个设备的默认宽度和高度即可。如果在设备更改方向时宽度和高度发生了翻转,您可能可以使用宽高比来代替,或者只是找出两个维度中较小的一个来确定宽度。

模块这一个可以帮你找到设备的尺寸或设备类型。


我已经安装了反应,本机设备,但它给我的“无法解析模块尺寸”的错误,当我运行的应用程序
悉尼Loteria

听起来您需要确保为模块使用正确的RN版本
Isaac Madwed 2015年

我正在使用最新版本的React Native :)我认为当前不支持它?
悉尼Loteria 2015年

可能...也许尝试删除您的node_modules文件夹并重新npm install
Isaac Madwed 2015年

6

看看我写的图书馆:https : //github.com/tachyons-css/react-native-style-tachyons

它允许您rem在启动时指定root-fontSize(),您可以使其与您的PixelRatio设备特性或其他设备特性相关。

然后,您将获得相对于您的样式rem,不仅是fontSize,而且还有填充等。

<Text style={[s.f5, s.pa2, s.tc]}>
     Something
</Text>

扩充内容:

  • f5始终是您的基本字体
  • pa2 给您相对于基本字体大小的填充。

5

我只使用屏幕尺寸的比例,对我来说效果很好。

const { width, height } = Dimensions.get('window');

// Use iPhone6 as base size which is 375 x 667
const baseWidth = 375;
const baseHeight = 667;

const scaleWidth = width / baseWidth;
const scaleHeight = height / baseHeight;
const scale = Math.min(scaleWidth, scaleHeight);

export const scaledSize =
    (size) => Math.ceil((size * scale));

测试

const size = {
    small: scaledSize(25),
    oneThird: scaledSize(125),
    fullScreen: scaledSize(375),
};

console.log(size);

// iPhone 5s
{small: 22, oneThird: 107, fullScreen: 320}
// iPhone 6s
{small: 25, oneThird: 125, fullScreen: 375}
// iPhone 6s Plus
{small: 28, oneThird: 138, fullScreen: 414}

这是否意味着您必须使用iPhone 6模拟器,并根据它的外观在其他设备上看起来不错?
Walter Monecke '19

@WalterMonecke在我的情况下是的。您还可以适应使用其他模拟器作为基础。
shentaoy

4

adjustsFontSizeToFitnumberOfLines我的作品。他们将长电子邮件调整为1行。

<View>
  <Text
    numberOfLines={1}
    adjustsFontSizeToFit
    style={{textAlign:'center',fontSize:30}}
  >
    {this.props.email}
  </Text>
</View>

10
根据文档“ adjustsFontSizeToFit”仅适用于iOS
mdehghani

这是行不通的Android
萨曼莎Withanage

3

通过执行以下操作,我设法克服了这一问题。

  1. 为您当前的视图选择所需的字体大小(确保在模拟器中使用的当前设备看起来不错)。

  2. import { Dimensions } from 'react-native' 并定义组件外部的宽度,如下所示: let width = Dimensions.get('window').width;

  3. 现在console.log(width)并写下来。例如,如果您的漂亮字体大小为15,宽度为360,则取360并除以15(= 24)。这将是要调整为不同大小的重要值。

    在样式对象中使用此数字,如下所示: textFontSize: { fontSize = width / 24 },...

现在您有了一个响应式fontSize。


嘿,真的有效吗?f1 =宽度/(宽度/尺寸)这不能正常工作吗?
Elrond

1
我最终使用react-native-text
Walter Monecke

3

我们可以使用flex布局,并使用AdjustsFontSizeToFit = {true}来响应字体大小,然后文本会根据容器的大小进行调整。

     <Text
    adjustsFontSizeToFit
    style={styles.valueField}>{value}
    </Text>

但是在样式中,您还需要放置一个fontsize,然后才可以调整AdjustFontSizeToFit工作。

    valueField: {
    flex: 3,
    fontSize: 48,
    marginBottom: 5,
    color: '#00A398',
},

2

我最近遇到了这个问题,最终使用了react-native-extended-stylesheet

您可以rem根据屏幕尺寸设置值和其他尺寸条件。根据文档:

// component
const styles = EStyleSheet.create({
  text: {
    fontSize: '1.5rem',
    marginHorizontal: '2rem'
  }
});
// app entry
let {height, width} = Dimensions.get('window');
EStyleSheet.build({
  $rem: width > 340 ? 18 : 16
});


2
import { Dimensions } from 'react-native';

const { width, fontScale } = Dimensions.get("window");

const styles = StyleSheet.create({
    fontSize: idleFontSize / fontScale,
});

fontScale根据您的设备获得规模


在我使用的Android Emulator 4_WVGA_Nexus_S_API虚拟设备上,fontscale只会返回1。
reggie3

0

需要使用这种方式,我已经用过了,而且工作正常。

react-native- active -screen npm install react-native-response-screen-保存

就像我有一台设备1080x1920

The vertical number we calculate from height **hp**
height:200
200/1920*100 = 10.41% - height:hp("10.41%")


The Horizontal number we calculate from width **wp**
width:200
200/1080*100 = 18.51% - Width:wp("18.51%")

适用于所有设备


0

一种稍微不同的方法对我有用:-

const normalize = (size: number): number => {
  const scale = screenWidth / 320;
  const newSize = size * scale;
  let calculatedSize = Math.round(PixelRatio.roundToNearestPixel(newSize))

  if (PixelRatio.get() < 3)
    return calculatedSize - 0.5
  return calculatedSize
};

请参考像素比率,因为这可以使您根据设备密度更好地设置功能。


-3

您可以使用类似这样的东西。

var {height,width} = Dimensions.get('window'); var textFontSize = width * 0.03;

inputText: {
    color : TEXT_COLOR_PRIMARY,
    width: '80%',
    fontSize: textFontSize
}

希望这对您有所帮助,而无需安装任何第三方库。


1
0.03是哪里来的?
DavidNoreña18年

它会有所响应吗?
Deepak Ganachari
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.