Created
August 3, 2020 01:35
-
-
Save bmfurtado/06aa9f6f4ef512673000aa1d3de9bced to your computer and use it in GitHub Desktop.
Map IR codes for smartir climate stuff
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import base64 | |
import broadlink | |
import click | |
import json | |
import pdb | |
def split_csv(ctx, param, value): | |
return [x.strip() for x in value.split(',')] | |
def generate_temps(min, max, step): | |
n = min | |
while n <= max: | |
yield n | |
n = n + step | |
def choose_broadlink(): | |
print('Discovering broadlinks in network...') | |
devices = broadlink.discover(timeout=10) | |
choices = list(range(len(devices))) | |
for i, device in enumerate(devices): | |
print('{}: {} [{}]'.format(i, device.model, device.host[0])) | |
while True: | |
choice = click.prompt('Choose a broadlink device.', type=int) | |
if choice in list(range(len(devices))): | |
break | |
print('Invalid choice, options are {}.'.format(choices)) | |
return devices[choice] | |
def learn_code(device, message): | |
device.enter_learning() | |
while not click.confirm(message, default=True): | |
device.enter_learning() | |
code = base64.b64encode(device.check_data()).decode() | |
print('Learned {}'.format(code)) | |
return code | |
def format_float(x): | |
return ('%f' % x).rstrip('0').rstrip('.') | |
@click.command() | |
@click.option('--outfile', type=click.File('w'), required=True) | |
@click.option('--manufacturer', prompt=True) | |
@click.option('--models', callback=split_csv, prompt=True) | |
@click.option('--min-temp', prompt=True, type=click.FLOAT) | |
@click.option('--max-temp', prompt=True, type=click.FLOAT) | |
@click.option('--temp-precision', prompt=True, type=click.FLOAT) | |
@click.option('--modes', prompt=True, callback=split_csv) | |
@click.option('--fan-modes', prompt=True, callback=split_csv) | |
def generate(outfile, manufacturer, models, min_temp, max_temp, temp_precision, modes, fan_modes): | |
device = choose_broadlink() | |
device.auth() | |
codes = { | |
'manufacturer': manufacturer, | |
'supportedModels': models, | |
'supportedController': 'Broadlink', | |
'commandsEncoding': 'Base64', | |
'minTemperature': min_temp, | |
'maxTemperature': max_temp, | |
'precision': temp_precision, | |
'operationModes': modes, | |
'fanModes': fan_modes, | |
} | |
commands = {} | |
for mode in modes: | |
commands[mode] = {} | |
print('Starting collection of mode {}.'.format(mode)) | |
first_fan_mode = True | |
for fan_mode in fan_modes: | |
print('Starting collection of fan mode {}.'.format(fan_mode)) | |
if not first_fan_mode and click.confirm('Do you want to skip this mode?'): | |
commands[mode][fan_mode] = commands[mode][list(commands[mode].keys())[0]] | |
continue | |
first_fan_mode = False | |
commands[mode][fan_mode] = {} | |
if click.confirm('Does this mode support temperatures?', default=True): | |
for t in generate_temps(min_temp, max_temp, temp_precision): | |
temp = format_float(t) | |
commands[mode][fan_mode][temp] = learn_code(device, 'Send code for {}/{}/{} and press enter.'.format(mode, fan_mode, temp)) | |
else: | |
code = learn_code(device, 'Send code for {}/{} and press enter.'.format(mode, fan_mode)) | |
for t in generate_temps(min_temp, max_temp, temp_precision): | |
temp = format_float(t) | |
commands[mode][fan_mode][temp] = code | |
commands['off'] = learn_code(device, 'Send code for off and press enter.') | |
codes['commands'] = commands | |
json.dump(codes, outfile) | |
if __name__ == '__main__': | |
generate() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment