Skip to content

Commit 75088d9

Browse files
committed
Bulb examples and BulbDevice updates
1 parent fb2e495 commit 75088d9

File tree

6 files changed

+120
-86
lines changed

6 files changed

+120
-86
lines changed

examples/bulb-music.py

Lines changed: 37 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -3,34 +3,38 @@
33
"""
44
TinyTuya - Smart Bulb RGB Music Test
55
6-
TODO: Figure out what strings to send to the bulb to
7-
represent real music data, beats, note, fades, etc.
8-
96
Author: Jason A. Cox
107
For more information see https://github.com/jasonacox/tinytuya
118
129
"""
1310
import tinytuya
1411
import time
1512
import random
13+
import os
1614

1715
#tinytuya.set_debug()
1816

19-
# SmartBulb
2017
DEVICEID = "01234567891234567890"
21-
DEVICEIP = "10.0.1.99"
22-
DEVICEKEY = "0123456789abcdef"
23-
DEVICEVERS = "3.3"
18+
DEVICEIP = "Auto" # Will try to discover the bulb on the network
19+
DEVICEKEY = "" # Leave blank to read from devices.json
20+
DEVICEVERS = 3.3 # Must be set correctly unless IP=Auto
21+
22+
# Check for environmental variables and always use those if available
23+
DEVICEID = os.getenv("DEVICEID", DEVICEID)
24+
DEVICEIP = os.getenv("DEVICEIP", DEVICEIP)
25+
DEVICEKEY = os.getenv("DEVICEKEY", DEVICEKEY)
26+
DEVICEVERS = os.getenv("DEVICEVERS", DEVICEVERS)
2427

2528
print("TinyTuya - Smart Bulb Music Test [%s]\n" % tinytuya.__version__)
2629
print('TESTING: Device %s at %s with key %s version %s' %
2730
(DEVICEID, DEVICEIP, DEVICEKEY, DEVICEVERS))
2831

2932
# Connect to Tuya BulbDevice
30-
d = tinytuya.BulbDevice(DEVICEID, DEVICEIP, DEVICEKEY)
31-
d.set_version(float(DEVICEVERS)) # IMPORTANT to always set version
32-
# Keep socket connection open between commands
33-
d.set_socketPersistent(True)
33+
d = tinytuya.BulbDevice(DEVICEID, address=DEVICEIP, local_key=DEVICEKEY, version=DEVICEVERS, persist=True)
34+
35+
if (not DEVICEIP) or (DEVICEIP == 'Auto') or (not DEVICEKEY) or (not DEVICEVERS):
36+
print('Device %s found at %s with key %r version %s' %
37+
(d.id, d.address, d.local_key, d.version))
3438

3539
# Show status of device
3640
data = d.status()
@@ -41,25 +45,30 @@
4145
d.set_mode('music')
4246
data = d.status()
4347

44-
x = 0
45-
while (x<20):
48+
# Disable waiting and receive retrying to speed up responses
49+
d.set_socketPersistent( True )
50+
d.set_sendWait( None )
51+
d.set_retry( False )
52+
53+
# Set default transition (can be ovcerridden later)
54+
d.musicmode_transition = d.MUSIC_TRANSITION_JUMP
55+
56+
for x in range(100):
4657
# Value is 0 1111 2222 3333 4444 5555
4758
# see: https://developer.tuya.com/en/docs/iot/solarlight-function-definition?id=K9tp16f086d5h#title-10-DP27(8)%3A%20music
48-
mode = 0 # 0 - hard transitions (jumping), 1 - smooth transitions (gradient)
49-
hue = random.randint(0,360) # 1111 (hue: 0–360, 0X0000–0X0168)
50-
saturation = random.randint(0,1000) # 2222 (saturation: 0–1000, 0X0000–0X03E8)
51-
brightness = random.randint(0,1000) # 3333 (brightness: 0–1000, 0X0000–0X03E8)
52-
white_brightness = 0 # 4444: indicates brightness. It ranges from 0 to 1,000.
53-
temperature = 0 # 5555: the temperature value (0–1000)
54-
value = f"{mode:01X}{hue:04X}{saturation:04X}{brightness:04X}{white_brightness:04X}{temperature:04X}"
55-
print (" > Sending %s" % value)
56-
payload = d.generate_payload(tinytuya.CONTROL, {"27": value})
57-
d.send(payload)
58-
if (x % 3):
59-
time.sleep(1) # extend every 3 beat
60-
time.sleep(0.2)
61-
x = x + 1
59+
red = random.randint(0,255)
60+
green = random.randint(0,255)
61+
blue = random.randint(0,255)
62+
63+
if (x % 6 == 0):
64+
# extend every 6 beat
65+
d.set_music_colour( red, green, blue, transition=d.MUSIC_TRANSITION_FADE )
66+
time.sleep(2)
67+
else:
68+
# Jump!
69+
d.set_music_colour( red, green, blue )
70+
time.sleep(0.1) # the bulbs seem to get upset if updates are faster than 0.1s (100ms)
6271

