Flatten media player(s) into a group card

Sure, here it is:

First i have a custom_component that acts as a sensor for the source and volume_levels.
custom_components/switch/denonxml.py

import time, math, requests
import voluptuous as vol

from xml.etree import ElementTree

from homeassistant.components.media_player import (PLATFORM_SCHEMA, MediaPlayerDevice)
from homeassistant.const import (CONF_HOST, CONF_PORT)
import homeassistant.helpers.config_validation as cv

PLATFORM_SCHEMA = PLATFORM_SCHEMA.extend({
    vol.Required(CONF_HOST): cv.string,
    vol.Required(CONF_PORT): cv.string,
})

def setup_platform(hass, config, add_devices, discovery_info=None):

    denonxml = DenonSensor(config.get(CONF_HOST), config.get(CONF_PORT))
    add_devices([denonxml])

class DenonSensor(MediaPlayerDevice):

    def __init__(self, host, port):
        self._state = "off"
        self._host  = host
        self._port  = port
        self._name  = "Denon " + port

    @property
    def name(self):
        return "Denon Zone" + self._port

    @property
    def state(self):
        return self._state

    @property
    def source(self):
        return self._mediasource 

    @property
    def volume_level(self):
        return self._volume 

    def getZon(self):
        if self._port == "2":
            return "Z2"
        else:
            return "ZM"

    def turn_off(self):
        url = "http://" + self._host + "/goform/formiPhoneAppDirect.xml?" + self.getZon() + "OFF"
        requests.get(url)
        time.sleep(4)
 
    def turn_on(self):
        url = "http://" + self._host + "/goform/formiPhoneAppDirect.xml?" + self.getZon() + "ON"
        requests.get(url)
        time.sleep(4)
    
    def update(self):

        url = "http://" + self._host + "/goform/formMainZone_MainZoneXml.xml?ZoneName=zone" + self._port
        response = requests.get(url)
        root = ElementTree.fromstring(response.content)        

        on_off = root.find('ZonePower').find('value').text
        src    = root.find('InputFuncSelect').find('value').text
        volume = root.find('MasterVolume').find('value').text

        self._state = on_off.lower()
        self._mediasource = src
        self._volume = math.ceil(float(volume)) + 80

Next, comes the custom_ui
custom_ui/state-card-custom_source.html

<dom-module id="state-card-custom_source">
  <template>
    <style is="custom-style" include="iron-flex iron-flex-alignment"></style>
    <style>
      :host {
        line-height: 1.5;
      }
      ha-entity-toggle {
        margin-left: 55px;
      }
      paper-button.nml {
        min-width: 35px;
      }
      paper-button.sel {
        min-width: 35px;
        color: #03a9f4;
        font-weight: 800;
      }
      paper-slider {
        margin: 4px 0;
        max-width: 100%;
        min-width: 100px;
        width: var(--ha-paper-slider-width, 200px);
      }
    </style>

    <div class='horizontal justified layout'>
      <state-info state-obj="[[stateObj]]"></state-info>
      <paper-slider min="10" max="70" value="[[vol_num]]" pin on-change="volChanged" on-tap="stopPropagation"></paper-slider>
    </div>
    <div class='horizontal justified layout'>
      <ha-entity-toggle state-obj="[[stateObj]]" hass="[[hass]]"></ha-entity-toggle>
      <paper-button-group>
        <template is='dom-if' if='[[_showControl(stateObj,"1")]]'>
          <paper-button class$='[[_clsbtn(stateObj,"Game")]]' on-tap="btntap11">XBOX</paper-button>
          <paper-button class$='[[_clsbtn(stateObj,"CBL/SAT")]]' on-tap="btntap12">TATASKY</paper-button>
          <paper-button class$='[[_clsbtn(stateObj,"Media Player")]]' on-tap="btntap13">KODI</paper-button>
        </template>

        <template is='dom-if' if='[[_showControl(stateObj,"2")]]'>
          <paper-button class$='[[_clsbtn(stateObj,"Online Music")]]' on-tap="btntap21">AIRPLAY</paper-button>
          <paper-button class$='[[_clsbtn(stateObj,"AUX")]]' on-tap="btntap22">KODI</paper-button>
        </template>
      </paper-button-group>
    </div>
  </template>
</dom-module>

<script>
Polymer({
  is: 'state-card-custom_source',
  properties: {
    hass: {
      type: Object,
    },
    stateObj: {
      type: Object,
    },
    vol_num: {
      type: String,
      computed: 'computeVol(stateObj)',
    },
  },

  _showControl: function (stateObj,zone) {
    return (this.stateObj.entity_id.slice(-1) === zone);
  },

  _clsbtn: function (stateObj,btn_src) {
    if (btn_src === this.stateObj.attributes.source)
      return "sel";
    else
      return "nml";
  },

  computeVol: function(stateObj) {
    return stateObj.attributes.volume_level;
  },

  btntap11: function (ev) {
    this.setSource('SIGAME', ev);
  },
  btntap12: function (ev) {
    this.setSource('SISAT/CBL', ev);
  },
  btntap13: function (ev) {
    this.setSource('SIMPLAY', ev);
  },
  btntap21: function (ev) {
    this.setSource('Z2NET', ev);
  },
  btntap22: function (ev) {
    this.setSource('Z2AUX1', ev);
  },
  
  setSource(src, ev) {
    var serviceData = {source: src} || {};
    this.hass.callService('shell_command', 'set_denon_source', serviceData);
    ev.stopPropagation();
  },
  
  volChanged: function(ev) {
    var serviceData = {zone: this.stateObj.entity_id.slice(-1), volume: ev.target.value} || {};
    this.hass.callService('shell_command', 'set_denon_volume', serviceData);
  },

  stopPropagation: function (ev) {
    ev.stopPropagation();
  },
    
});
</script>

Finally, configuration.yaml

switch:               
  - platform: denonxml
    host: 192.168.1.136
    port: 1           
    scan_interval: 5  
  - platform: denonxml
    host: 192.168.1.136
    port: 2           
    scan_interval: 5
shell_command:                                  
  set_denon_volume: '/usr/bin/curl -X GET http://192.168.1.136/goform/formiPhoneAppVolume.xml?{{ zone }}+{{ volume | float - 80 }}'
  set_denon_source: '/usr/bin/curl -X GET http://192.168.1.136/goform/formiPhoneAppDirect.xml?{{ source }}'
group:
  denon:
    name: Denon AVR
    entities:
      - switch.denon_zone1
      - switch.denon_zone2
  
  customize:        
    switch.denon_zone1:
      friendly_name: Living Room
      icon: mdi:video
      custom_ui_state_card: custom_source
    switch.denon_zone2:
      friendly_name: BedRoom
      icon: mdi:volume-high
      custom_ui_state_card: custom_source

And you should get: