@ledvance/base 1.3.109 → 1.3.110

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -4,7 +4,7 @@
4
4
  "name": "@ledvance/base",
5
5
  "pid": [],
6
6
  "uiid": "",
7
- "version": "1.3.109",
7
+ "version": "1.3.110",
8
8
  "scripts": {
9
9
  "prepublishOnly": "python update-localazy.py"
10
10
  },
@@ -1,44 +1,43 @@
1
- import {View} from 'react-native'
2
- import React, {useCallback} from 'react'
1
+ import { hex2Hsv, hsv2Hex } from '@utils'
2
+ import { useReactive, useUpdateEffect } from 'ahooks'
3
+ import React, { useCallback } from 'react'
4
+ import { StyleSheet, View } from 'react-native'
5
+ import { Utils } from 'tuya-panel-kit'
6
+ import I18n from '../i18n/index'
7
+ import { useNewPalette } from '../models/modules/NativePropsSlice'
8
+ import LdvColorBrightness from './ldvColorBrightness'
3
9
  import LdvColorSlider from './ldvColorSlider'
4
- import {hex2Hsv, hsv2Hex} from '@utils'
5
10
  import LdvPresetView from './ldvPresetView'
6
11
  import LdvSaturation from './ldvSaturation'
7
- import LdvColorBrightness from './ldvColorBrightness'
8
- import I18n from '../i18n/index'
9
12
  import RectColorAndBrightPicker from './rect-color-and-bright-picker'
10
- import {Utils} from "tuya-panel-kit";
11
- import {useReactive, useUpdateEffect} from "ahooks";
12
- import {useNewPalette, useIsPad} from "../models/modules/NativePropsSlice";
13
13
  import Spacer from './Spacer'
14
14
 
15
- const {convertX: cx, width: screenWidth} = Utils.RatioUtils
15
+ // 只引入 cx 用于尺寸转换
16
+ const { convertX: cx } = Utils.RatioUtils
16
17
  const scaleUp = (value) => value * 10
17
18
  const scaleDown = (value) => Math.round(value / 10)
18
19
 
19
20
  export interface ColorAdjustViewProps {
20
- h: number
21
- s: number
22
- v: number
23
- minBrightness?: number // 最小亮度
24
- minSaturation?: number // 最小Saturation
25
- reserveSV?: boolean // 保留 s v
26
- hideSat?: boolean // 隐藏saturation
27
- onHSVChange?: (h: number, s: number, v: number) => void
28
- onHSVChangeComplete: (h: number, s: number, v: number) => void
21
+ h: number;
22
+ s: number;
23
+ v: number;
24
+ minBrightness?: number;
25
+ minSaturation?: number;
26
+ reserveSV?: boolean;
27
+ hideSat?: boolean;
28
+ onHSVChange?: (h: number, s: number, v: number) => void;
29
+ onHSVChangeComplete: (h: number, s: number, v: number) => void;
29
30
  }
30
31
 