6372
# Done
6473
print('\nDone')
65-
d.set_white()
74+
d.turn_off()

examples/bulb-scenes.py

Lines changed: 36 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,29 +1,38 @@
11
# TinyTuya Example
22
# -*- coding: utf-8 -*-
33
"""
4-
TinyTuya - RGB SmartBulb - Scene Test for Bulbs with DPS Index 25
4+
TinyTuya - RGB SmartBulb - Scene Test for Bulbs
55
66
Author: Jason A. Cox
77
For more information see https://github.com/jasonacox/tinytuya
88
99
"""
1010
import tinytuya
1111
import time
12+
import os
13+
1214

1315
DEVICEID = "01234567891234567890"
14-
DEVICEIP = "10.0.1.99"
15-
DEVICEKEY = "0123456789abcdef"
16-
DEVICEVERS = "3.3"
16+
DEVICEIP = "Auto" # Will try to discover the bulb on the network
17+
DEVICEKEY = "" # Leave blank to read from devices.json
18+
DEVICEVERS = 3.3 # Must be set correctly unless IP=Auto
19+
20+
# Check for environmental variables and always use those if available
21+
DEVICEID = os.getenv("DEVICEID", DEVICEID)
22+
DEVICEIP = os.getenv("DEVICEIP", DEVICEIP)
23+
DEVICEKEY = os.getenv("DEVICEKEY", DEVICEKEY)
24+
DEVICEVERS = os.getenv("DEVICEVERS", DEVICEVERS)
1725

1826
print("TinyTuya - Smart Bulb String Scenes Test [%s]\n" % tinytuya.__version__)
1927
print('TESTING: Device %s at %s with key %s version %s' %
2028
(DEVICEID, DEVICEIP, DEVICEKEY, DEVICEVERS))
2129

2230
# Connect to Tuya BulbDevice
23-
d = tinytuya.BulbDevice(DEVICEID, DEVICEIP, DEVICEKEY)
24-
d.set_version(float(DEVICEVERS)) # IMPORTANT to always set version
25-
# Keep socket connection open between commands
26-
d.set_socketPersistent(True)
31+
d = tinytuya.BulbDevice(DEVICEID, address=DEVICEIP, local_key=DEVICEKEY, version=DEVICEVERS, persist=True)
32+
33+
if (not DEVICEIP) or (DEVICEIP == 'Auto') or (not DEVICEKEY) or (not DEVICEVERS):
34+
print('Device %s found at %s with key %r version %s' %
35+
(d.id, d.address, d.local_key, d.version))
2736

2837
# Show status of device
2938
data = d.status()
@@ -33,33 +42,28 @@
3342
print('\nSetting bulb mode to Scenes')
3443
d.set_mode('scene')
3544

36-
# Determine bulb type - if it has index 25 it uses strings to set scene
37-
if("dps" in data):
38-
if("25" in data["dps"]):
39-
print('\n [Bulb Type B] String based scenes compatible smartbulb detected.')
45+
if d.bulb_has_capability(d.BULB_FEATURE_SCENE_DATA):
46+
print('\n String based scenes compatible smartbulb detected.')
47+
# Example: Color rotation
48+
print(' Switch to Scene 7 - Color Rotation')
49+
d.set_scene( 7, '464602000003e803e800000000464602007803e803e80000000046460200f003e803e800000000464602003d03e803e80000000046460200ae03e803e800000000464602011303e803e800000000')
50+
time.sleep(10)
4051

41-
# Example: Color rotation
42-
print(' Scene - Color Rotation')
43-
d.set_value(25, '07464602000003e803e800000000464602007803e803e80000000046460200f003e803e800000000464602003d03e803e80000000046460200ae03e803e800000000464602011303e803e800000000')
44-
time.sleep(10)
52+
# Example: Read scene
53+
print(' Switch to Scene 1 - Reading Light')
54+
d.set_scene( 1, '0e0d0000000000000003e803e8')
55+
time.sleep(5)
4556

46-
# Example: Read scene
47-
print(' Scene - Reading Light')
48-
d.set_value(25, '010e0d0000000000000003e803e8')
57+
# You can pull the scene strings from your smartbulb by running the async_send_receive.py script
58+
# and using the SmartLife app to change between scenes.
59+
else:
60+
print('\n Your smartbulb does not appear to support string based scenes.')
61+
# Rotate through numeric scenes
62+
for n in range(1, 5):
63+
print(' Scene - %d' % n)
64+
d.set_scene(n)
4965
time.sleep(5)
5066

51-
# You can pull the scene strings from your smartbulb by running the async_send_receive.py script
52-
# and using the SmartLife app to change between scenes.
53-
54-
else:
55-
print('\n [Bulb Type A] Your smartbulb does not appear to support string based scenes.')
56-
57-
# Rotate through numeric scenes
58-
for n in range(1, 4):
59-
print(' Scene - %d' % n)
60-
d.set_scene(n)
61-
time.sleep(5)
62-
6367
# Done
6468
print('\nDone')
65-
d.set_white()
69+
d.turn_off()

