React Native Responsive Font Size

92

Saya ingin bertanya bagaimana bereaksi menangani native atau melakukan font responsif. Misalnya di iphone 4s saya memiliki fontSize: 14, sedangkan di iphone 6 saya memiliki fontSize: 18.

Sydney Loteria
sumber
19
Jika ada yang mencari cara untuk menonaktifkan penskalaan font sepenuhnya, gunakanText.defaultProps.allowFontScaling=false
CoderDave
1
@CoderDave ini brilian!
Abdo
Jika Anda menginginkan fontSize relatif berdasarkan ukuran layar daripada fontSize yang tepat, Anda dapat mencoba npmjs.com/package/react-native-responsive-dimensions , Ini akan secara otomatis mengubah ukuran font Anda berdasarkan screenSize perangkat
Dani Akash

Jawaban:

98

Anda dapat menggunakan PixelRatio

sebagai contoh:

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
  }
});

Edit:

Contoh lain:

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
  }
}

Pemakaian:

fontSize: normalize(24)

Anda dapat melangkah lebih jauh dengan memungkinkan ukuran yang akan digunakan pada setiap <Text />komponen dengan ukuran yang telah ditentukan sebelumnya.

Contoh:

const styles = {
  mini: {
    fontSize: normalize(12),
  },
  small: {
    fontSize: normalize(15),
  },
  medium: {
    fontSize: normalize(17),
  },
  large: {
    fontSize: normalize(20),
  },
  xlarge: {
    fontSize: normalize(24),
  },
};
chinloong
sumber
22
di mana Anda menggunakan skala const Anda di sini?
Jan Franz Palngipang
2
Ini sepertinya tidak melakukan apa-apa. mini selalu === 12
A.com
14
Mengapa Anda mengurangi 2 untuk perangkat non-ios?
Parth Tamane
51

Kami menggunakan fungsi utilitas penskalaan sederhana, lurus ke depan, yang kami tulis:

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};

Menghemat waktu Anda melakukan banyak jika. Anda dapat membaca lebih lanjut tentang itu di posting blog saya .


Sunting: Saya pikir mungkin berguna untuk mengekstrak fungsi-fungsi ini ke paket npm mereka sendiri, saya juga menyertakan ScaledSheetdalam paket, yang merupakan versi skala otomatis StyleSheet. Anda dapat menemukannya di sini: react-native-size-matter .

nirsky
sumber
Terima kasih, apa skenario terbaik untuk menggunakan utilitas ini? Maksud saya di mana menggunakan scale, verticaleScale dan moderateScale?
Pir Shukarullah Shah
4
Saya menggunakan moderatScale pada hampir semua hal yang membutuhkan penskalaan, seperti fontSize, margin, gambar, dan ukuran Svg, (untuk tata letak saya menggunakan flex) karena penskalaan imo tidak boleh linier, tapi itu masalah preferensi pribadi. Jika Anda ingin mencapai hasil linier, gunakan sebagian besar skala, dan gunakan verticalScale pada hal-hal seperti ketinggian kontainer.
nirsky
16

Karena unit responsif tidak tersedia di react-native saat ini, saya akan mengatakan taruhan terbaik Anda adalah mendeteksi ukuran layar dan kemudian menggunakannya untuk menyimpulkan jenis perangkat dan mengatur fontSize secara kondisional.

Anda bisa menulis modul seperti:

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

Anda hanya perlu mencari lebar dan tinggi default untuk setiap perangkat. Jika lebar dan tinggi dibalik saat perangkat mengubah orientasi, Anda mungkin dapat menggunakan rasio aspek atau hanya mencari tahu yang lebih kecil dari dua dimensi untuk mengetahui lebar.

Modul ini atau satu ini dapat membantu Anda menemukan dimensi perangkat atau jenis perangkat.

Isaac Madwed
sumber
Saya telah menginstal react-native-device tetapi itu memberi saya kesalahan "Tidak dapat menyelesaikan Dimensi modul" ketika saya menjalankan aplikasi
Sydney Loteria
Sepertinya Anda perlu memastikan bahwa Anda menggunakan versi RN yang benar untuk modul
Isaac Madwed
Saya menggunakan React Native versi terbaru :) Saya rasa saat ini tidak didukung?
Sydney Loteria
Mungkin ... Mungkin coba hapus folder node_modules Anda dan kembalinpm install
Isaac Madwed
6

Lihatlah perpustakaan yang saya tulis: https://github.com/tachyons-css/react-native-style-tachyons

Ini memungkinkan Anda untuk menentukan root-fontSize ( rem) saat memulai, yang dapat Anda jadikan sebagai ketergantunganPixelRatio karakteristik perangkat atau perangkat lainnya.

