- Notifications
You must be signed in to change notification settings - Fork0
Sync your RGB devices through MQTT with OpenRGB, your Desktop Wallpaper, Chroma devices, and more to come
License
sparten11740/allmylights
Folders and files
Name | Name | Last commit message | Last commit date | |
---|---|---|---|---|
Repository files navigation
I am a command line app that synchronizes your ambient lighting and RGBperipherals. I serve as a broker that consumes input values through MQTT andother sources, and applies those to a number of configurablesinks. Those can be an OpenRGB instance, Chroma enabled devices, or your Desktopwallpaper.
OpenRGB is one of the supported options to control the RGB peripherals of yourhost system.
Open source RGB lighting control that doesn't depend on manufacturer software.Supports Windows and Linux.
You can download the OpenRGB binaries in therelease section of the project's gitlab
Followthese instructionsto run a minimized OpenRGB server when logging in to your machine.
For questions around the detection of your devices, please refer to the OpenRGBcommunity.
Inputs such as profile names, or color strings are received through subscriptionof anMQTT topic.
MQTT is an OASIS standard messaging protocol for the Internet of Things (IoT).It is designed as an extremely lightweight publish/subscribe messagingtransport that is ideal for connecting remote devices with a small codefootprint and minimal network bandwidth
Given that you are looking at this page, you probably have a smart homeframework in place already and want to integrate with it. Chances are thatyou are using MQTT as part of that setup. In that case you can go ahead andskip the rest of this section. If you're using a smart home framework withoutMQTT, please refer to the following resources for getting your MQTT serverstarted and integrated.
An OpenRGB Binding for OpenHAB does not exist. However, it is somethingthat would be easy to implement.
OpenHAB has a binding that connects with an MQTT broker. Install the brokerMosquitto on your device running OpenHAB and afterwardsproceed installing theMQTT Binding.
You could then create a rule along the lines (using the rules DSL):
"Set RGB value"whenItemMy_Color_Item received command thenval actions= getActions("mqtt","mqtt:broker:mosquitto")valHSBType hsb= receivedCommandasHSBTypevalColor color=Color::getHSBColor(hsb.hue.floatValue/360, hsb.saturation.floatValue/100, hsb.brightness.floatValue/100)valString rgb=String::format("%1$02x%2$02x%3$02xFF" , color.red, color.green, color.blue) actions.publishMQTT("stat/open-rgb/RESULT", rgb)end
Download the binaries for your target platform in thereleases section (stable)or from the uploaded artifacts of themost recent workflow runs.Place them in your desired target location. You can also clone this repositoryand build the project yourself.
In order to build the binaries for Windows, you have to use a Windows machine.This is because of a framework dependency on
Microsoft.WindowsDesktop.App
that is only available on Windows. However, MacOS and Linux binaries can bebuilt and published from any host system.
First you need to install theVisual Studio Community Edition 2019on your machine.
Make suredotnet
is available in your path and run the following command fromthe project root to build a standalone.exe
(Windows):
dotnet publish --runtime win-x64 --configuration Release -p:PublishSingleFile=true --self-containedfalse
Run the following if you want the application to work on a target without the.NET runtime installed:
dotnet publish --runtime win-x64 --configuration Release -p:PublishSingleFile=true -p:PublishTrimmed=true --self-containedtrue
The required parameters such as connection details are provided in aconfiguration file calledallmylightsrc.json
(default). Hereinafter, I willadivse on what this file should look like to satisfy your requirements.
A number of usage examples can also be found inthe wiki.
The configuration distinguishes between
- sources, that provide values to the app
- transformations, that alter those values
- sinks, that consume and apply those values
- (optional routes that define from which sources to what sinks those values travel)
Any value emitted by a source is routed to all sinks unless routes are specified.
The structure of theallmylightsrc.json
is the following:
// allmylightsrc.json{"Sources":[// ... see available options below],"Sinks":[// ... see available options below],"Routes":[// ... see route section]}
Available source, sink, and transformation types are:
Type | Options |
---|---|
Source | Mqtt ,OpenRGB |
Sink | OpenRGB ,Wallpaper ,Chroma ,Mqtt |
Transformation | JsonPath ,Color ,Mapping ,Expression |
Sources produce values that are eventually consumed by sinks. All sources have aTransformations
property in common. Therein you can define transformationsthat alter the value emitted by the source to suit your requirements.
The MQTT source subscribes to a topic and emits all values that are published tothat topic.
{// optional id that can be used to define routes"Id":"my-mqtt-source","Type" :"Mqtt","Server":"192.168.1.20","Port":1883,"Topics":{// optional command topic that is used to request the current color on startup"Command":"cmnd/sonoff-1144-dimmer-5/color","Result":"stat/sonoff-1144-dimmer-5/RESULT"},// transformations are applied in order on any received message"Transformations":[// ... see section transformations for options]}
The OpenRGB source continueously polls your configured OpenRGB server and emitsan object that contains the colors per device whenever a device state changes.
{// optional id that can be used to define routes"Id":"my-openrgb-source","Type" :"OpenRGB","Server":"127.0.0.1","Port":6742,// controls how often OpenRGB is asked for changes, default is 1000ms"PollingInterval":1000,// transformations are applied in order on any received message"Transformations":[// ... see section transformations for options]}
The produced value is of typeDictionary<string, DeviceState>
where thekey is the name of your OpenRGB device andDeviceState
is a struct thathas the following properties:
publicstructDeviceState{publicIEnumerable<Color>Colors;}
To extract values from it, use theExpression
transformation such as
{"Type":"Expression","Expression":"value[\"Corsair H150i PRO RGB\"].Colors.Cast().First().ToCommaSeparatedRgbString()"}
Sinks conclude the transformation process and consume values. A sink can definetransformations which are applied on the valuebefore it is consumed by the sink.
The OpenRGB sink can receive values of typeSystem.Drawing.Color
orstring
.
Colors are applied to all devices connected to your OpenRGB instanceunless specified otherwise in the sink'sOverrides
property. A color type canbe converted from a string (such as#FF0022
orRed
) by adding aColor
transformation to the sink.
String values received by the sink have to be valid OpenRGB profile names suchasMyProfile.orp
. They end in.orp
and have to exist on your OpenRGB host.Note that a working version of the profile management API was only added incommitf63aec11
to OpenRGB. Please make sure that you have an up-to-dateversion on your machine.
{// optional id that can be used to define routes"Id":"my-openrgb-sink","Type":"OpenRGB","Server":"127.0.0.1","Port":6742,// if you want to override certain OpenRGB controlled devices you can do so here"Overrides":{// ignore an entire device"Razer Copperhead":{"Ignore":true,},"MSI Mystic Light MS_7C84":{"Zones":{// configure what color is passed to what channel of a zone"JRGB2":{"ChannelLayout":"GRB"},// ignore a single zone of a device"JRAINBOW1":{"Ignore":true}}}},// transformations can also be applied before a sink consumes a value"Transformations" :[]}
The MQTT sink publishes any value it consumes to all configured topics.
{// optional id that can be used to define routes"Id":"my-mqtt-sink","Type" :"Mqtt","Server":"192.168.1.20","Port":1883,// Optional username, remove if not required"Username":"",// Optional password, remove if not required"Password":"","Topics":["some/topic","another/topic"],"Transformations":[// ... see section transformations for options]}
The Wallpaper sink currently only works on Windows machines and only if yourun the app on the host machine itself. It can receive values of typestring
which have to be valid file paths to apply the same wallpaper to all screensor multiple file paths keyed by screen index to apply different wallpapersindividually (seethis wiki example for the latter). The command line flag--info
can be used to print availablescreen indexes. IfRelativeTo
is specified, the command also prints availablefiles under that directory.
{// optional id that can be used to define routes"Id":"my-wallpaper-sink","Type":"Wallpaper",// if the input value is a relative path or file name and RelativeTo is specified, it will be prepended to the input value"RelativeTo":"C:\\Users\\brucewayne\\Pictures\\Wallpaper","Transformations":[// one could for example map from a color to a filename here, see transformation options down below]}
The Chroma sink controls the RGB of your Chroma enabled devices. You can providevalues of typeSystem.Drawing.Color
(returned by theColor
transformation)orstring
.
It depends on the Razer Synapse software on your machine with the Chroma Connectmodule added.
AnySystem.Drawing.Color
received will be applied to all devices listed inSupportedDevices
as static effect.
Anystring
received must be valid JSON and conform to the expected Chroma SDKstructure. Examples of valid inputs can be found in theRazer Chroma SDK REST Documentation
{// optional id that can be used to define routes"Id":"my-chroma-sink","Type":"Chroma","SupportedDevices":[// can be any combination of the following"keyboard","mouse","headset","mousepad","keypad","chromalink"]}
This transformation can be used for extracting values from a JSON input.
{"Type":"JsonPath","Expression":"$.data[0].color" }
For further information on how to extract a value from JSON usingJsonPath
expressions, please refer tothis documentation.
This transformation is used to deal with the type conversion from an inputstring to a Color type that can be consumed by a sink that expects such.
{"Type":"Color","ChannelLayout":"RGBA" }
Supported values are hex strings such as the following#f2d
,#ed20ff
,#2020ffed
and color names where the name can be anyknown color.
It also supports the optional propertyChannelLayout
to deal with cases wherethe channels of a color in the hex string are mixed up for some reason such asf.i. when the first hex number does not correspond with red but with green.Possible values are any string of up to 4 characters containingR
,G
,B
,orA
for alpha. Also_
can be used to ignore values, for instance if you hadan RGBA hex string, you could use the channel layoutRGB_
to ignore the alphavalue which then will default toOxff
(255). The default for ignored colorchannels is0x00
(0);
This transformation is used to map an input value to an output value. It can beprovided a number of mappings where the first matching one is used to map theinput value. Per defaultFailOnMiss
is false so that input values that are notmatched by any mapping are simply passed through.
TheFrom
property of a mapping expects a regular expression. Please make surethat you escape any control characters if your goal is a simple string match.
{"Type":"Mapping","FailOnMiss":false,"Mappings": [ {"From":"#?FFFFFF.+","To":"#ff0000" } ] }
This transformation is used to transform a value by applying advanced logic. Anyexpression covered in thesimple expression section of the ExpressionEvaluator repocan be evaluated by this transformation. The input value provided to thistransformation is made available to the context of the expression asvalue
.
Non primitive types are also supported. For instance by prepending a colortransformation, any method or property defined in theSystem.Drawing.Color
(documentation)becomes available in the expression context on value.
{"Type":"Expression","Expression":"value.B > value.R && value.B > value.G ?\"Blueish\" :\"Some other color\"" }
A route connects a source to one or more sinks. If any route is defined inyourallmylightsrc.json
, the default behaviour of values being emittedto all sinks is no longer applied. Each sink has to be connected to at leastone source explicitly to receive values.
As a prerequisite to using routes, you need to specify IDs on your sinks andsources. A route has the following structure:
// allmylightsrc.json//..."Routes":[{// valid ID of a source defined in your config"From":"my-mqtt-source",// valid IDs of sinks defined in your config"To":["my-openrgb-sink","my-chroma-sink"]}]
Initial validation will make you aware of any unconnected sinks or sources onstartup (warning). Referencing a non-existing ID will prevent startup.
Before you start, download and install the .NET core runtimehere.
You can run the app as simple as follows (assuming theallmylightsrc.json
resides in the same directory as the executable)
.\AllMyLights.exe
You can also change the log level to one of the following:info
,debug
,warn
,error
,off
.
.\AllMyLights.exe--config/config/elsewhere/allmylightsrc.json--log-level off
As a prerequisite followMicrosoft's instructionsto install the .NET Core runtime or alternatively build the project yourselfwith the--self-contained
flag set totrue
. The latter results in aframework independant binary.
You can run the app by simply calling (assuming the default config fileallmylightsrc.json
in the same folder as the binary)
./AllMyLights
Argument | Description |
---|---|
‑‑config | Path to the config file that contains the sink & source settings. Defaultallmylightsrc.json |
‑‑fail-on-unknown-property | Fails if an unknown property is encountered in the provided config file |
‑‑export-config-schema-to | Writes the configuration schema (Open API v3) to the provided filepath. |
‑‑log-level | Change the log level to either debug, info (default), warn, error, or off. |
‑‑log-file | If provided, log output will additionally be captured in the provided file. |
‑‑minimized | Minimize to tray after startup (Windows only) |
‑‑info | List dynamic information of your sinks such as available options |
‑‑enable-autostart | Generates an autostart entry |
A shortcut can be generated in the user startup folder by runningthe following(the config fileallmylightsrc.json
is expected to reside in the same folderas the executable, but can be customized by providing the--config
parameter)
.\AllMyLights.exe--enable-autostart
Create a shortcut to yourAllMyLights.exe
, open its properties and change thetarget to something along the lines:
"D:\Program Files\AllMyLights\AllMyLights.exe"--config allmylightsrc.json--minimized true
Move the shortcut to%APPDATA%\Microsoft\Windows\Start Menu\Programs\Startup
Make also sure that your OpenRGB server is run on startup as described in theOpenRGB Section
I can generate a service definition and enable startup on boot (in distributionsusing systemd). Simply call me with elevated privileges using the--enable-autostart
flag. I assume that a config file namedallmylightsrc.json
resides in the same folder as my executable. This can becustomized using the--config
parameter. Also the log level can be changed.Before executing the following lines, please make sure that the environmentvariable DOTNET_ROOT is set (f.i. in/etc/environment
)
sudo su./AllMyLights --enable-autostart --log-level debug# double check that I am up and runningservice allmylights status
The following instructions work for Raspbian or any other distribution thatuses systemd.
Copy the binary for your platform and theallmylightsrc.json
to a targetdirectory (f.i.$HOME/allmylights
) on your machine. Create a servicedefinition usingsudo vi /etc/systemd/system/allmylights.service
and copy thefollowing configuration:
[Unit]Description=AllMyLights service to sync colors via MQTT to an OpenRGB instance[Service]WorkingDirectory=/home/pi/allmylightsExecStart=/home/pi/allmylights/AllMyLights --config allmylightsrc.json --log-level infoRestart=alwaysRestartSec=10KillSignal=SIGINTSyslogIdentifier=allmylightsUser=piEnvironment=DOTNET_ROOT=/home/pi/dotnet-arm32[Install]WantedBy=multi-user.target
Customize theWorkingDirectory
andExecStart
to use the folder created inthe previous step if required. Change the value ofUser
to the user you wantthe service to be run as. Also note theDOTNET_ROOT
environment variable. Forframework dependant binaries, you have to change the path to the directory whereyour .NET Core runtime resides.
Start the service withsudo service allmylights start
and check thateverything is running smoothly usingsudo service allmylights status
.Afterwards usesudo systemctl enable allmylights
to make systemd automaticallystart your service during boot up.
Make also sure that the OpenRGB server on the machine you want to control is runon startup as described in theOpenRGB Section
"RGB Icon" byElegantthemes licensed underCC BY 4.0
About
Sync your RGB devices through MQTT with OpenRGB, your Desktop Wallpaper, Chroma devices, and more to come