examples/bulb.py

Lines changed: 16 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -12,10 +12,12 @@
1212
import os
1313
import random
1414

15+
#tinytuya.set_debug()
16+
1517
DEVICEID = "01234567891234567890"
16-
DEVICEIP = "10.0.1.99"
17-
DEVICEKEY = "0123456789abcdef"
18-
DEVICEVERS = "3.3"
18+
DEVICEIP = "Auto" # Will try to discover the bulb on the network
19+
DEVICEKEY = "" # Leave blank to read from devices.json
20+
DEVICEVERS = 3.3 # Must be set correctly unless IP=Auto
1921

2022
# Check for environmental variables and always use those if available
2123
DEVICEID = os.getenv("DEVICEID", DEVICEID)
@@ -28,18 +30,19 @@
2830
(DEVICEID, DEVICEIP, DEVICEKEY, DEVICEVERS))
2931

3032
# Connect to Tuya BulbDevice
31-
d = tinytuya.BulbDevice(DEVICEID, DEVICEIP, DEVICEKEY)
32-
d.set_version(float(DEVICEVERS)) # IMPORTANT to always set version
33-
# Keep socket connection open between commands
34-
d.set_socketPersistent(True)
33+
d = tinytuya.BulbDevice(DEVICEID, address=DEVICEIP, local_key=DEVICEKEY, version=DEVICEVERS, persist=True)
34+
35+
if (not DEVICEIP) or (DEVICEIP == 'Auto') or (not DEVICEKEY) or (not DEVICEVERS):
36+
print('Device %s found at %s with key %r version %s' %
37+
(d.id, d.address, d.local_key, d.version))
3538

3639
# Show status of device
3740
data = d.status()
3841
print('\nCurrent Status of Bulb: %r' % data)
3942

4043
# Set to full brightness warm white
4144
print('\nWarm White Test')
42-
d.set_white()
45+
d.set_white_percentage(100.0, 0.0) # 100% brightness, 0% colour temperature
4346
time.sleep(2)
4447

4548
# Power Control Test
@@ -54,8 +57,10 @@
5457
# Dimmer Test
5558
print('\nDimmer Control Test')
5659
for level in range(11):
57-
print(' Level: %d%%' % (level*10))
58-
d.set_brightness_percentage(level*10)
60+
level *= 10
61+
if not level: level = 1
62+
print(' Level: %d%%' % level)
63+
d.set_brightness_percentage(level)
5964
time.sleep(1)
6065

6166
# Colortemp Test
@@ -112,4 +117,4 @@
112117

113118
# Done
114119
print('\nDone')
115-
d.set_white()
120+
d.turn_off()

tests.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,7 @@ def test_set_colour_A(self):
116116
d = build_mock_bulb('A')
117117

118118
# act
119-
d.set_colour(255,255,255)
119+
d.set_colour(255,127,63)
120120

121121
# gather results
122122
result_cmd, result_payload = get_results_from_mock(d)
@@ -126,7 +126,7 @@ def test_set_colour_A(self):
126126
# expectations
127127
expected_cmd = tinytuya.CONTROL
128128
# expected_payload = {"dps":{"2":"colour", "5":"ffffff000000ff"}, "devId":"DEVICE_ID_HERE","uid":"DEVICE_ID_HERE", "t": ""}
129-
expected_payload = {"dps":{"1": True, "2":"colour", "5":"ffffff000000ff"}, "devId":"DEVICE_ID_HERE","uid":"DEVICE_ID_HERE", "t": ""}
129+
expected_payload = {"dps":{"1": True, "2":"colour", "5":"ff7f3f0014c0ff"}, "devId":"DEVICE_ID_HERE","uid":"DEVICE_ID_HERE", "t": ""}
130130

131131
# assert
132132
self.assertEqual(result_cmd, expected_cmd)
@@ -137,7 +137,7 @@ def test_set_colour_B(self):
137137
d = build_mock_bulb('B')
138138

139139
# act
140-
d.set_colour(255,255,255)
140+
d.set_colour(255,127,63)
141141

142142
# gather results
143143
result_cmd, result_payload = get_results_from_mock(d)
@@ -147,7 +147,7 @@ def test_set_colour_B(self):
147147
# expectations
148148
expected_cmd = tinytuya.CONTROL
149149
# expected_payload = {"dps":{"2":"colour", "5":"ffffff000000ff"}, "devId":"DEVICE_ID_HERE","uid":"DEVICE_ID_HERE", "t": ""}
150-
expected_payload = {"dps":{"20": True, "21":"colour", "24":"0000000003e8"}, "devId":"DEVICE_ID_HERE","uid":"DEVICE_ID_HERE", "t": ""}
150+
expected_payload = {"dps":{"20": True, "21":"colour", "24":"001402f003e8"}, "devId":"DEVICE_ID_HERE","uid":"DEVICE_ID_HERE", "t": ""}
151151

152152
# assert
153153
self.assertEqual(result_cmd, expected_cmd)

0 commit comments

Comments
 (0)