diff --git a/devices/homie/modules/home-assistant/default.nix b/devices/homie/modules/home-assistant/default.nix
index d2139335..9a364353 100644
--- a/devices/homie/modules/home-assistant/default.nix
+++ b/devices/homie/modules/home-assistant/default.nix
@@ -19,6 +19,7 @@
     enable = true;
 
     extraComponents = [
+      "androidtv"
       "androidtv_remote"
       "caldav"
       "cast"
@@ -30,6 +31,13 @@
       "yamaha_musiccast"
     ];
 
+    customComponents = builtins.attrValues {
+      inherit
+        (self.legacyPackages.${pkgs.system}.hass-components)
+        yamaha-soundbar
+        ;
+    };
+
     config = {
       homeassistant = {
         name = "Home";
@@ -40,6 +48,17 @@
         external_url = "https://homie.nelim.org";
       };
 
+      media_player = [
+        {
+          platform = "yamaha_soundbar";
+          host = "192.168.0.96";
+          name = "Living Room Speaker";
+          sources = {
+            HDMI = "TV";
+          };
+        }
+      ];
+
       # Proxy settings
       http = {
         server_host = "0.0.0.0";
diff --git a/devices/homie/modules/home-assistant/frontend.nix b/devices/homie/modules/home-assistant/frontend.nix
index 2b9a93f8..8907d413 100644
--- a/devices/homie/modules/home-assistant/frontend.nix
+++ b/devices/homie/modules/home-assistant/frontend.nix
@@ -90,6 +90,7 @@ in {
       inherit
         (pkgs.home-assistant-custom-lovelace-modules)
         card-mod
+        universal-remote-card
         ;
 
       inherit
@@ -140,6 +141,166 @@ in {
                 "timer.assist_timer3"
               ];
             }
+
+            {
+              type = "custom:android-tv-card";
+
+              media_player_id = "media_player.living_room_speaker";
+              keyboard_id = "remote.android_tv_192_168_0_106";
+              remote_id = "remote.onn_4k_streaming_box";
+
+              rows = [
+                "navigation_buttons"
+                [null "slider" null]
+                [null]
+                ["jellyfin" "home" "back" "keyboard"]
+                [null]
+              ];
+
+              custom_actions = [
+                {
+                  name = "center";
+                  type = "button";
+                  icon = "mdi:checkbox-blank-circle";
+
+                  styles = ''
+                    :host {
+                        --icon-color: rgb(94, 94, 94);
+                        --size: 200px;
+                        background: rgb(31, 31, 31);
+                        border-radius: 200px;
+                        margin: -70px;
+                        padding: 70px;
+                    }
+                  '';
+
+                  tap_action = {
+                    action = "key";
+                    key = "DPAD_CENTER";
+                  };
+                }
+
+                {
+                  name = "up";
+                  type = "button";
+                  icon = "mdi:chevron-up";
+
+                  styles = ''
+                    :host {
+                        --icon-color: rgb(197, 199, 197);
+                        z-index: 2;
+                        top: 25px;
+                        height: 90px;
+                        width: 300px;
+                    }
+                  '';
+
+                  hold_action = {action = "repeat";};
+                  tap_action = {
+                    action = "key";
+                    key = "DPAD_UP";
+                  };
+                }
+
+                {
+                  name = "down";
+                  type = "button";
+                  icon = "mdi:chevron-down";
+
+                  styles = ''
+                    :host {
+                        --icon-color: rgb(197, 199, 197);
+                        z-index: 2;
+                        bottom: 25px;
+                        height: 90px;
+                        width: 300px;
+                    }
+                  '';
+
+                  hold_action = {action = "repeat";};
+                  tap_action = {
+                    action = "key";
+                    key = "DPAD_DOWN";
+                  };
+                }
+
+                {
+                  name = "left";
+                  type = "button";
+                  icon = "mdi:chevron-left";
+
+                  styles = ''
+                    :host {
+                        --icon-color: rgb(197, 199, 197);
+                        z-index: 2;
+                        left: 30px;
+                        height: 170px;
+                        width: 90px;
+                    }
+                  '';
+
+                  hold_action = {action = "repeat";};
+                  tap_action = {
+                    action = "key";
+                    key = "DPAD_LEFT";
+                  };
+                }
+
+                {
+                  name = "right";
+                  type = "button";
+                  icon = "mdi:chevron-right";
+
+                  styles = ''
+                    :host {
+                        --icon-color: rgb(197, 199, 197);
+                        z-index: 2;
+                        right: 30px;
+                        height: 170px;
+                        width: 90px;
+                    }
+                  '';
+
+                  hold_action = {action = "repeat";};
+                  tap_action = {
+                    action = "key";
+                    key = "DPAD_RIGHT";
+                  };
+                }
+
+                {
+                  name = "slider";
+                  type = "slider";
+                  icon = "mdi:volume-high";
+
+                  range = [0 1];
+                  step = 0.01;
+
+                  tap_action = {
+                    action = "perform-action";
+                    perform_action = "media_player.volume_set";
+                    data = {
+                      volume_level = "{{ value | float }}";
+                    };
+                  };
+                  value_attribute = "volume_level";
+                }
+              ];
+
+              styles = ''
+                #row-1 {
+                    justify-content: center;
+                }
+
+                #row-2 {
+                    justify-content: center;
+                }
+
+                #row-3 {
+                    justify-content: center;
+                }
+              '';
+            }
           ];
         }
       ];
