react-native: `setNativeProps` does not work with `text` property on `Text` component

Environment

  React Native Environment Info:
    System:
      OS: macOS 10.14.1
      CPU: (8) x64 Intel(R) Core(TM) i7-6700HQ CPU @ 2.60GHz
      Memory: 123.34 MB / 16.00 GB
      Shell: 5.3 - /bin/zsh
    Binaries:
      Node: 8.11.3 - /usr/local/bin/node
      Yarn: 1.10.1 - ~/.yarn/bin/yarn
      npm: 5.6.0 - ~/n/bin/npm
      Watchman: 4.9.0 - /usr/local/bin/watchman
    SDKs:
      iOS SDK:
        Platforms: iOS 12.1, macOS 10.14, tvOS 12.1, watchOS 5.1
      Android SDK:
        API Levels: 23, 24, 26, 27, 28
        Build Tools: 23.0.1, 26.0.2, 26.0.3, 27.0.3, 28.0.0, 28.0.0, 28.0.1, 28.0.2, 28.0.3
        System Images: android-27 | Google Play Intel x86 Atom
    IDEs:
      Xcode: 10.1/10B61 - /usr/bin/xcodebuild
    npmPackages:
      react: 16.6.3 => 16.6.3
      react-native: 0.57.8 => 0.57.8
    npmGlobalPackages:
      create-react-native-app: 1.0.0
      generator-module-react-native: 0.0.2
      react-native-cli: 2.0.1
      react-native-create-bridge: 1.2.1
      react-native-create-library: 3.1.2
      react-native-git-upgrade: 0.2.7

Description

setNativeProps does not work with text property on Text component.

Reproducible Demo

See this repo:

https://github.com/tychota/bugSetNativePropsText

Expected:

  • first print ā€œ-ā€ then goes from 0 to 100 in 2 seconds

Real life:

  • prints ā€œ-ā€ on šŸŽ (ios), then does nothing
  • prints ā€œ-ā€ on šŸ¤– (android), then does nothing

People to CC

Cause hypothesis

AFAIK:

  • there is two component involved in rendering a text: a RCTText and a RCTRawText
  • while most of the properties are handled by the RCTText (eg opacity, color, ect), the text itself is handled by RCTRawText
  • there is no property in the RCTText (or its parent RCTBaseText) to set text

Next steps

I’m willing to contribute.

I think we can do something similar to https://github.com/facebook/react-native/commit/2307ea60d03edd234511bfe32474c453f30c1693.

Not sure exactly how to get the text since the information must be in attributed string and I would like to keep having one single source of True (hence not duplicating text and adding it as property like previous commit).

About this issue

  • Original URL
  • State: closed
  • Created 5 years ago
  • Reactions: 4
  • Comments: 19 (14 by maintainers)

Most upvoted comments

This feature would be awesome!! šŸ„‡

For Android this seems to work:

/**
 * Copyright (c) 2015-present, Facebook, Inc.
 * <p>
 * This source code is licensed under the MIT license found in the
 * LICENSE file in the root directory of this source tree.
 */

package com.facebook.react.views.text;

public class ReactTextShadowNode extends ReactBaseTextShadowNode {

    // .....

    @ReactProp(name = "text")
    public void setText(@Nullable String text) {
        List<ReactShadowNode> childrens = this.getChildrenList();
        if (childrens != null) {
            for (ReactShadowNode child : childrens) {
                if (child instanceof ReactRawTextShadowNode) {
                    ((ReactRawTextShadowNode) child).setText(text);
                }
            }
        }
        markUpdated();
    }
}