Skip to content

Instantly share code, notes, and snippets.

@fragtion
Created January 6, 2025 17:30
Show Gist options
  • Save fragtion/dfe50ded016398e9b0384d354bc5433d to your computer and use it in GitHub Desktop.
Save fragtion/dfe50ded016398e9b0384d354bc5433d to your computer and use it in GitHub Desktop.
tasmota raw compact to legacy converter
###
# Converts Tasmota's New IR Raw compact encoding back to the legacy numerical format
# (Basically https://tasmota.hadinger.fr/util , but in Python form)
# See: https://tasmota.github.io/docs/IRSend-RAW-Encoding/
# Author: Dimitri Pappas (https://github.com/fragtion)
###
import re
import json
import sys
def convert_ir_pulse(input_string):
def round_to_5(value):
return round(abs(value) / 5) * 5
if "MQT:" in input_string:
try:
json_data = json.loads(input_string.split(" MQT: ")[1].split(" = ")[1])
raw_data = json_data['IrReceived']['RawData']
except (KeyError, json.JSONDecodeError) as e:
print("Error extracting RawData:", e)
return
else:
raw_data = input_string # Treat the whole string as raw data if no MQT: present
pulses = re.findall(r'[+-]?\d+', raw_data)
pulses = [round_to_5(int(pulse)) for pulse in pulses]
value_map = {}
next_char = 65
result = []
for pulse in pulses:
if pulse not in value_map:
value_map[pulse] = chr(next_char)
next_char += 1
output_string = ''
i = 0
while i < len(raw_data):
char = raw_data[i]
if char.isalpha():
pulse_value = None
for value, letter in value_map.items():
if letter == char.upper():
pulse_value = value
break
if pulse_value is not None:
if char.islower():
output_string += f"-{pulse_value}"
else:
output_string += f"+{pulse_value}"
i += 1
elif char in '+-':
output_string += char
i += 1
num_start = i
while i < len(raw_data) and raw_data[i].isdigit():
i += 1
num_str = raw_data[num_start:i]
if num_str:
pulse_value = round_to_5(int(num_str))
output_string += str(pulse_value)
else:
output_string += char
i += 1
pulse_values = re.findall(r'\d+', output_string)
csv_output = ','.join(pulse_values)
print(csv_output)
return output_string
if __name__ == "__main__":
input_line = sys.stdin.read().strip()
convert_ir_pulse(input_line)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment