|
1 | 1 | # react-native-nitro-text |
2 | 2 |
|
3 | | -react-native-nitro-text is a drop in replacement of the react native text component |
| 3 | +Drop‑in, high‑performance Text for React Native (Fabric). Native iOS rendering with smooth selection, rich styling fragments, precise measurement, and line limiting. |
4 | 4 |
|
5 | 5 | [](https://www.npmjs.com/package/react-native-nitro-text) |
6 | 6 | [](https://www.npmjs.com/package/react-native-nitro-text) |
7 | 7 | [](https://github.com/patrickkabwe/react-native-nitro-text/LICENSE) |
8 | 8 |
|
9 | | -## Requirements |
| 9 | +## Features |
| 10 | + |
| 11 | +- Native iOS rendering: UITextView/TextKit for smooth selection and layout. |
| 12 | +- Rich styling fragments: nested styles merged into native attributed text. |
| 13 | +- Precise measurement: reports size for dynamic UIs; supports `numberOfLines`. |
| 14 | +- Text alignment & transform: `textAlign` and `textTransform` support. |
| 15 | +- Color parsing: decimal ARGB, named colors, hex (RGB/RGBA), `rgb()/rgba()`. |
| 16 | +- Works with RN Text: use NitroText inside RN `<Text>` and vice‑versa. |
10 | 17 |
|
11 | | -- React Native v0.76.0 or higher |
12 | | -- Node 18.0.0 or higher |
| 18 | +## Requirements |
13 | 19 |
|
14 | | -> [!IMPORTANT] |
15 | | -> To Support `Nitro Views` you need to install React Native version v0.78.0 or higher. |
| 20 | +- React Native v0.78.0 or higher (Fabric/Nitro Views) |
| 21 | +- Node 18+ (Node 20+ recommended) |
16 | 22 |
|
17 | 23 | ## Installation |
18 | 24 |
|
19 | 25 | ```bash |
20 | 26 | bun add react-native-nitro-text react-native-nitro-modules |
21 | 27 | ``` |
22 | 28 |
|
| 29 | +iOS |
| 30 | + |
| 31 | +```bash |
| 32 | +cd ios && pod install && cd - |
| 33 | +``` |
| 34 | + |
| 35 | +That’s it. Nitro autolinking registers the view and codegen output. |
| 36 | + |
| 37 | +## Usage |
| 38 | + |
| 39 | +Basic |
| 40 | + |
| 41 | +```tsx |
| 42 | +import { NitroText } from 'react-native-nitro-text' |
| 43 | + |
| 44 | +export function Title() { |
| 45 | + return ( |
| 46 | + <NitroText style={{ fontSize: 24, fontWeight: 'bold' }}> |
| 47 | + 🚀 NitroText Showcase |
| 48 | + </NitroText> |
| 49 | + ) |
| 50 | +} |
| 51 | +``` |
| 52 | + |
| 53 | +Rich text (nested fragments) |
| 54 | + |
| 55 | +```tsx |
| 56 | +<NitroText style={{ fontSize: 16, lineHeight: 24 }}> |
| 57 | + Welcome to <NitroText style={{ fontWeight: 'bold' }}>bold</NitroText> and{' '} |
| 58 | + <NitroText style={{ fontStyle: 'italic', color: '#6f42c1' }}>italic</NitroText> |
| 59 | + {' '}text with colors and sizes. |
| 60 | +}</NitroText> |
| 61 | +``` |
| 62 | + |
| 63 | +Line limiting and measurement |
| 64 | + |
| 65 | +```tsx |
| 66 | +<NitroText numberOfLines={2} style={{ fontSize: 16 }}> |
| 67 | + This long text will be truncated with an ellipsis when it exceeds two lines. |
| 68 | +</NitroText> |
| 69 | + |
| 70 | +// Native height callback (iOS) |
| 71 | +<NitroText |
| 72 | + onSelectableTextMeasured={(height) => console.log('height', height)} |
| 73 | + style={{ fontSize: 16 }} |
| 74 | +> |
| 75 | + Measure my height after layout |
| 76 | +</NitroText> |
| 77 | +``` |
| 78 | + |
| 79 | +Mixed with RN Text |
| 80 | + |
| 81 | +```tsx |
| 82 | +<Text> |
| 83 | + RN <NitroText style={{ fontWeight: 'bold' }}>meets Nitro</NitroText> inside |
| 84 | + one paragraph. |
| 85 | +</Text> |
| 86 | +``` |
| 87 | + |
| 88 | +## Props |
| 89 | + |
| 90 | +Unless noted, props mirror React Native Text style behavior through the `style` prop. |
| 91 | + |
| 92 | +- `style`: supports `color`, `fontSize`, `fontWeight`, `fontStyle`, `lineHeight`, `textAlign`, `textTransform`. |
| 93 | +- `numberOfLines?: number`: single/multi‑line with tail truncation for single line. |
| 94 | +- `selectable?: boolean` (default `true`): enables native selection. |
| 95 | +- `onSelectableTextMeasured?(height: number)`: native iOS height after layout. |
| 96 | + |
| 97 | +Note: Nested `<NitroText>` elements produce styling fragments merged natively. |
| 98 | + |
| 99 | +## Platform Support |
| 100 | + |
| 101 | +- iOS (Fabric) |
| 102 | + |
| 103 | +## Parity Roadmap |
| 104 | + |
| 105 | +Status toward React Native `Text` parity. Checked = implemented, unchecked = planned. |
| 106 | + |
| 107 | +- [x] Core styles: `color`, `fontSize`, `fontWeight`, `fontStyle`, `lineHeight` |
| 108 | +- [x] Layout/behavior: `numberOfLines` (single‑line tail truncation), nested spans |
| 109 | +- [x] Alignment/transform: `textAlign`, `textTransform` |
| 110 | +- [x] Color parsing: decimal ARGB, named colors, hex, `rgb()/rgba()` |
| 111 | +- [x] Native selection: iOS selection handles/caret; smooth scrolling/selection |
| 112 | +- [x] Measurement: native height via `onSelectableTextMeasured` |
| 113 | +- [ ] `fontFamily` (custom fonts + weight/style fallback matrix) |
| 114 | +- [ ] `letterSpacing`, `textDecoration*`, `textShadow*` |
| 115 | +- [ ] `ellipsizeMode` parity (head, middle, tail, clip) and multi‑line behavior |
| 116 | +- [ ] `allowFontScaling`, `maxFontSizeMultiplier` (Dynamic Type) |
| 117 | +- [ ] `fontVariant` (small‑caps, tabular‑nums, oldstyle‑nums, etc.) |
| 118 | +- [ ] iOS `lineBreakStrategyIOS`, `hyphenationFactor` |
| 119 | +- [ ] `selectionColor`, `dataDetectorTypes`, linkable spans |
| 120 | +- [ ] Press events: `onPress`, `onLongPress`, `onPressIn/Out` incl. nested spans |
| 121 | +- [ ] `onTextLayout` parity (line/fragment metrics) |
| 122 | +- [ ] Accessibility: roles/labels/hints, nested span accessibility |
| 123 | +- [ ] Bidi/RTL: `writingDirection`, mixed LTR/RTL validation |
| 124 | +- [ ] Baseline/typography: `baselineOffset`, ligatures, kerning |
| 125 | +- [ ] Inline attachments (inline images/icons) where feasible |
| 126 | + |
| 127 | +Priorities: fontFamily, letterSpacing/decoration/shadows, ellipsizeMode parity, press events. |
| 128 | + |
| 129 | +## Text vs NitroText |
| 130 | + |
| 131 | +| Aspect | RN `Text` | `NitroText` | |
| 132 | +| --- | --- | --- | |
| 133 | +| Rendering engine | Platform text primitives via RN | Native iOS TextKit/UITextView via Fabric (reduced JS overhead) | |
| 134 | +| Performance | General‑purpose, solid for most cases | Optimized for rich text and large lists; faster layout/measurement and smoother selection | |
| 135 | +| Props coverage | Full RN `Text` surface | Core styles, alignment/transform, nested fragments, selection, single‑line `numberOfLines`; rest tracked in roadmap | |
| 136 | +| Selection | Functional selection behavior | Native iOS selection with precise caret/handles and smooth interaction | |
| 137 | +| Ellipsis | `ellipsizeMode`: head/middle/tail/clip; multi‑line | Tail on single‑line today; multi‑line + full parity planned | |
| 138 | +| Accessibility | Mature, cross‑platform | iOS first; parity in progress per roadmap | |
| 139 | +| Platform support | iOS, Android, Web (via RN impls) | iOS (Fabric) today; Android planned | |
| 140 | +| Recommended usage | Broad, cross‑platform text needs | Heavy/nested styled text and list performance; native selection/measurement focus | |
| 141 | + |
| 142 | +## Why NitroText? |
| 143 | + |
| 144 | +NitroText uses Nitro Modules + Fabric to render natively with minimal JS overhead. Text selection, layout, and styling are handled in native code (Swift/C++/Obj‑C++), delivering smooth performance in complex lists and rich text scenarios. |
| 145 | + |
| 146 | +## Development |
| 147 | + |
| 148 | +- `bun run build` — typecheck and build package. |
| 149 | +- `bun run codegen` — regenerate Nitrogen codegen outputs. |
| 150 | +- Example app in `example/` (run pods in `example/ios` and start RN). |
| 151 | + |
23 | 152 | ## Credits |
24 | 153 |
|
25 | 154 | Bootstrapped with [create-nitro-module](https://github.com/patrickkabwe/create-nitro-module). |
26 | 155 |
|
27 | 156 | ## Contributing |
28 | 157 |
|
29 | | -Pull requests are welcome. For major changes, please open an issue first to discuss what you would like to change. |
| 158 | +PRs welcome! Please open an issue first for major changes. |
0 commit comments