31
32
  const NewColorPicker = React.memo((props: ColorAdjustViewProps) => {
32
33
  const { h = 0, s = 100, v = 100, minBrightness, onHSVChange, onHSVChangeComplete } = props
33
- const isPad = useIsPad()
34
- const width = isPad ? cx(screenWidth - 10) : (screenWidth - 80)
34
+
35
35
  const state = useReactive({
36
36
  hue: h,
37
37
  saturation: scaleUp(s),
38
38
  value: scaleUp(v),
39
39
  moving: false
40
40
  })
41
-
42
41
  useUpdateEffect(() => {
43
42
  if (!state.moving) {
44
43
  state.hue = h
@@ -46,33 +45,22 @@ const NewColorPicker = React.memo((props: ColorAdjustViewProps) => {
46
45
  state.value = scaleUp(v)
47
46
  }
48
47
  }, [h, s, v])
49
-
50
48
  const handleMove = useCallback((v) => {
51
49
  onHSVChange?.(v.hue, scaleDown(v.saturation), scaleDown(v.value))
52
50
  }, [onHSVChange])
53
-
54
51
  const handleComplete = useCallback((v) => {
55
52
  onHSVChangeComplete?.(v.hue, scaleDown(v.saturation), scaleDown(v.value))
56
53
  state.moving = false
57
54
  }, [onHSVChangeComplete])
58
-
59
- const { hue, saturation, value } = state;
60
- const hsv = { hue, saturation, value };
55
+ const { hue, saturation, value } = state
56
+ const hsv = { hue, saturation, value }
61
57
  const minBrightnessValue = minBrightness ?? 1
62
-
63
58
  return (
64
- <View style={{justifyContent: 'center', alignItems: 'center'}}>
65
- <View style={{
66
- width: width,
67
- height: cx(200),
68
- borderRadius: cx(10),
69
- borderColor: '#eeeeef',
70
- borderWidth: 1,
71
- overflow: 'hidden'
72
- }}>
59
+ <View style={styles.container}>
60
+ <View style={styles.pickerWrapper}>
73
61
  <RectColorAndBrightPicker.ColourPicker
74
62
  value={hsv}
75
- brightOption={{min: scaleUp(minBrightnessValue), minPercent: minBrightnessValue ? minBrightnessValue : 0}}
63
+ brightOption={{ min: scaleUp(minBrightnessValue), minPercent: minBrightnessValue ? minBrightnessValue : 0 }}
76
64
  onGrant={() => state.moving = true}
77
65
  onMove={handleMove}
78
66
  onRelease={handleComplete}
@@ -83,6 +71,23 @@ const NewColorPicker = React.memo((props: ColorAdjustViewProps) => {
83
71
  )
84
72
  })
85
73
 
74
+ const styles = StyleSheet.create({
75
+ container: {
76
+ // 为整个组件提供水平内边距,使其自适应
77
+ paddingHorizontal: cx(16),
78
+ },
79
+ pickerWrapper: {
80
+ // 高度保持不变
81
+ height: cx(200),
82
+ // 圆角、边框等样式保持不变
83
+ borderRadius: cx(10),
84
+ borderColor: '#eeeeef',
85
+ borderWidth: 1,
86
+ overflow: 'hidden',
87
+ // 这里不再需要 width 属性,它会自动填充父容器
88
+ },
89
+ })
90
+
86
91
  const OldColorPicker = React.memo((props: ColorAdjustViewProps) => {
87
92
  return (
88
93
  <View>
@@ -1,31 +1,30 @@
1
- import {View} from 'react-native'
2
- import React, {useCallback} from 'react'
1
+ import { StyleSheet, View } from 'react-native'
2
+ import React, { useCallback } from 'react'
3
3
  import LdvColorSlider from './ldvColorSlider'
4
4
  import Spacer from './Spacer'
5
5
  import LdvPresetView from './ldvPresetView'
6
6
  import LdvSlider from './ldvSlider'
7
- import {Utils} from 'tuya-panel-kit'
7
+ import { Utils } from 'tuya-panel-kit'
8
8
  import I18n from '../i18n/index'
9
- import {cctToColor} from '../utils/cctUtils'
10
- import RectColorAndBrightPicker from "./rect-color-and-bright-picker";
11
- import {useReactive, useUpdateEffect} from 'ahooks'
12
- import { useNewPalette, useIsPad } from 'models/modules/NativePropsSlice'
9
+ import { cctToColor } from '../utils/cctUtils'
10
+ import RectColorAndBrightPicker from './rect-color-and-bright-picker'
11
+ import { useReactive, useUpdateEffect } from 'ahooks'
12
+ import { useNewPalette } from 'models/modules/NativePropsSlice'
13
13
 
14
- const {convertX: cx, width: screenWidth} = Utils.RatioUtils
15
-
16
- const scaleUp = (value: number) => value * 10;
17
- const scaleDown = (value: number) => Math.round(value / 10);
14
+ const { convertX: cx } = Utils.RatioUtils
15
+ const scaleUp = (value: number) => value * 10
16
+ const scaleDown = (value: number) => Math.round(value / 10)
18
17
 
19
18
  export interface ColorTempAdjustViewProps {
20
- colorTemp: number
21
- brightness: number
22
- minBrightness?: number
23
- isSupportTemperature: boolean
24
- isSupportBrightness: boolean
25
- onCCTChange?: (cct: number) => void
26
- onCCTChangeComplete: (cct: number) => void
27
- onBrightnessChange?: (brightness: number) => void
28
- onBrightnessChangeComplete: (brightness: number) => void
19
+ colorTemp: number;
20
+ brightness: number;
21
+ minBrightness?: number;
22
+ isSupportTemperature: boolean;
23
+ isSupportBrightness: boolean;
24
+ onCCTChange?: (cct: number) => void;
25
+ onCCTChangeComplete: (cct: number) => void;
26
+ onBrightnessChange?: (brightness: number) => void;
27
+ onBrightnessChangeComplete: (brightness: number) => void;
29
28
  }
30
29
 
31
30
  const NewColorTempPicker = React.memo((props: ColorTempAdjustViewProps) => {
@@ -40,18 +39,14 @@ const NewColorTempPicker = React.memo((props: ColorTempAdjustViewProps) => {
40
39
  onBrightnessChange,
41
40
  onBrightnessChangeComplete,
42
41
  } = props
43
- const isPad = useIsPad()
44
- const width = isPad ? cx(screenWidth - 10) : (screenWidth - 80)
42
+
45
43
  const state = useReactive({
46
44
  temperature: scaleUp(colorTemp),
47
45
  brightness: scaleUp(brightness),
48
- moving: false
46
+ moving: false,
49
47
  })
50
-
51
48
  useUpdateEffect(() => {
52
49
  if (!state.moving) {
53
- // 外部props更新时同步内部状态
54
-
55
50
  state.temperature = scaleUp(colorTemp)
56
51
  state.brightness = scaleUp(brightness)
57
52
  }
@@ -86,27 +81,21 @@ const NewColorTempPicker = React.memo((props: ColorTempAdjustViewProps) => {
86
81
  const { temperature, brightness: stateBrightness } = state
87
82
  const white = { temperature, brightness: stateBrightness }
88
83
  const minBrightnessValue = minBrightness ?? 1
89
- const height = cx(isSupportTemperature? 200 : (isSupportBrightness ? 45 : 0))
84
+
85
+ const height = cx(isSupportTemperature ? 200 : (isSupportBrightness ? 45 : 0))
90
86
  const borderWidth = (isSupportTemperature || isSupportBrightness) ? 1 : 0
91
87
  return (
92
- <View style={{justifyContent: 'center', alignItems: 'center'}}>
93
- <View style={{
94
- width: width,
95
- height: height,
96
- borderRadius: cx(10),
97
- borderColor: '#eeeeef',
98
- borderWidth: borderWidth,
99
- overflow: 'hidden'
100
- }}>
88
+ <View style={styles.container}>
89
+ <View style={[styles.pickerWrapper, { height, borderWidth }]}>
101
90
  {
102
91
  isSupportTemperature ? <RectColorAndBrightPicker.WhitePicker
103
92
  value={white}
104
- brightOption={{min: scaleUp(minBrightnessValue), minPercent: minBrightnessValue ? minBrightnessValue : 0}}
93
+ brightOption={{ min: scaleUp(minBrightnessValue), minPercent: minBrightnessValue ? minBrightnessValue : 0 }}
105
94
  onGrant={() => state.moving = true}
106
95
  onMove={handleMove}
107
96
  onRelease={handleComplete}
108
97
  onPress={handleComplete}
109
- /> : isSupportBrightness ? <RectColorAndBrightPicker.BrightnessSlider
98
+ /> : isSupportBrightness ? <RectColorAndBrightPicker.BrightnessSlider
110
99
  value={stateBrightness}
111
100
  min={scaleUp(minBrightnessValue)}
112
101
  minPercent={minBrightnessValue ? minBrightnessValue : 0}
@@ -115,14 +104,26 @@ const NewColorTempPicker = React.memo((props: ColorTempAdjustViewProps) => {
115
104
  onMove={handleBrightnessMove}
116
105
  onRelease={handleBrightnessComplete}
117
106
  onPress={handleBrightnessComplete}
118
- /> : <></>
107
+ /> : null // 使用 null 代替 <></> 更为标准
119
108
  }
120
-
121
109
  </View>
122
110
  </View>
123
111
  )
124
112
  })
125
113
 
114
+ const styles = StyleSheet.create({
115
+ container: {
116
+ // 定义水平内边距,让组件自适应
117
+ paddingHorizontal: cx(16),
118
+ },
119
+ pickerWrapper: {
120
+ // 定义基础样式,移除 width
121
+ borderRadius: cx(10),
122
+ borderColor: '#eeeeef',
123
+ overflow: 'hidden',
124
+ },
125
+ })
126
+
126
127
  const OldColorTempPicker = React.memo((props: ColorTempAdjustViewProps) => {
127
128
  return (
128
129
  <View>
@@ -138,7 +139,7 @@ const OldColorTempPicker = React.memo((props: ColorTempAdjustViewProps) => {
138
139
  <Spacer height={cx(10)}/>
139
140
  <LdvPresetView
140
141
  type={'temperature'}
141
- style={{height: cx(60)}}
142
+ style={{ height: cx(60) }}
142
143
  onPress={item => {
143
144
  props.onCCTChangeComplete(item.value)
144
145
  }}/>
@@ -1,36 +1,46 @@
1
- import LinearGradientLine from './LinearGradientLine'
2
- import React from 'react'
3
- import {Utils} from 'tuya-panel-kit'
4
- import {StyleProp, StyleSheet, ViewStyle} from 'react-native'
5
- import ColorsLine from './ColorsLine'
6
- import {useIsPad} from '../models/modules/NativePropsSlice'
1
+ // MoodColorsLine.tsx (接收显式 width 的版本)
7
2
 
8
- const { convertX: cx, width: screenWidth } = Utils.RatioUtils
3
+ import LinearGradientLine from './LinearGradientLine';
4
+ import React from 'react';
5
+ import { Utils } from 'tuya-panel-kit';
6
+ import { StyleProp, StyleSheet, ViewStyle } from 'react-native';
7
+ import ColorsLine from './ColorsLine';
9
8
 
10
- export type MoodColorsLineType = 'gradient' | 'separate'
9
+ const { convertX: cx } = Utils.RatioUtils;
10
+
11
+ export type MoodColorsLineType = 'gradient' | 'separate';
11
12
 
12
13
  interface MoodColorsLineProps {
13
- width?: number
14
- height?: number
15
- type: MoodColorsLineType
16
- colors: string[]
17
- nodeStyle?: StyleProp<ViewStyle>
14
+ width: number; // 【关键】: 明确要求一个数字类型的 width
15
+ height?: number;
16
+ type: MoodColorsLineType;
17
+ colors: string[];
18
+ nodeStyle?: StyleProp<ViewStyle>;
19
+ style?: StyleProp<ViewStyle>; // style prop 仍然保留,以备不时之需
18
20
  }
19
21
 
20
22
  export default function MoodColorsLine(props: MoodColorsLineProps) {
21
- const isPad = useIsPad()
22
- const width = props.width || (isPad ? cx(screenWidth - 10) : (screenWidth - 80))
23
- const height = props.height || cx(24)
24
- if (props.type === 'separate' || props.colors.length < 2) {
25
- return (<ColorsLine colors={props.colors} style={{width, height}} nodeStyle={props.nodeStyle}/>)
23
+ const { width, type, colors, nodeStyle, style } = props;
24
+ const height = props.height || cx(24);
25
+
26
+ // 子组件现在使用明确传入的数字 width
27
+ if (type === 'separate' || colors.length < 2) {
28
+ return (
29
+ <ColorsLine
30
+ colors={colors}
31
+ style={[{ width, height }, style]} // 将数字 width 和 height 应用到 style
32
+ nodeStyle={nodeStyle}
33
+ />
34
+ );
26
35
  } else {
27
36
  return (
28
37
  <LinearGradientLine
29
- width={width}
38
+ width={width} // 将数字 width 作为 prop 传递
30
39
  height={height}
31
- style={styles.gradient}
32
- colors={props.colors}/>
33
- )
40
+ style={[styles.gradient, style]}
41
+ colors={colors}
42
+ />
43
+ );
34
44
  }
35
45
  }
36
46
 
@@ -38,4 +48,4 @@ const styles = StyleSheet.create({
38
48
  gradient: {
39
49
  borderRadius: cx(8),
40
50
  },
41
- })
51
+ });
@@ -1,12 +1,11 @@
1
- import React, { useMemo } from 'react'
2
- import {StyleProp, StyleSheet, Text, View, ViewStyle} from 'react-native'
3
- import {LinearGradient, Slider, Utils} from 'tuya-panel-kit'
4
- import {Rect} from 'react-native-svg'
5
- import ThemeType from '../config/themeType'
6
- import { useIsPad } from '../models/modules/NativePropsSlice'
1
+ import React, { useMemo, useState } from 'react';
2
+ import { StyleProp, StyleSheet, Text, View, ViewStyle, LayoutChangeEvent } from 'react-native';
3
+ import { LinearGradient, Slider, Utils } from 'tuya-panel-kit';
4
+ import { Rect } from 'react-native-svg';
5
+ import ThemeType from '../config/themeType';
7
6
 
8
- const { convertX: cx, width: screenWidth } = Utils.RatioUtils
9
- const { withTheme } = Utils.ThemeUtils
7
+ const { convertX: cx } = Utils.RatioUtils;
8
+ const { withTheme } = Utils.ThemeUtils;
10
9
 
11
10
  const temperatures = {
12
11
  '0%': 'rgb(254, 172, 90)',
@@ -15,7 +14,7 @@ const temperatures = {
15
14
  '60%': 'rgb(252, 250, 242)',
16
15
  '80%': 'rgb(226, 235, 248)',
17
16
  '100%': 'rgb(194, 217, 254)',
18
- }
17
+ };
19
18
 
20
19
  const colors = {
21
20
  '0%': 'rgb(255, 0, 0)',
@@ -25,31 +24,38 @@ const colors = {
25
24
  '65%': 'rgb(43, 0, 255)',
26
25
  '80%': 'rgb(180, 0, 255)',
27
26
  '100%': 'rgb(255, 0, 0)',
28
- }
27
+ };
29
28
 
30
- export const TEMP_KEY = 'temperature'
29
+ export const TEMP_KEY = 'temperature';
31
30
 
32
31
  interface LdvColorSliderProps {
33
- theme?: ThemeType
34
- title: string,
35
- type: string,
36
- onValueChange?: (number) => void | undefined,
37
- onSlidingComplete: (number) => void,
38
- thumbColor: string,
39
- value: number,
40
- width?: number | undefined,
41
- style?: StyleProp<ViewStyle> | undefined
32
+ theme?: ThemeType;
33
+ title: string;
34
+ type: string;
35
+ onValueChange?: (number) => void | undefined;
36
+ onSlidingComplete: (number) => void;
37
+ thumbColor: string;
38
+ value: number;
39
+ width?: number | undefined;
40
+ style?: StyleProp<ViewStyle> | undefined;
42
41
  }
43
42
 
44
43
  const LdvColorSlider = (props: LdvColorSliderProps) => {
45
- const {title, type, onSlidingComplete, thumbColor, value} = props
46
- const isPad = useIsPad()
47
- let dataSource = type === TEMP_KEY ? temperatures : colors
48
- let max = type === TEMP_KEY ? 100 : 359
49
- let min = type === TEMP_KEY ? 0 : 0
50
- const width = props.width || (isPad ? cx(screenWidth - 10) : (screenWidth - 80))
44
+ const { title, type, onSlidingComplete, thumbColor, value } = props;
45
+ const dataSource = type === TEMP_KEY ? temperatures : colors;
46
+ const max = type === TEMP_KEY ? 100 : 359;
47
+ const min = type === TEMP_KEY ? 0 : 0;
48
+
49
+ const [sliderWidth, setSliderWidth] = useState(0);
51
50
 
52
- const styles = useMemo(() => getStyles(props.theme), [props.theme])
51
+ const styles = useMemo(() => getStyles(props.theme), [props.theme]);
52
+
53
+ const handleLayout = (event: LayoutChangeEvent) => {
54
+ const { width } = event.nativeEvent.layout;
55
+ if (width > 0 && width !== sliderWidth) {
56
+ setSliderWidth(width);
57
+ }
58
+ };
53
59
 
54
60
  return (
55
61
  <View style={[styles.container, props.style]}>
@@ -58,8 +64,8 @@ const LdvColorSlider = (props: LdvColorSliderProps) => {
58
64
  </Text>
59
65
  <Slider.Horizontal
60
66
  accessibilityLabel={"ColorSliderHorizontal"}
61
- style={{...styles.shadeSlider, width}}
62
- styles={{track: styles.sliderTrack, thumb: {...styles.shadeThumb, backgroundColor: thumbColor}}}
67
+ style={styles.shadeSlider}
68
+ styles={{ track: styles.sliderTrack, thumb: { ...styles.shadeThumb, backgroundColor: thumbColor } }}
63
69
  maximumValue={max}
64
70
  minimumValue={min}
65
71
  value={value}
@@ -71,32 +77,39 @@ const LdvColorSlider = (props: LdvColorSliderProps) => {
71
77
  onlyMaximumTrack={true}
72
78
  renderMaximumTrack={() => {
73
79
  return (
74
- <View style={{flex: 1, borderRadius: cx(15)}}>
75
- <LinearGradient
76
- style={{...styles.sliderLinearGradient, width}}
77
- x1="0%"
78
- y1="0%"
79
- x2="100%"
80
- y2="0%"
81
- stops={dataSource}>
82
- <Rect {...styles.sliderLinearGradient} width={width}/>
83
- </LinearGradient>
80
+ <View style={{ flex: 1, borderRadius: cx(15), overflow: 'hidden' }} onLayout={handleLayout}>
81
+ {sliderWidth > 0 && (
82
+ <LinearGradient
83
+ // 【关键改动 1】: 合并样式,使用样式表中的 height 和 state 中的 width
84
+ style={[styles.sliderLinearGradient, { width: sliderWidth }]}
85
+ x1="0%"
86
+ y1="0%"
87
+ x2="100%"
88
+ y2="0%"
89
+ stops={dataSource}>
90
+ {/* 【关键改动 2】: 为 Rect 提供明确的、数字类型的 height 和 width */}
91
+ <Rect
92
+ height={styles.sliderLinearGradient.height} // 使用样式表中的数字高度
93
+ width={sliderWidth} // 使用 state 中的数字宽度
94
+ />
95
+ </LinearGradient>
96
+ )}
84
97
  </View>
85
- )
98
+ );
86
99
  }}
87
100
  onValueChange={props.onValueChange}
88
101
  onSlidingComplete={onSlidingComplete}
89
102
  />
90
103
  </View>
91
- )
92
- }
104
+ );
105
+ };
93
106
 
94
107
  const getStyles = (theme?: ThemeType) =>
95
108
  StyleSheet.create({
96
109
  container: {
97
110
  height: cx(57),
98
111
  flexDirection: 'column',
99
- paddingStart: cx(16),
112
+ paddingHorizontal: cx(17),
100
113
  },
101
114
  title: {
102
115
  marginTop: cx(4),
@@ -130,12 +143,13 @@ const getStyles = (theme?: ThemeType) =>
130
143
  height: cx(4),
131
144
  },
132
145
  },
146
+ // 【关键】: 这个样式定义了渐变层的数字高度
133
147
  sliderLinearGradient: {
134
148
  height: cx(12),
135
149
  },
136
150
  presetView: {
137
151
  height: cx(60),
138
152
  },
139
- })
153
+ });
140
154
 
141
- export default withTheme(LdvColorSlider)
155
+ export default withTheme(LdvColorSlider);