Kemudian Anda mendapatkan gaya yang sesuai dengan Anda rem, tidak hanya fontSize, tetapi juga paddings dll:

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

Ekspansi:

  • f5selalu ukuran font dasar Anda
  • pa2 memberi Anda padding relatif terhadap ukuran font dasar Anda.
Fabian Zeindl
sumber
5

Saya cukup menggunakan rasio ukuran layar, yang berfungsi dengan baik untuk saya.

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));

Uji

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}
shentaoy
sumber
Apakah ini berarti Anda harus menggunakan Simulator iPhone 6 dan berdasarkan tampilannya, Simulator iPhone akan terlihat bagus di perangkat lain?
Walter Monecke
@Walteronecke dalam kasus saya ya. Anda juga dapat beradaptasi untuk menggunakan simulator lain sebagai basis.
shentaoy
4

adjustsFontSizeToFitdan numberOfLinesbekerja untuk saya. Mereka menyesuaikan email yang panjang menjadi 1 baris.

<View>
  <Text
    numberOfLines={1}
    adjustsFontSizeToFit
    style={{textAlign:'center',fontSize:30}}
  >
    {this.props.email}
  </Text>
</View>
Gundam Meister
sumber
10
menurut dokumentasi 'adjustsFontSizeToFit' hanya berlaku untuk iOS
mdehghani
Ini tidak bekerja untuk android
Samantha Withanage
3

Saya berhasil mengatasinya dengan melakukan hal berikut.

  1. Pilih ukuran font yang Anda suka untuk tampilan saat ini yang Anda miliki (Pastikan tampilannya bagus untuk perangkat saat ini yang Anda gunakan di simulator).

  2. import { Dimensions } from 'react-native' dan tentukan lebar di luar komponen seperti ini: let width = Dimensions.get('window').width;

  3. Sekarang console.log (lebar) dan tuliskan. Jika ukuran font Anda yang bagus adalah 15 dan lebarnya 360 misalnya, ambil 360 dan bagi dengan 15 (= 24). Ini akan menjadi nilai penting yang akan menyesuaikan dengan ukuran yang berbeda.

    Gunakan nomor ini di objek gaya Anda seperti: textFontSize: { fontSize = width / 24 },...

Sekarang Anda memiliki fontSize responsif.

Walter Monecke
sumber
hei apakah itu benar-benar berhasil? f1 = width / (width / size) ini tidak bisa berfungsi?
Elrond
1
Saya akhirnya menggunakan react-native-text.
Walter Monecke
3

Kita bisa menggunakan tata letak fleksibel dan menggunakan adjustsFontSizeToFit = {true} untuk ukuran font responsif. Dan teks akan menyesuaikan sesuai dengan ukuran penampung.

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

Tetapi dalam gaya Anda perlu meletakkan ukuran font juga hanya kemudian akan menyesuaikan pekerjaanFontSizeToFit.

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

Saya baru-baru ini mengalami masalah ini dan akhirnya menggunakan react-native-extended-stylesheet

Anda dapat mengatur remnilai dan kondisi ukuran tambahan berdasarkan ukuran layar. Sesuai dokumen:

// 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
});
colakollektiv.dll
sumber
2

Kenapa tidak digunakan PixelRatio.getPixelSizeForLayoutSize(/* size in dp */);, sama saja dengan pdunit di Android.

Ahmed Kamal
sumber
2
import { Dimensions } from 'react-native';

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

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

fontScaledapatkan skala sesuai perangkat Anda .

Paras Korat
sumber
fontscale baru saja mengembalikan 1 pada perangkat virtual Android Emulator 4_WVGA_Nexus_S_API yang saya gunakan.
reggie3
0

Perlu menggunakan cara ini, saya telah menggunakan yang ini dan berfungsi dengan baik.

react-native-responsive-screen npm install react-native-responsive-screen --save

Sama seperti saya memiliki perangkat 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%")

Ini berfungsi untuk semua perangkat

Tushar Kumawat
sumber
0

Pendekatan yang sedikit berbeda berhasil untuk saya: -

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
};

Lihat Rasio Piksel karena ini memungkinkan Anda untuk mengatur fungsi dengan lebih baik berdasarkan kepadatan perangkat.

Arpan Sharma
sumber
-3

Anda bisa menggunakan sesuatu seperti ini.

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

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

Semoga ini bisa membantu tanpa menginstal pustaka pihak ketiga.

Guna Sekhar
sumber
1
dan dari mana 0,03 berasal?
David Noreña
apakah itu akan responsif?
Deepak Ganachari