@@ -12,34 +12,37 @@ import {
12
12
} from '../../commons/new' ;
13
13
import { Colors } from 'style' ;
14
14
15
- export type TextProps = RNTextProps & TypographyModifiers & ColorsModifiers & MarginModifiers & {
16
- /**
17
- * color of the text
18
- */
19
- color ?: string ;
20
- /**
21
- * whether to center the text (using textAlign)
22
- */
23
- center ?: boolean ;
24
- /**
25
- * whether to change the text to uppercase
26
- */
27
- uppercase ?: boolean ;
28
- /**
29
- * Substring to highlight
30
- */
31
- highlightString ?: string ;
32
- /**
33
- * Custom highlight style for highlight string
34
- */
35
- highlightStyle ?: TextStyle ;
36
- /**
37
- * Use Animated.Text as a container
38
- */
39
- animated ?: boolean ;
40
- textAlign ?: string ;
41
- style ?: StyleProp < TextStyle | Animated . AnimatedProps < TextStyle > > ;
42
- }
15
+ export type TextProps = RNTextProps &
16
+ TypographyModifiers &
17
+ ColorsModifiers &
18
+ MarginModifiers & {
19
+ /**
20
+ * color of the text
21
+ */
22
+ color ?: string ;
23
+ /**
24
+ * whether to center the text (using textAlign)
25
+ */
26
+ center ?: boolean ;
27
+ /**
28
+ * whether to change the text to uppercase
29
+ */
30
+ uppercase ?: boolean ;
31
+ /**
32
+ * Substring to highlight
33
+ */
34
+ highlightString ?: string | string [ ] ;
35
+ /**
36
+ * Custom highlight style for highlight string
37
+ */
38
+ highlightStyle ?: TextStyle ;
39
+ /**
40
+ * Use Animated.Text as a container
41
+ */
42
+ animated ?: boolean ;
43
+ textAlign ?: string ;
44
+ style ?: StyleProp < TextStyle | Animated . AnimatedProps < TextStyle > > ;
45
+ } ;
43
46
export type TextPropTypes = TextProps ; //TODO: remove after ComponentPropTypes deprecation;
44
47
45
48
type PropsTypes = BaseComponentInjectedProps & ForwardRefInjectedProps & TextProps ;
@@ -62,50 +65,97 @@ class Text extends PureComponent<PropsTypes> {
62
65
// this._root.setNativeProps(nativeProps); // eslint-disable-line
63
66
// }
64
67
65
- getTextPartsByHighlight ( targetString = '' , highlightString = '' ) {
66
- if ( _ . isEmpty ( highlightString . trim ( ) ) ) {
67
- return [ targetString ] ;
68
+ getPartsByHighlight ( targetString = '' , highlightString : string | string [ ] ) {
69
+ if ( typeof highlightString === 'string' ) {
70
+ if ( _ . isEmpty ( highlightString . trim ( ) ) ) {
71
+ return [ { string : targetString , shouldHighlight : false } ] ;
72
+ }
73
+ return this . getTextPartsByHighlight ( targetString , highlightString ) ;
74
+ } else {
75
+ return this . getArrayPartsByHighlight ( targetString , highlightString ) ;
68
76
}
77
+ }
69
78
79
+ getTextPartsByHighlight ( targetString = '' , highlightString = '' ) {
80
+ if ( highlightString === '' ) {
81
+ return [ { string : targetString , shouldHighlight : false } ] ;
82
+ }
70
83
const textParts = [ ] ;
71
84
let highlightIndex ;
72
-
73
85
do {
74
86
highlightIndex = targetString . toLowerCase ( ) . indexOf ( highlightString . toLowerCase ( ) ) ;
75
87
if ( highlightIndex !== - 1 ) {
76
88
if ( highlightIndex > 0 ) {
77
- textParts . push ( targetString . substring ( 0 , highlightIndex ) ) ;
89
+ textParts . push ( { string : targetString . substring ( 0 , highlightIndex ) , shouldHighlight : false } ) ;
78
90
}
79
- textParts . push ( targetString . substr ( highlightIndex , highlightString . length ) ) ;
91
+ textParts . push ( { string : targetString . substr ( highlightIndex , highlightString . length ) , shouldHighlight : true } ) ;
80
92
targetString = targetString . substr ( highlightIndex + highlightString . length ) ;
81
93
} else {
82
- textParts . push ( targetString ) ;
94
+ textParts . push ( { string : targetString , shouldHighlight : false } ) ;
83
95
}
84
96
} while ( highlightIndex !== - 1 ) ;
85
97
86
98
return textParts ;
87
99
}
88
100
101
+ getArrayPartsByHighlight ( targetString = '' , highlightString = [ '' ] ) {
102
+ const target = _ . toLower ( targetString ) ;
103
+ const indices = [ ] ;
104
+ let index = 0 ;
105
+ let lastWordLength = 0 ;
106
+ for ( let j = 0 ; j < highlightString . length ; j ++ ) {
107
+ const word = _ . toLower ( highlightString [ j ] ) ;
108
+ const targetSuffix = target . substring ( index + lastWordLength ) ;
109
+ const i = targetSuffix . indexOf ( word ) ;
110
+ if ( i >= 0 ) {
111
+ const newIndex = index + lastWordLength + i ;
112
+ indices . push ( { start : index + lastWordLength + i , end : index + lastWordLength + i + word . length } ) ;
113
+ index = newIndex ;
114
+ lastWordLength = word . length ;
115
+ } else {
116
+ break ;
117
+ }
118
+ }
119
+ const parts = [ ] ;
120
+ for ( let k = 0 ; k < indices . length ; k ++ ) {
121
+ if ( k === 0 && indices [ k ] . start !== 0 ) {
122
+ parts . push ( { string : targetString . substring ( 0 , indices [ k ] . start ) , shouldHighlight : false } ) ;
123
+ }
124
+ parts . push ( { string : targetString . substring ( indices [ k ] . start , indices [ k ] . end ) , shouldHighlight : true } ) ;
125
+ if ( k === indices . length - 1 ) {
126
+ parts . push ( { string : targetString . substring ( indices [ k ] . end ) , shouldHighlight : false } ) ;
127
+ } else {
128
+ parts . push ( { string : targetString . substring ( indices [ k ] . end , indices [ k + 1 ] . start ) , shouldHighlight : false } ) ;
129
+ }
130
+ }
131
+ return parts ;
132
+ }
133
+
89
134
renderText ( children : any ) : any {
90
135
const { highlightString, highlightStyle} = this . props ;
91
136
92
137
if ( ! _ . isEmpty ( highlightString ) ) {
93
138
if ( _ . isArray ( children ) ) {
94
- return _ . map ( children , ( child ) => {
139
+ return _ . map ( children , child => {
95
140
return this . renderText ( child ) ;
96
141
} ) ;
97
142
}
98
143
99
144
if ( _ . isString ( children ) ) {
100
- const textParts = this . getTextPartsByHighlight ( children , highlightString ) ;
101
- return _ . map ( textParts , ( text , index ) => {
102
- const shouldHighlight = _ . lowerCase ( text ) === _ . lowerCase ( highlightString ) ;
103
- return (
104
- < RNText key = { index } style = { shouldHighlight ? [ styles . highlight , highlightStyle ] : styles . notHighlight } >
105
- { text }
106
- </ RNText >
107
- ) ;
108
- } ) ;
145
+ const textParts = highlightString && this . getPartsByHighlight ( children , highlightString ) ;
146
+ return (
147
+ textParts &&
148
+ _ . map ( textParts , ( text , index ) => {
149
+ return (
150
+ < RNText
151
+ key = { index }
152
+ style = { text . shouldHighlight ? [ styles . highlight , highlightStyle ] : styles . notHighlight }
153
+ >
154
+ { text . string }
155
+ </ RNText >
156
+ ) ;
157
+ } )
158
+ ) ;
109
159
}
110
160
}
111
161
return children ;
0 commit comments