# check if device is found
adb devices
# reboot into sideload modus
adb reboot sideload
Or manually boot into TWRP recovery, holding Volume Up + Power when the phone is off. Navigate to Advanced → ADB Sideload.
Update MIUI Firmware
Following the docs, I first had to check the Firmware version. V12.0.3.0.QEAMIXM was required, and I already had it installed. If you’re on an older version, download the right MIUI Firmware for your device from https://xiaomifirmwareupdater.com/firmware/dipper/. Flash the new Firmware via TWRP or via ADB sideload.
I recently saw this cool dashboard and the person cards caught my eye. As the dashboard creator also provided all the yaml code and a really helpful guide, I tried to rebuild it. I was already using the mushroom-person-card, so I “just” had to add the little icons (mushroom-chips-card) below it (using the vertical-stack-in-card). To display the network type and the charging status, you first have to enable these sensors in the Home Assistant Companion App on your mobile phone. This is my result:
type: horizontal-stack
cards:
- type: custom:vertical-stack-in-card
cards:
- type: custom:mushroom-person-card
entity: person.nico
icon_type: entity-picture
secondary_info: last-changed
card_mod:
style: |
ha-card {
background: transparent;
}
- type: horizontal-stack
cards:
- type: custom:mushroom-chips-card
alignment: center
card_mod:
style: |
ha-card {
--chip-font-size: 0.3em;
--chip-icon-size: 0.5em;
--chip-border-width: 0;
--chip-box-shadow: none;
--chip-background: none;
--chip-border: none;
--chip-spacing: none;
--chip-font-weight: bold;
}
chips:
- type: template
entity: sensor.mi_8_network_type
content: '{{ states(''sensor.mi_8_network_type'')}}'
icon: |-
{% if is_state('sensor.mi_8_network_type','wifi')%}
mdi:wifi
{% elif is_state('sensor.mi_8_network_type','vpn')%}
mdi:network
{% elif is_state('sensor.mi_8_network_type','cellular')%}
mdi:signal-4g
{% else %}
mdi:network-strength-off
{% endif %}
icon_color: >-
{% if is_state('sensor.mi_8_network_type','wifi') or
is_state('sensor.mi_8_network_type','vpn')%}
green
{% elif is_state('sensor.mi_8_network_type','cellular')%}
red
{% else %}
grey
{% endif %}
tap_action:
action: more-info
- type: template
entity: sensor.mi_8_battery_level
content: '{{ states(''sensor.mi_8_battery_level'')}}%'
icon: |-
{% set state = states('sensor.mi_8_battery_level')|float %}
{% if state >= 0 and state < 10 %} mdi:battery-10
{% elif state >= 10 and state < 20 %} mdi:battery-20
{% elif state >= 20 and state < 30 %} mdi:battery-30
{% elif state >= 30 and state < 40 %} mdi:battery-40
{% elif state >= 40 and state < 50 %} mdi:battery-50
{% elif state >= 50 and state < 60 %} mdi:battery-60
{% elif state >= 60 and state < 70 %} mdi:battery-70
{% elif state >= 70 and state < 80 %} mdi:battery-80
{% elif state >= 80 and state < 95 %} mdi:battery-90
{% else %} mdi:battery
{% endif %}
icon_color: |-
{% set state = states('sensor.mi_8_battery_level')|float %}
{% if state >= 0 and state < 20 %} red
{% elif state >= 20 and state < 50 %} orange
{% elif state >= 50 and state < 80 %} yellow
{% else %} green
{% endif %}
tap_action:
action: more-info
- type: template
entity: sensor.mi_8_battery_power
content: '{{ states(''sensor.mi_8_battery_power'')}} W'
icon: |-
{% if is_state('binary_sensor.mi_8_is_charging','on')%}
mdi:power-plug
{% else %}
mdi:power-plug-off
{% endif %}
icon_color: |-
{% if is_state('binary_sensor.mi_8_is_charging','on')%}
blue
{% else %}
grey
{% endif %}
tap_action:
action: more-info
- type: custom:vertical-stack-in-card
cards:
- type: custom:mushroom-person-card
entity: person.user2
icon_type: entity-picture
secondary_info: last-changed
card_mod:
style: |
ha-card {
background: transparent;
}
- type: horizontal-stack
cards:
- type: custom:mushroom-chips-card
alignment: center
card_mod:
style: |
ha-card {
--chip-font-size: 0.3em;
--chip-icon-size: 0.5em;
--chip-border-width: 0;
--chip-box-shadow: none;
--chip-background: none;
--chip-border: none;
--chip-spacing: none;
--chip-font-weight: bold;
}
chips:
- type: template
entity: sensor.redmi_note_8_pro_network_type
content: '{{ states(''sensor.redmi_note_8_pro_network_type'')}}'
icon: >-
{% if
is_state('sensor.redmi_note_8_pro_network_type','wifi')%}
mdi:wifi
{% elif
is_state('sensor.redmi_note_8_pro_network_type','vpn')%}
mdi:network
{% elif
is_state('sensor.redmi_note_8_pro_network_type','cellular')%}
mdi:signal-4g
{% else %}
mdi:network-strength-off
{% endif %}
icon_color: >-
{% if is_state('sensor.redmi_note_8_pro_network_type','wifi')
or is_state('sensor.redmi_note_8_pro_network_type','vpn')%}
green
{% elif
is_state('sensor.redmi_note_8_pro_network_type','cellular')%}
red
{% else %}
grey
{% endif %}
tap_action:
action: more-info
- type: template
entity: sensor.mi_8_battery_level
content: '{{ states(''sensor.redmi_note_8_pro_battery_level'')}}%'
icon: >-
{% set state = states('sensor.redmi_note_8_pro_battery_level')|float %}
{% if state >= 0 and state < 10 %} mdi:battery-10
{% elif state >= 10 and state < 20 %} mdi:battery-20
{% elif state >= 20 and state < 30 %} mdi:battery-30
{% elif state >= 30 and state < 40 %} mdi:battery-40
{% elif state >= 40 and state < 50 %} mdi:battery-50
{% elif state >= 50 and state < 60 %} mdi:battery-60
{% elif state >= 60 and state < 70 %} mdi:battery-70
{% elif state >= 70 and state < 80 %} mdi:battery-80
{% elif state >= 80 and state < 95 %} mdi:battery-90
{% else %} mdi:battery
{% endif %}
icon_color: >-
{% set state = states('sensor.redmi_note_8_pro_battery_level')|float %}
{% if state >= 0 and state < 20 %} red
{% elif state >= 20 and state < 50 %} orange
{% elif state >= 50 and state < 80 %} yellow
{% else %} green
{% endif %}
tap_action:
action: more-info
- type: template
entity: sensor.redmi_note_8_pro_battery_power
content: '{{ states(''sensor.redmi_note_8_pro_battery_power'')}} W'
icon: >-
{% if is_state('binary_sensor.redmi_note_8_pro_is_charging','on')%}
mdi:power-plug
{% else %}
mdi:power-plug-off
{% endif %}
icon_color: >-
{% if is_state('binary_sensor.redmi_note_8_pro_is_charging','on')%}
blue
{% else %}
grey
{% endif %}
tap_action:
action: more-info
Update 15.01.2025: When I migrated my dashboard to the new sections layout, I could get rid of the surrounding horizontal stack and had to adjust some minor things like font size and icon size. I also added the Steps sensor from my mobile phone (chekc here). Here is it, how it looks now:
type: custom:vertical-stack-in-card
cards:
- type: custom:mushroom-person-card
entity: person.nocin
icon_type: entity-picture
secondary_info: last-changed
card_mod:
style: |
ha-card {
background: transparent;
}
- type: horizontal-stack
cards:
- type: custom:mushroom-chips-card
alignment: center
card_mod:
style: |
ha-card {
--chip-font-size: 0.32em;
--chip-icon-size: 0.5em;
--chip-border-width: 0;
--chip-box-shadow: none;
--chip-background: none;
--chip-border: none;
--chip-spacing: none;
--chip-font-weight: bold;
}
chips:
- type: template
entity: sensor.mi_8_network_type
content: "{{ states('sensor.mi_8_network_type')}}"
icon: |-
{% if is_state('sensor.mi_8_network_type','wifi')%}
mdi:wifi
{% elif is_state('sensor.mi_8_network_type','vpn')%}
mdi:network
{% elif is_state('sensor.mi_8_network_type','cellular')%}
mdi:signal-4g
{% else %}
mdi:network-strength-off
{% endif %}
icon_color: >-
{% if is_state('sensor.mi_8_network_type','wifi') or
is_state('sensor.mi_8_network_type','vpn')%}
green
{% elif is_state('sensor.mi_8_network_type','cellular')%}
red
{% else %}
grey
{% endif %}
tap_action:
action: more-info
- type: template
entity: sensor.mi_8_battery_level
content: "{{ states('sensor.mi_8_battery_level')}}%"
icon: |-
{% set state = states('sensor.mi_8_battery_level')|float %}
{% if state >= 0 and state < 10 %} mdi:battery-10
{% elif state >= 10 and state < 20 %} mdi:battery-20
{% elif state >= 20 and state < 30 %} mdi:battery-30
{% elif state >= 30 and state < 40 %} mdi:battery-40
{% elif state >= 40 and state < 50 %} mdi:battery-50
{% elif state >= 50 and state < 60 %} mdi:battery-60
{% elif state >= 60 and state < 70 %} mdi:battery-70
{% elif state >= 70 and state < 80 %} mdi:battery-80
{% elif state >= 80 and state < 95 %} mdi:battery-90
{% else %} mdi:battery
{% endif %}
icon_color: |-
{% set state = states('sensor.mi_8_battery_level')|float %}
{% if state >= 0 and state < 20 %} red
{% elif state >= 20 and state < 50 %} orange
{% elif state >= 50 and state < 80 %} yellow
{% else %} green
{% endif %}
tap_action:
action: more-info
- type: template
entity: sensor.mi_8_battery_power
content: "{{ states('sensor.mi_8_battery_power')}} W"
icon: |-
{% if is_state('binary_sensor.mi_8_is_charging','on')%}
mdi:power-plug
{% else %}
mdi:power-plug-off
{% endif %}
icon_color: |-
{% if is_state('binary_sensor.mi_8_is_charging','on')%}
blue
{% else %}
grey
{% endif %}
tap_action:
action: more-info
- type: horizontal-stack
cards:
- type: custom:mushroom-chips-card
alignment: center
card_mod:
style: |
ha-card {
--chip-font-size: 0.32em;
--chip-icon-size: 0.5em;
--chip-border-width: 0;
--chip-box-shadow: none;
--chip-background: none;
--chip-border: none;
--chip-spacing: none;
--chip-font-weight: bold;
}
chips:
- type: template
entity: sensor.daily_steps_mi8
content: "{{ states('sensor.daily_steps_mi8')}} steps today"
tap_action:
action: more-info
Cool template sensor idea I found here, which combines the states of two sensors and display the different combined states. Useful if, for example, you want to combine a door lock and a contact sensor on the same door.
{% if is_state('lock.kellertur', 'locked') and is_state('binary_sensor.kellertur_contact', 'off') %}
Locked
{% elif is_state('lock.kellertur', 'unlocked') and is_state('binary_sensor.kellertur_contact', 'on') %}
Open
{% elif is_state('lock.kellertur', 'unlocked') and is_state('binary_sensor.kellertur_contact', 'off') %}
Closed, Unlocked
{% elif is_state('lock.kellertur', 'locked') and is_state('binary_sensor.kellertur_contact', 'on') %}
Open, Locked
{% else %}
Unknown
{% endif %}
Helpful to check whether a door is really closed when locking it via a smart lock. Because else it could happen, that you would see status “Locked“, although the door is still open. But with this helper, you will get in this situation “Open, Locked“.
To emphasize such a situation even more clearly, you can of course also add some icon colors.
I have some lights in my garden which are turned on in the night and are controlled by the Adaptive Lighting component, to automatically adjust brightness and color during the night. But if someone comes home late and this is detected by a motion sensor, I wanted to increase the brightness of all the lights in the garden for a short time.
Increasing the brightness was easy, as it can be done by using the light.turn_on service. However, it took me a few minutes to figure out how to reactivate adaptive lighting on these lights when motion is no longer detected. But it’s actually super simple (and it’s directly written on the GitHub start page here and here). You just have to deactivate the “manually controlled” flag that got activated by “manually” increasing the brightness. Following an example with a single motion sensor (binary_sensor.haustuer_motion), a lamp (light.haustur_light) and the adaptive lightning switch entity (switch.adaptive_lighting_haustuer).
alias: Motion sensor front door
description: "Increase brightness for three minutes when motion is detected"
trigger:
- platform: state
entity_id:
- binary_sensor.haustuer_motion
to: "on"
condition:
- condition: state
entity_id: sun.sun
state: below_horizon
action:
- service: light.turn_on
data:
transition: 3
brightness_pct: 70
target:
entity_id: light.haustur_light
- wait_for_trigger:
- platform: state
entity_id:
- binary_sensor.haustuer_motion
to: "off"
for:
hours: 0
minutes: 3
seconds: 0
timeout:
hours: 0
minutes: 0
seconds: 0
milliseconds: 0
- service: adaptive_lighting.set_manual_control
data:
manual_control: false
entity_id: switch.adaptive_lighting_haustuer
lights:
- light.haustur_light
mode: single
In my case, there was no way to bind the model to the view, so I did the mapping for each ProcessFlowLaneHeader in the callback function after reading the oData entity.
view.xml
<flow:ProcessFlow id="process-flow"/>
controller.js
var oProcessFlow = this.getView().byId("process-flow")
var oRequestFilter = new sap.ui.model.Filter({
path: "myId",
operator: sap.ui.model.FilterOperator.EQ,
value1: myId
})
this.getView().getModel().read("/WorkflowSet", {
filters: [oFormularIdFilter],
success: (oData, response) => {
for (var i = 0; i < oData.results.length; i++) {
var oLaneHeader = new ProcessFlowLaneHeader({
laneId: oData.results[i].LaneId,
iconSrc: oData.results[i].IconSrc,
text: oData.results[i].Text,
position: oData.results[i].Position,
state: [{state: oData.results[i].State, value: "100"}]
});
oProcessFlow.addLane(oLaneHeader)
}
},
error: oError => {
sap.m.MessageToast.show("An error occured while reading entity /WorkflowSet.")
}
});
I was looking for a way, to get the candidate ID and Job Application ID for a given User. In a Process Trigger, you can get a good overview of an employee who moved from REC, via ONB to EC, and there I found all the required information.
Manage Data → Search → Process Trigger
This information can also be fetched via API.
API Entity: ONB2Process
### Process Trigger
GET {{$dotenv sf_api_url}}/odata/v2/ONB2Process('06B129C95FD3482B851018D37B697149')
Authorization: Basic {{$dotenv sf_api_auth_base64}}
Accept: application/json
### processTriggerNav, includes rcmCandidateId, rcmApplicationId, rcmJobReqId
GET {{$dotenv sf_api_url}}/odata/v2/ONB2Process('06B129C95FD3482B851018D37B697149')
?$expand=processTriggerNav
Authorization: Basic {{$dotenv sf_api_auth_base64}}
Accept: application/json
### Fetch candidateId, jobApplicationId, jobReqId via userId
GET {{$dotenv sf_api_url}}/odata/v2/User(100000)/userOfONB2ProcessNav
?$expand=processTriggerNav
&$select=processId,processTriggerNav/rcmApplicationId,processTriggerNav/rcmJobReqId,processTriggerNav/rcmCandidateId
Authorization: Basic {{$dotenv sf_api_auth_base64}}
Accept: application/json