Author: IPlayCodex Warehouse: Github, codePen Blog: Nugget, SegmentFault, Zhihu, Jianshushu, Blogpark, LeetCode Public account: FEZONE contact me: [email protected] Special statement: Original is not easy, unauthorized shall not be reproduced or copied this article, otherwise according to infringement treatment, if you need to reprint or open the public number white list can contact me, respect the original respect for intellectual property rights from me

1. Introduction

When using React-Native for development, we read the official document that screen adaptation is to use flexBox for layout

Click here to see the flexBox layout

The attributes of flexBox are not explained here. If not, please refer to the official documentation. This is just to mention, because the disadvantages of using Flexbox for screen adaptation and how to solve them

In React-Native, we use StyleSheet as an object for style development. Such as:

import { StyleSheet } from "react-native";

// declare a style variable, which is used to style the component
let style = StyleSheet.crate({
    title: {
        fontSize: 14.color: "#BBB",},subTitle: {
        marginTop: 10.marginBottom: 10.paddingLeft: 10.paddingRight: 10,}});Copy the code

You can see there’s a big difference between writing styles in React – Native and writing CSS on the Web. Less,sass, etc. And you can’t use composite styles. Such as:

Write styles in the Web

/* web */
.title {
    padding: 10 20 15 5;
}
Copy the code

Write styles in React-native

/* react-native */
title: {paddingTop:10.paddingRight:20.paddingBottom:15.paddingLeft:5
}
Copy the code

And you can see that writing styles in Rn is a bit of a hassle.

2. Useflexboxlayout

FlexBox provide us with the layout of the convenient method, but sometimes we still need some conventional properties, such as width, height, paddingTop, fontSize, etc… Since styles are unitless in Rn (dp by default), the problem is that their DPI is different on different screens. How does this fit?

By looking at official documents, I found a solution. Encapsulate a method dp2px as follows:

import { Dimensions } from "react-native";
const deviceWidthDp = Dimensions.get("window").width;
// Default design draft 375
const uiWidthPx = 375;
function dp2px(uiElementPx) {
    return (uiElementPx * deviceWidthDp) / uiWidthPx;
}
export default dp2px;
Copy the code

This allows you to reference this method directly when you need to use width, height, etc. As follows:

import dp2px from './dp2px';

title:{
    paddingTop:dp2px(10),
    paddingRight:dp2px(20),
    paddingBottom:dp2px(15),
    paddingLeft:dp2px(5)}Copy the code

This completes the adaptation. But is this the optimal solution? Obviously not. Every time you write a style, you need to reference this function, and every time you write a lot of DP2XP, it is very troublesome. So the question is, how do we optimize?

3. Encapsulate CustomStyleSheet instead of native StyleSheet

Looking through the source code, we found that StyleSheet is not a class, so we don’t need to inherit it and rewrite its method. We just need to encapsulate a function like StyleSheet to do some calculations inside it, and then use our CustomStyleSheet instead where we need to write the style Native StyleSheet will do. The code looks like this:

import { StyleSheet } from "react-native";
import dp2px from "./dp2px";

let MyStyleSheet = {
    create(style) {
        lets = { ... style };// Currently only the following attributes are processed
        let list = [
            "width"."height"."marginTop"."marginBottom"."marginLeft"."marginRight"."paddingTop"."paddingRight"."paddingBottom"."paddingLeft"."top"."right"."bottom"."left"."fontSize"."lineHeight",];for (let outKey in s) {
            for (let innerKey in s[outKey]) {
                if (
                    list.includes(innerKey) &&
                    typeof s[outKey][innerKey] == "number") { s[outKey][innerKey] = px2dp(s[outKey][innerKey]); }}}returnStyleSheet.create(s); }};export default MyStyleSheet;
Copy the code

It is very convenient to use after the above encapsulation. Use it directly in the React-Native component instead of the native StyleSheet. You can zoom in and out year-on-year depending on the screen size of the device. The principle is somewhat similar to rem. The code is as follows:

import MyStyleSheet from "./myStyleSheet";

// Use encapsulated MyStyleSheet instead of native StyleSheet, and write the numbers directly to automatically convert them into different screen-adapted DP
let style = MyStyleSheet.create({
    title: {
        fontSize: 14.width: 100,},subTitle: {
        paddingTop: 10.paddingBottom: 10.marginTop: 10.marginBottom: 10,}});Copy the code

So far, the end. Attached with the relevant information for learning.


References:

Ruan Yifeng’s Flex tutorial

4. The conclusion

❤️ attention + likes + favorites + comments + forwarding ❤️ original is not easy, encourage the author to create better articles ~