Coverage for src / bluetooth_sig / gatt / characteristics / audio_input_state.py: 100%

35 statements  

« prev     ^ index     » next       coverage.py v7.13.5, created at 2026-04-03 16:41 +0000

1"""Audio Input State characteristic (0x2B77).""" 

2 

3from __future__ import annotations 

4 

5from enum import IntEnum 

6 

7import msgspec 

8 

9from ..context import CharacteristicContext 

10from .base import BaseCharacteristic 

11from .utils import DataParser 

12 

13 

14class AudioInputMuteState(IntEnum): 

15 """Audio input mute state.""" 

16 

17 NOT_MUTED = 0 

18 MUTED = 1 

19 DISABLED = 2 

20 

21 

22class AudioInputGainMode(IntEnum): 

23 """Audio input gain mode.""" 

24 

25 MANUAL_ONLY = 0 

26 AUTOMATIC_ONLY = 1 

27 MANUAL = 2 

28 AUTOMATIC = 3 

29 

30 

31class AudioInputStateData(msgspec.Struct, frozen=True, kw_only=True): # pylint: disable=too-few-public-methods 

32 """Parsed data from Audio Input State characteristic. 

33 

34 Contains gain setting, mute state, gain mode, and change counter. 

35 """ 

36 

37 gain_setting: int 

38 mute: AudioInputMuteState 

39 gain_mode: AudioInputGainMode 

40 change_counter: int 

41 

42 

43class AudioInputStateCharacteristic(BaseCharacteristic[AudioInputStateData]): 

44 """Audio Input State characteristic (0x2B77). 

45 

46 org.bluetooth.characteristic.audio_input_state 

47 

48 Reports the current audio input state including gain, mute, 

49 gain mode, and change counter. 

50 """ 

51 

52 expected_length = 4 

53 

54 def _decode_value( 

55 self, data: bytearray, ctx: CharacteristicContext | None = None, *, validate: bool = True 

56 ) -> AudioInputStateData: 

57 """Parse Audio Input State data. 

58 

59 Format: gain_setting (sint8) + mute (uint8) + gain_mode (uint8) + change_counter (uint8). 

60 """ 

61 gain_setting = DataParser.parse_int8(data, 0, signed=True) 

62 mute = AudioInputMuteState(DataParser.parse_int8(data, 1, signed=False)) 

63 gain_mode = AudioInputGainMode(DataParser.parse_int8(data, 2, signed=False)) 

64 change_counter = DataParser.parse_int8(data, 3, signed=False) 

65 return AudioInputStateData( 

66 gain_setting=gain_setting, 

67 mute=mute, 

68 gain_mode=gain_mode, 

69 change_counter=change_counter, 

70 ) 

71 

72 def _encode_value(self, data: AudioInputStateData) -> bytearray: 

73 """Encode Audio Input State data to bytes.""" 

74 result = bytearray() 

75 result += DataParser.encode_int8(data.gain_setting, signed=True) 

76 result += DataParser.encode_int8(int(data.mute)) 

77 result += DataParser.encode_int8(int(data.gain_mode)) 

78 result += DataParser.encode_int8(data.change_counter) 

79 return result