diff --git a/flake.lock b/flake.lock
index 98689a69..ae085258 100644
--- a/flake.lock
+++ b/flake.lock
@@ -1719,7 +1719,8 @@
         "tuya-local-src": "tuya-local-src",
         "vimplugin-easytables-src": "vimplugin-easytables-src",
         "vimplugin-ts-error-translator-src": "vimplugin-ts-error-translator-src",
-        "wakewords-src": "wakewords-src"
+        "wakewords-src": "wakewords-src",
+        "yamaha-soundbar-src": "yamaha-soundbar-src"
       }
     },
     "scss-reset": {
@@ -2104,6 +2105,22 @@
         "repo": "xdg-desktop-portal-hyprland",
         "type": "github"
       }
+    },
+    "yamaha-soundbar-src": {
+      "flake": false,
+      "locked": {
+        "lastModified": 1720618370,
+        "narHash": "sha256-nVbWmzZZ7akqJGg/J5xBNgO2ky7iQgI0vDYRXCo6zR4=",
+        "owner": "osk2",
+        "repo": "yamaha-soundbar",
+        "rev": "ebb3949a31a9d8460aed38924ae3a311204a06a2",
+        "type": "github"
+      },
+      "original": {
+        "owner": "osk2",
+        "repo": "yamaha-soundbar",
+        "type": "github"
+      }
     }
   },
   "root": "root",
diff --git a/flake.nix b/flake.nix
index 5b560250..3e9b48c0 100644
--- a/flake.nix
+++ b/flake.nix
@@ -1,5 +1,4 @@
 # Do not modify! This file is generated.
-
 {
   inputs = {
     ags = {
@@ -467,6 +466,12 @@
       repo = "home-assistant-wakewords-collection";
       type = "github";
     };
+    yamaha-soundbar-src = {
+      flake = false;
+      owner = "osk2";
+      repo = "yamaha-soundbar";
+      type = "github";
+    };
   };
   outputs = inputs: inputs.flakegen ./outputs.nix inputs;
-}
\ No newline at end of file
+}
diff --git a/inputs.nix b/inputs.nix
index 847dd2c8..ee7df55c 100644
--- a/inputs.nix
+++ b/inputs.nix
@@ -202,6 +202,11 @@ let
       owner = "net-daemon";
       repo = "integration";
     }
+    {
+      owner = "osk2";
+      repo = "yamaha-soundbar";
+    }
+
     ### SpotifyPlus
     {
       name = "spotifyplus-src";
diff --git a/legacyPackages/hass-components/default.nix b/legacyPackages/hass-components/default.nix
index 0534f425..bdfdb615 100644
--- a/legacyPackages/hass-components/default.nix
+++ b/legacyPackages/hass-components/default.nix
@@ -13,4 +13,5 @@ in {
   netdaemon = buildHassComponent ./netdaemon {};
   spotifyplus = import ./spotifyplus ({inherit buildHassComponent;} // inputs);
   tuya-local = buildHassComponent ./tuya-local {};
+  yamaha-soundbar = buildHassComponent ./yamaha-soundbar {};
 })
diff --git a/legacyPackages/hass-components/yamaha-soundbar/default.nix b/legacyPackages/hass-components/yamaha-soundbar/default.nix
new file mode 100644
index 00000000..5992f4a9
--- /dev/null
+++ b/legacyPackages/hass-components/yamaha-soundbar/default.nix
@@ -0,0 +1,22 @@
+{
+  yamaha-soundbar-src,
+  buildHomeAssistantComponent,
+  python3Packages,
+  ...
+}: let
+  inherit (builtins) fromJSON readFile;
+
+  manifest = fromJSON (readFile "${yamaha-soundbar-src}/custom_components/yamaha_soundbar/manifest.json");
+in
+  buildHomeAssistantComponent {
+    owner = "osk2";
+
+    inherit (manifest) domain version;
+    src = yamaha-soundbar-src;
+
+    propagatedBuildInputs = with python3Packages; [
+      async-upnp-client
+      chardet
+      validators
+    ];
+  }