App 2.6.0: floating button to open the app
The MG4's launcher does not list third-party apps, so the app could only be opened by reinstalling it. Now a small round MG-red button floats over the car's screens: tap opens the app, drag moves it (the position is kept and clamped to the screen), and it hides while the app itself is open. A switch in the Upload tab turns it off. The always-on service owns the overlay, so the button is there from boot. It needs the overlay permission (SYSTEM_ALERT_WINDOW), which the car build has through the system UID; without it, or if the window manager refuses, the button stays away and nothing crashes, and the Upload tab offers the system permission screen. Tested on an Android 9 AOSP emulator at the head unit's 1920x1080 / 160 dpi with the car APK (installs as UID 1000): button appears over the home screen, tap opens the app, hidden while open, drag moves it without opening the app, position survives a force-stop, the switch works through the UI. FloatingButtonGeometry has 3 unit tests. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QLJfZQZeAKAwSqViTmLzki
This commit is contained in:
@@ -6,6 +6,12 @@
|
||||
<TextView android:id="@+id/status_text" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="@drawable/bg_input_panel" android:padding="16dp" android:layout_marginTop="20dp" android:layout_marginBottom="12dp" android:text="@string/state_stopped" android:textAppearance="@style/Text.EV.Body" />
|
||||
<com.google.android.material.switchmaterial.SwitchMaterial android:id="@+id/abrp_upload_switch" android:layout_width="match_parent" android:layout_height="wrap_content" android:minHeight="72dp" android:text="@string/label_abrp_upload_enabled" android:textAppearance="@style/Text.EV.Body" android:paddingTop="8dp" android:paddingBottom="8dp" app:useMaterialThemeColors="true" app:thumbTint="@color/switch_thumb" app:trackTint="@color/switch_track" android:textColor="@color/ev_text_primary" />
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/hint_abrp_upload_enabled" android:textAppearance="@style/Text.EV.Secondary" />
|
||||
<com.google.android.material.switchmaterial.SwitchMaterial android:id="@+id/floating_button_switch" android:layout_width="match_parent" android:layout_height="wrap_content" android:minHeight="72dp" android:text="@string/label_floating_button" android:textAppearance="@style/Text.EV.Body" android:paddingTop="8dp" android:paddingBottom="8dp" app:useMaterialThemeColors="true" app:thumbTint="@color/switch_thumb" app:trackTint="@color/switch_track" android:textColor="@color/ev_text_primary" />
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/hint_floating_button" android:textAppearance="@style/Text.EV.Secondary" />
|
||||
<LinearLayout android:id="@+id/overlay_permission_note" android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" android:layout_marginTop="8dp" android:visibility="gone">
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/overlay_permission_missing" android:textAppearance="@style/Text.EV.Secondary" android:textColor="@color/ev_error" />
|
||||
<com.google.android.material.button.MaterialButton android:id="@+id/overlay_permission_button" style="@style/Widget.EV.Button.Outlined" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="8dp" android:text="@string/btn_overlay_permission" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
<LinearLayout android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:orientation="vertical" android:padding="24dp" android:background="@drawable/bg_glass">
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/design_service_timing" android:textAppearance="@style/Text.EV.Eyebrow" />
|
||||
|
||||
@@ -6,6 +6,12 @@
|
||||
<TextView android:id="@+id/status_text" android:layout_width="match_parent" android:layout_height="wrap_content" android:background="@drawable/bg_input_panel" android:padding="16dp" android:layout_marginTop="20dp" android:layout_marginBottom="12dp" android:text="@string/state_stopped" android:textAppearance="@style/Text.EV.Body" />
|
||||
<com.google.android.material.switchmaterial.SwitchMaterial android:id="@+id/abrp_upload_switch" android:layout_width="match_parent" android:layout_height="wrap_content" android:minHeight="72dp" android:text="@string/label_abrp_upload_enabled" android:textAppearance="@style/Text.EV.Body" android:paddingTop="8dp" android:paddingBottom="8dp" app:useMaterialThemeColors="true" app:thumbTint="@color/switch_thumb" app:trackTint="@color/switch_track" android:textColor="@color/ev_text_primary" />
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/hint_abrp_upload_enabled" android:textAppearance="@style/Text.EV.Secondary" />
|
||||
<com.google.android.material.switchmaterial.SwitchMaterial android:id="@+id/floating_button_switch" android:layout_width="match_parent" android:layout_height="wrap_content" android:minHeight="72dp" android:text="@string/label_floating_button" android:textAppearance="@style/Text.EV.Body" android:paddingTop="8dp" android:paddingBottom="8dp" app:useMaterialThemeColors="true" app:thumbTint="@color/switch_thumb" app:trackTint="@color/switch_track" android:textColor="@color/ev_text_primary" />
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/hint_floating_button" android:textAppearance="@style/Text.EV.Secondary" />
|
||||
<LinearLayout android:id="@+id/overlay_permission_note" android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" android:layout_marginTop="8dp" android:visibility="gone">
|
||||
<TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:text="@string/overlay_permission_missing" android:textAppearance="@style/Text.EV.Secondary" android:textColor="@color/ev_error" />
|
||||
<com.google.android.material.button.MaterialButton android:id="@+id/overlay_permission_button" style="@style/Widget.EV.Button.Outlined" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="8dp" android:text="@string/btn_overlay_permission" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
<Space android:layout_width="1dp" android:layout_height="20dp" />
|
||||
<LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" android:padding="24dp" android:background="@drawable/bg_glass">
|
||||
|
||||
@@ -107,6 +107,12 @@
|
||||
<string name="conn_err_timeout">Connection timed out</string>
|
||||
<string name="conn_err_http">Server error (HTTP %1$d)</string>
|
||||
|
||||
<string name="label_floating_button">Show floating button</string>
|
||||
<string name="hint_floating_button">A small round button over the car\'s screens that opens this app. Drag it to move it; it hides while the app is open.</string>
|
||||
<string name="overlay_permission_missing">This build may not draw over other apps, so the button cannot appear.</string>
|
||||
<string name="btn_overlay_permission">Allow display over other apps</string>
|
||||
<string name="overlay_settings_missing">The system screen for this permission is not available here</string>
|
||||
<string name="floating_button_description">Open Nils\' MG4</string>
|
||||
<string name="label_abrp_upload_enabled">Send live telemetry to the server</string>
|
||||
<string name="hint_abrp_upload_enabled">The server stores it and forwards it to ABRP. Turn this off when another app feeds ABRP; consumption and charging tracking keep running.</string>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user