feat(components): DialTile for sensor signal rows
This commit is contained in:
1 parent
bea019fb0f
commit
8232882977
2 files changed
+99
No files matched your search
@@ -0,0 +1,34 @@
|
||||
import React from 'react';
|
||||
import TestRenderer from 'react-test-renderer';
|
||||
|
||||
import { DialTile } from '../components/DialTile';
|
||||
|
||||
describe('DialTile', () => {
|
||||
it('renders label and value', () => {
|
||||
let tree: any;
|
||||
TestRenderer.act(() => {
|
||||
tree = TestRenderer.create(React.createElement(DialTile, { label: 'RSSI', value: '-61 dBm', testID: 'dial' }));
|
||||
});
|
||||
const json = JSON.stringify(tree.toJSON());
|
||||
expect(json).toContain('RSSI');
|
||||
expect(json).toContain('-61 dBm');
|
||||
});
|
||||
|
||||
it('combines label and value into accessibilityLabel', () => {
|
||||
let tree: any;
|
||||
TestRenderer.act(() => {
|
||||
tree = TestRenderer.create(React.createElement(DialTile, { label: 'RSSI', value: '-61 dBm', testID: 'dial' }));
|
||||
});
|
||||
const json = JSON.stringify(tree.toJSON());
|
||||
expect(json).toContain('"accessibilityLabel":"RSSI: -61 dBm"');
|
||||
});
|
||||
|
||||
it('uses action color when tone=red', () => {
|
||||
let tree: any;
|
||||
TestRenderer.act(() => {
|
||||
tree = TestRenderer.create(React.createElement(DialTile, { label: 'X', value: 'Y', tone: 'red', testID: 'dial' }));
|
||||
});
|
||||
const json = JSON.stringify(tree.toJSON());
|
||||
expect(json).toContain('#E23B2E');
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,65 @@
|
||||
import React from 'react';
|
||||
import { StyleSheet, Text, View, type ViewStyle } from 'react-native';
|
||||
import { colors, spacing, typography } from '../theme';
|
||||
|
||||
type Tone = 'amber' | 'green' | 'red';
|
||||
|
||||
type Props = {
|
||||
readonly label: string;
|
||||
readonly value: string;
|
||||
readonly tone?: Tone;
|
||||
readonly testID?: string;
|
||||
};
|
||||
|
||||
function toneColor(tone: Tone | undefined): string {
|
||||
if (tone === 'red') return colors.action;
|
||||
if (tone === 'green') return colors.success;
|
||||
return colors.warning;
|
||||
}
|
||||
|
||||
export function DialTile({ label, value, tone = 'amber', testID }: Props) {
|
||||
const markerStyle: ViewStyle = { backgroundColor: toneColor(tone) };
|
||||
return (
|
||||
<View
|
||||
accessibilityLabel={`${label}: ${value}`}
|
||||
style={styles.row}
|
||||
testID={testID}
|
||||
>
|
||||
<View style={styles.markerWrap}>
|
||||
<View style={[styles.marker, markerStyle]} />
|
||||
</View>
|
||||
<Text style={styles.value}>{value}</Text>
|
||||
<Text style={styles.label}>{label}</Text>
|
||||
</View>
|
||||
);
|
||||
}
|
||||
|
||||
const styles = StyleSheet.create({
|
||||
row: {
|
||||
minHeight: 56,
|
||||
flexDirection: 'row',
|
||||
alignItems: 'center',
|
||||
borderTopWidth: 1,
|
||||
borderColor: colors.line,
|
||||
paddingVertical: spacing.sm,
|
||||
paddingHorizontal: spacing.md,
|
||||
gap: spacing.md,
|
||||
},
|
||||
markerWrap: {
|
||||
width: 4,
|
||||
height: 32,
|
||||
justifyContent: 'center',
|
||||
},
|
||||
marker: {
|
||||
width: 2,
|
||||
height: 32,
|
||||
},
|
||||
value: {
|
||||
...typography.detailNumeric,
|
||||
flex: 1,
|
||||
},
|
||||
label: {
|
||||
...typography.label,
|
||||
color: colors.textDim,
|
||||
},
|
||||
});
|
||||
Reference in new issue
Block a user