|
6 | 6 | * |
7 | 7 | * @flow strict-local |
8 | 8 | * @format |
| 9 | + * @oncall react_native |
9 | 10 | */ |
10 | 11 |
|
11 | 12 | import '@react-native/fantom/src/setUpDefaultReactNativeEnvironment'; |
12 | 13 |
|
13 | | -import type {HostInstance} from 'react-native'; |
14 | | - |
15 | 14 | import * as Fantom from '@react-native/fantom'; |
16 | | -import nullthrows from 'nullthrows'; |
17 | 15 | import * as React from 'react'; |
18 | | -import {createRef} from 'react'; |
19 | 16 | import {ActivityIndicator} from 'react-native'; |
20 | 17 |
|
21 | | -describe('<ActivityIndicator>', () => { |
22 | | - it('sets displayName', () => { |
23 | | - expect(ActivityIndicator.displayName).toBe('ActivityIndicator'); |
| 18 | +function renderSizeOutput(element: React.MixedElement): React.Node { |
| 19 | + const root = Fantom.createRoot(); |
| 20 | + Fantom.runTask(() => { |
| 21 | + root.render(element); |
24 | 22 | }); |
25 | | - |
26 | | - describe('props', () => { |
27 | | - describe('size', () => { |
28 | | - it('defaults to "small" (20x20)', () => { |
29 | | - const root = Fantom.createRoot(); |
30 | | - |
31 | | - Fantom.runTask(() => { |
32 | | - root.render(<ActivityIndicator />); |
33 | | - }); |
34 | | - |
35 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
36 | | - <rn-androidProgressBar height="20" width="20" />, |
37 | | - ); |
38 | | - }); |
39 | | - |
40 | | - it('renders with size "small"', () => { |
41 | | - const root = Fantom.createRoot(); |
42 | | - |
43 | | - Fantom.runTask(() => { |
44 | | - root.render(<ActivityIndicator size="small" />); |
45 | | - }); |
46 | | - |
47 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
48 | | - <rn-androidProgressBar height="20" width="20" />, |
49 | | - ); |
50 | | - }); |
51 | | - |
52 | | - it('renders with size "large" (36x36)', () => { |
53 | | - const root = Fantom.createRoot(); |
54 | | - |
55 | | - Fantom.runTask(() => { |
56 | | - root.render(<ActivityIndicator size="large" />); |
57 | | - }); |
58 | | - |
59 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
60 | | - <rn-androidProgressBar height="36" width="36" />, |
61 | | - ); |
62 | | - }); |
63 | | - |
64 | | - it('renders with numeric size on Android', () => { |
65 | | - const root = Fantom.createRoot(); |
66 | | - |
67 | | - Fantom.runTask(() => { |
68 | | - root.render(<ActivityIndicator size={48} />); |
69 | | - }); |
70 | | - |
71 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
72 | | - <rn-androidProgressBar height="48" width="48" />, |
73 | | - ); |
74 | | - }); |
75 | | - }); |
76 | | - |
77 | | - describe('color', () => { |
78 | | - it('renders an AndroidProgressBar when color is set', () => { |
79 | | - const root = Fantom.createRoot(); |
80 | | - |
81 | | - Fantom.runTask(() => { |
82 | | - root.render(<ActivityIndicator color="red" />); |
83 | | - }); |
84 | | - |
85 | | - // Color is a native prop not serialized as a view attribute, |
86 | | - // but the component still renders correctly |
87 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
88 | | - <rn-androidProgressBar height="20" width="20" />, |
89 | | - ); |
90 | | - }); |
91 | | - }); |
92 | | - |
93 | | - describe('animating', () => { |
94 | | - it('defaults to true', () => { |
95 | | - const root = Fantom.createRoot(); |
96 | | - |
97 | | - Fantom.runTask(() => { |
98 | | - root.render(<ActivityIndicator />); |
99 | | - }); |
100 | | - |
101 | | - // Component renders normally when animating (default) |
102 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
103 | | - <rn-androidProgressBar height="20" width="20" />, |
104 | | - ); |
105 | | - }); |
106 | | - |
107 | | - it('renders when animating is false', () => { |
108 | | - const root = Fantom.createRoot(); |
109 | | - |
110 | | - Fantom.runTask(() => { |
111 | | - root.render(<ActivityIndicator animating={false} />); |
112 | | - }); |
113 | | - |
114 | | - // Component still renders when not animating |
115 | | - expect(root.getRenderedOutput().toJSX()).toEqual( |
116 | | - <rn-androidProgressBar height="20" width="20" />, |
117 | | - ); |
118 | | - }); |
119 | | - }); |
120 | | - |
121 | | - describe('style', () => { |
122 | | - it('applies wrapper View style', () => { |
123 | | - const root = Fantom.createRoot(); |
124 | | - |
125 | | - Fantom.runTask(() => { |
126 | | - root.render(<ActivityIndicator style={{opacity: 0.5}} />); |
127 | | - }); |
128 | | - |
129 | | - expect(root.getRenderedOutput({props: ['opacity']}).toJSX()).toEqual( |
130 | | - <rn-view opacity="0.5"> |
131 | | - <rn-androidProgressBar /> |
132 | | - </rn-view>, |
133 | | - ); |
134 | | - }); |
135 | | - }); |
136 | | - |
137 | | - describe('accessibilityLabel', () => { |
138 | | - it('is propagated to the native component', () => { |
139 | | - const root = Fantom.createRoot(); |
140 | | - |
141 | | - Fantom.runTask(() => { |
142 | | - root.render( |
143 | | - <ActivityIndicator accessibilityLabel="Loading content" />, |
144 | | - ); |
145 | | - }); |
146 | | - |
147 | | - expect( |
148 | | - root.getRenderedOutput({props: ['accessibilityLabel']}).toJSX(), |
149 | | - ).toEqual( |
150 | | - <rn-androidProgressBar accessibilityLabel="Loading content" />, |
151 | | - ); |
152 | | - }); |
153 | | - }); |
154 | | - |
155 | | - describe('testID', () => { |
156 | | - it('is propagated to the native component', () => { |
157 | | - const root = Fantom.createRoot(); |
158 | | - |
159 | | - Fantom.runTask(() => { |
160 | | - root.render(<ActivityIndicator testID="loading-spinner" />); |
161 | | - }); |
162 | | - |
163 | | - expect(root.getRenderedOutput({props: ['testID']}).toJSX()).toEqual( |
164 | | - <rn-androidProgressBar testID="loading-spinner" />, |
165 | | - ); |
166 | | - }); |
167 | | - }); |
| 23 | + return root.getRenderedOutput({props: ['width', 'height']}).toJSX(); |
| 24 | +} |
| 25 | + |
| 26 | +describe('ActivityIndicator', () => { |
| 27 | + it('renders the default (small) size', () => { |
| 28 | + expect(renderSizeOutput(<ActivityIndicator />)).toEqual( |
| 29 | + <rn-androidProgressBar width="20" height="20" />, |
| 30 | + ); |
168 | 31 | }); |
169 | 32 |
|
170 | | - describe('ref', () => { |
171 | | - it('provides a valid HTMLElement instance', () => { |
172 | | - const elementRef = createRef<HostInstance>(); |
173 | | - const root = Fantom.createRoot(); |
174 | | - |
175 | | - Fantom.runTask(() => { |
176 | | - root.render(<ActivityIndicator ref={elementRef} />); |
177 | | - }); |
178 | | - |
179 | | - expect(elementRef.current).toBeInstanceOf(HTMLElement); |
180 | | - }); |
181 | | - |
182 | | - it('has the correct tag name', () => { |
183 | | - const elementRef = createRef<HostInstance>(); |
184 | | - const root = Fantom.createRoot(); |
| 33 | + it('renders the large size', () => { |
| 34 | + expect(renderSizeOutput(<ActivityIndicator size="large" />)).toEqual( |
| 35 | + <rn-androidProgressBar width="36" height="36" />, |
| 36 | + ); |
| 37 | + }); |
185 | 38 |
|
186 | | - Fantom.runTask(() => { |
187 | | - root.render(<ActivityIndicator ref={elementRef} />); |
188 | | - }); |
| 39 | + it('renders a numeric size as an explicit width/height', () => { |
| 40 | + expect(renderSizeOutput(<ActivityIndicator size={42} />)).toEqual( |
| 41 | + <rn-androidProgressBar width="42" height="42" />, |
| 42 | + ); |
| 43 | + }); |
189 | 44 |
|
190 | | - const element = nullthrows(elementRef.current); |
191 | | - expect(element.tagName).toBe('RN:AndroidProgressBar'); |
192 | | - }); |
| 45 | + it('renders with color, animating and hidesWhenStopped props applied', () => { |
| 46 | + // color/animating/hidesWhenStopped are forwarded to the native component; |
| 47 | + // the mounted size still reflects the (default, small) size. |
| 48 | + expect( |
| 49 | + renderSizeOutput( |
| 50 | + <ActivityIndicator |
| 51 | + color="#ff0000" |
| 52 | + animating={false} |
| 53 | + hidesWhenStopped={false} |
| 54 | + />, |
| 55 | + ), |
| 56 | + ).toEqual(<rn-androidProgressBar width="20" height="20" />); |
193 | 57 | }); |
194 | 58 | }); |
0 commit comments