mirror of
https://github.com/firestar5683/StarPilot.git
synced 2026-07-14 13:52:12 +08:00
BigUI WIP: 4 Jon: His Eyes Are Saved
Pass 1 of collapsing sidebar, adjustor size increases, onroad bar size increase
This commit is contained in:
@@ -15,7 +15,9 @@ from openpilot.system.ui.widgets import Widget
|
||||
from openpilot.system.ui.widgets.network import NetworkUI
|
||||
|
||||
# Constants
|
||||
SIDEBAR_WIDTH = 500
|
||||
COLLAPSED_WIDTH = 0
|
||||
EXPANDED_WIDTH = 500
|
||||
SWIPE_THRESHOLD = 80
|
||||
CLOSE_BTN_SIZE = 200
|
||||
CLOSE_ICON_SIZE = 70
|
||||
NAV_BTN_HEIGHT = 110
|
||||
@@ -23,11 +25,13 @@ PANEL_MARGIN = 10
|
||||
|
||||
# Colors
|
||||
SIDEBAR_COLOR = rl.BLACK
|
||||
ACCENT_LINE_COLOR = rl.Color(139, 92, 246, 55)
|
||||
PANEL_COLOR = rl.BLACK
|
||||
CLOSE_BTN_COLOR = rl.Color(41, 41, 41, 255)
|
||||
CLOSE_BTN_PRESSED = rl.Color(59, 59, 59, 255)
|
||||
TEXT_NORMAL = rl.Color(128, 128, 128, 255)
|
||||
TEXT_SELECTED = rl.WHITE
|
||||
DARK_CORE_COLOR = rl.Color(12, 10, 18, 190)
|
||||
|
||||
|
||||
class PanelType(IntEnum):
|
||||
@@ -55,6 +59,12 @@ class SettingsLayout(Widget):
|
||||
# 0 = top level (settings main), 1+ = nested custom panels
|
||||
self._panel_depth = 0
|
||||
|
||||
# Collapse / swipe state (always start collapsed)
|
||||
self._sidebar_expanded = False
|
||||
self._swipe_start = None
|
||||
self._collapse_btn_rect = rl.Rectangle(0, 0, 0, 0)
|
||||
self._back_btn_rect = rl.Rectangle(0, 0, 0, 0)
|
||||
|
||||
# Panel configuration
|
||||
wifi_manager = WifiManager()
|
||||
wifi_manager.set_active(False)
|
||||
@@ -78,6 +88,10 @@ class SettingsLayout(Widget):
|
||||
# Callbacks
|
||||
self._close_callback: Callable | None = None
|
||||
|
||||
@property
|
||||
def _sidebar_width(self) -> int:
|
||||
return EXPANDED_WIDTH if self._sidebar_expanded else COLLAPSED_WIDTH
|
||||
|
||||
def set_callbacks(self, on_close: Callable):
|
||||
self._close_callback = on_close
|
||||
|
||||
@@ -100,81 +114,186 @@ class SettingsLayout(Widget):
|
||||
self._close_callback()
|
||||
|
||||
def _render(self, rect: rl.Rectangle):
|
||||
# Calculate layout
|
||||
sidebar_rect = rl.Rectangle(rect.x, rect.y, SIDEBAR_WIDTH, rect.height)
|
||||
panel_rect = rl.Rectangle(rect.x + SIDEBAR_WIDTH, rect.y, rect.width - SIDEBAR_WIDTH, rect.height)
|
||||
|
||||
# Draw components
|
||||
w = self._sidebar_width
|
||||
sidebar_rect = rl.Rectangle(rect.x, rect.y, w, rect.height)
|
||||
panel_rect = rl.Rectangle(rect.x + w, rect.y, rect.width - w, rect.height)
|
||||
self._draw_sidebar(sidebar_rect)
|
||||
self._draw_current_panel(panel_rect)
|
||||
|
||||
def _draw_chevron(self, cx: float, cy: float, right: bool, color: rl.Color, size: int = 14, bloom: bool = False):
|
||||
half = size / 2
|
||||
if right:
|
||||
p1 = rl.Vector2(cx - half, cy - size)
|
||||
p2 = rl.Vector2(cx + half, cy)
|
||||
p3 = rl.Vector2(cx - half, cy + size)
|
||||
else:
|
||||
p1 = rl.Vector2(cx + half, cy - size)
|
||||
p2 = rl.Vector2(cx - half, cy)
|
||||
p3 = rl.Vector2(cx + half, cy + size)
|
||||
if bloom:
|
||||
bloom_col = rl.Color(color.r, color.g, color.b, 35)
|
||||
rl.draw_line_ex(p1, p2, 7.0, bloom_col)
|
||||
rl.draw_line_ex(p2, p3, 7.0, bloom_col)
|
||||
rl.draw_line_ex(p1, p2, 2.8, color)
|
||||
rl.draw_line_ex(p2, p3, 2.8, color)
|
||||
|
||||
def _draw_sidebar(self, rect: rl.Rectangle):
|
||||
rl.draw_rectangle_rec(rect, SIDEBAR_COLOR)
|
||||
|
||||
# Back/Close button - hierarchical navigation
|
||||
back_btn_rect = rl.Rectangle(rect.x + (rect.width - CLOSE_BTN_SIZE) / 2, rect.y + 60, CLOSE_BTN_SIZE, CLOSE_BTN_SIZE)
|
||||
# 2px purple accent line — persistent in both collapsed and expanded states
|
||||
line_rect = rl.Rectangle(rect.x, rect.y, 2, rect.height)
|
||||
rl.draw_rectangle_rec(line_rect, ACCENT_LINE_COLOR)
|
||||
|
||||
pressed = gui_app.last_mouse_event.left_down and rl.check_collision_point_rec(gui_app.last_mouse_event.pos, back_btn_rect)
|
||||
close_color = CLOSE_BTN_PRESSED if pressed else CLOSE_BTN_COLOR
|
||||
rl.draw_rectangle_rounded(back_btn_rect, 1.0, 20, close_color)
|
||||
# Orb position: fixed anchor that stays at the same screen position
|
||||
# in both states — visual indicator when collapsed, collapse trigger when expanded
|
||||
orb_cx = int(rect.x + 5)
|
||||
orb_cy = int(rect.y + 581)
|
||||
depth_boost = 0.8 if self._panel_depth > 0 else 1.0
|
||||
|
||||
icon_color = rl.Color(255, 255, 255, 255) if not pressed else rl.Color(220, 220, 220, 255)
|
||||
icon_dest = rl.Rectangle(
|
||||
back_btn_rect.x + (back_btn_rect.width - self._close_icon.width) / 2,
|
||||
back_btn_rect.y + (back_btn_rect.height - self._close_icon.height) / 2,
|
||||
self._close_icon.width,
|
||||
self._close_icon.height,
|
||||
)
|
||||
rl.draw_texture_pro(
|
||||
self._close_icon,
|
||||
rl.Rectangle(0, 0, self._close_icon.width, self._close_icon.height),
|
||||
icon_dest,
|
||||
rl.Vector2(0, 0),
|
||||
0,
|
||||
icon_color,
|
||||
)
|
||||
if self._sidebar_expanded:
|
||||
# ── EXPANDED ──
|
||||
|
||||
# Store back button rect for click detection
|
||||
self._back_btn_rect = back_btn_rect
|
||||
# Collapse trigger: purple glow orb at the same position as the collapsed indicator
|
||||
# Now with << inside and a 60x60 tap zone centered on the orb
|
||||
self._collapse_btn_rect = rl.Rectangle(rect.x, orb_cy - 30, 60, 60)
|
||||
col_pressed = (
|
||||
gui_app.last_mouse_event.left_down
|
||||
and rl.check_collision_point_rec(gui_app.last_mouse_event.pos, self._collapse_btn_rect)
|
||||
)
|
||||
boost = 1.3 if col_pressed else 1.0
|
||||
accent = rl.Color(139, 92, 246, 255)
|
||||
rings = [
|
||||
(32, 8),
|
||||
(24, 14),
|
||||
(17, 24),
|
||||
(8, 38),
|
||||
]
|
||||
for radius, base_alpha in rings:
|
||||
a = max(2, min(255, int(base_alpha * boost)))
|
||||
rl.draw_circle(int(orb_cx), int(orb_cy), radius, rl.Color(accent.r, accent.g, accent.b, a))
|
||||
|
||||
# Navigation buttons
|
||||
y = rect.y + 300
|
||||
for panel_type, panel_info in self._panels.items():
|
||||
button_rect = rl.Rectangle(rect.x + 50, y, rect.width - 150, NAV_BTN_HEIGHT)
|
||||
# Dark core mask — creates dark interior matching HubTile glow-border pattern
|
||||
rl.draw_circle(int(orb_cx), int(orb_cy), 11, DARK_CORE_COLOR)
|
||||
|
||||
# Button styling
|
||||
is_selected = panel_type == self._current_panel
|
||||
text_color = TEXT_SELECTED if is_selected else TEXT_NORMAL
|
||||
# Draw button text (right-aligned)
|
||||
panel_name = tr(panel_info.name)
|
||||
text_size = measure_text_cached(self._font_medium, panel_name, 65)
|
||||
text_pos = rl.Vector2(button_rect.x + button_rect.width - text_size.x, button_rect.y + (button_rect.height - text_size.y) / 2)
|
||||
rl.draw_text_ex(self._font_medium, panel_name, rl.Vector2(round(text_pos.x), round(text_pos.y)), 65, 0, text_color)
|
||||
self._draw_chevron(orb_cx, orb_cy, False, accent, size=16, bloom=True)
|
||||
|
||||
# Store button rect for click detection
|
||||
panel_info.button_rect = button_rect
|
||||
# Back/Close button - hierarchical navigation
|
||||
back_btn_rect = rl.Rectangle(rect.x + (rect.width - CLOSE_BTN_SIZE) / 2, rect.y + 60, CLOSE_BTN_SIZE, CLOSE_BTN_SIZE)
|
||||
pressed = gui_app.last_mouse_event.left_down and rl.check_collision_point_rec(gui_app.last_mouse_event.pos, back_btn_rect)
|
||||
close_color = CLOSE_BTN_PRESSED if pressed else CLOSE_BTN_COLOR
|
||||
rl.draw_rectangle_rounded(back_btn_rect, 1.0, 20, close_color)
|
||||
|
||||
y += NAV_BTN_HEIGHT
|
||||
icon_color = rl.Color(255, 255, 255, 255) if not pressed else rl.Color(220, 220, 220, 255)
|
||||
icon_dest = rl.Rectangle(
|
||||
back_btn_rect.x + (back_btn_rect.width - self._close_icon.width) / 2,
|
||||
back_btn_rect.y + (back_btn_rect.height - self._close_icon.height) / 2,
|
||||
self._close_icon.width,
|
||||
self._close_icon.height,
|
||||
)
|
||||
rl.draw_texture_pro(
|
||||
self._close_icon,
|
||||
rl.Rectangle(0, 0, self._close_icon.width, self._close_icon.height),
|
||||
icon_dest,
|
||||
rl.Vector2(0, 0),
|
||||
0,
|
||||
icon_color,
|
||||
)
|
||||
|
||||
# Store back button rect for click detection
|
||||
self._back_btn_rect = back_btn_rect
|
||||
|
||||
# Navigation buttons
|
||||
y = rect.y + 300
|
||||
for panel_type, panel_info in self._panels.items():
|
||||
button_rect = rl.Rectangle(rect.x + 50, y, rect.width - 150, NAV_BTN_HEIGHT)
|
||||
|
||||
# Button styling
|
||||
is_selected = panel_type == self._current_panel
|
||||
text_color = TEXT_SELECTED if is_selected else TEXT_NORMAL
|
||||
# Draw button text (right-aligned)
|
||||
panel_name = tr(panel_info.name)
|
||||
text_size = measure_text_cached(self._font_medium, panel_name, 65)
|
||||
text_pos = rl.Vector2(button_rect.x + button_rect.width - text_size.x, button_rect.y + (button_rect.height - text_size.y) / 2)
|
||||
rl.draw_text_ex(self._font_medium, panel_name, rl.Vector2(round(text_pos.x), round(text_pos.y)), 65, 0, text_color)
|
||||
|
||||
# Store button rect for click detection
|
||||
panel_info.button_rect = button_rect
|
||||
|
||||
y += NAV_BTN_HEIGHT
|
||||
|
||||
else:
|
||||
# ── COLLAPSED: the orb is purely visual, indicating the swipe gesture zone ──
|
||||
accent = rl.Color(139, 92, 246, 255)
|
||||
rings = [
|
||||
(32, 8),
|
||||
(24, 14),
|
||||
(17, 24),
|
||||
(8, 38),
|
||||
]
|
||||
for radius, base_alpha in rings:
|
||||
a = max(2, min(255, int(base_alpha * depth_boost)))
|
||||
rl.draw_circle(int(orb_cx), int(orb_cy), radius, rl.Color(accent.r, accent.g, accent.b, a))
|
||||
|
||||
# Dark core mask — visual continuity with expanded state
|
||||
rl.draw_circle(int(orb_cx), int(orb_cy), 11, DARK_CORE_COLOR)
|
||||
|
||||
# Dim > chevron — shares shape language with expanded state, but muted to match passive affordance
|
||||
self._draw_chevron(orb_cx, orb_cy, True, rl.Color(139, 92, 246, 120), size=10, bloom=False)
|
||||
|
||||
# Pull handle: brighter accent-line segment near orb as tap/swipe affordance
|
||||
rl.draw_rectangle_rec(rl.Rectangle(rect.x, orb_cy - 20, 2, 40), rl.Color(139, 92, 246, 100))
|
||||
|
||||
def _draw_current_panel(self, rect: rl.Rectangle):
|
||||
rl.draw_rectangle_rounded(rl.Rectangle(rect.x + 10, rect.y + 10, rect.width - 20, rect.height - 20), 0.04, 30, PANEL_COLOR)
|
||||
content_rect = rl.Rectangle(rect.x + PANEL_MARGIN, rect.y + 10, rect.width - (PANEL_MARGIN * 2), rect.height - 20)
|
||||
# rl.draw_rectangle_rounded(content_rect, 0.03, 30, PANEL_COLOR)
|
||||
panel = self._panels[self._current_panel]
|
||||
if panel.instance:
|
||||
panel.instance.render(content_rect)
|
||||
|
||||
def _handle_mouse_press(self, mouse_pos: MousePos) -> None:
|
||||
if not self._sidebar_expanded:
|
||||
# Only record swipe start when touch is within the 10px left margin
|
||||
# (gesture zone — no overlap with panel content which starts at x=10)
|
||||
gesture_zone = rl.Rectangle(self._rect.x, self._rect.y, 10, self._rect.height)
|
||||
if rl.check_collision_point_rec(mouse_pos, gesture_zone):
|
||||
self._swipe_start = mouse_pos
|
||||
else:
|
||||
self._swipe_start = None
|
||||
|
||||
def _handle_mouse_release(self, mouse_pos: MousePos) -> None:
|
||||
# Check back/close button - hierarchical navigation
|
||||
if rl.check_collision_point_rec(mouse_pos, self._back_btn_rect):
|
||||
start = self._swipe_start
|
||||
self._swipe_start = None
|
||||
|
||||
# ── Collapsed: tap or swipe from left edge ──
|
||||
if not self._sidebar_expanded and start is not None:
|
||||
dx = mouse_pos.x - start.x
|
||||
dy = abs(mouse_pos.y - start.y)
|
||||
if dx > SWIPE_THRESHOLD:
|
||||
if self._panel_depth > 0:
|
||||
self._handle_back_navigation()
|
||||
else:
|
||||
self._sidebar_expanded = True
|
||||
return
|
||||
elif dy < 20:
|
||||
self._sidebar_expanded = True
|
||||
return
|
||||
|
||||
# ── Expanded: collapse button ──
|
||||
if self._sidebar_expanded and rl.check_collision_point_rec(mouse_pos, self._collapse_btn_rect):
|
||||
self._sidebar_expanded = False
|
||||
return
|
||||
|
||||
# ── Expanded: back button ──
|
||||
if self._sidebar_expanded and rl.check_collision_point_rec(mouse_pos, self._back_btn_rect):
|
||||
self._handle_back_navigation()
|
||||
return
|
||||
|
||||
# Check navigation buttons
|
||||
for panel_type, panel_info in self._panels.items():
|
||||
if rl.check_collision_point_rec(mouse_pos, panel_info.button_rect):
|
||||
self.set_current_panel(panel_type)
|
||||
return
|
||||
# ── Expanded: nav items ──
|
||||
if self._sidebar_expanded:
|
||||
for panel_type, panel_info in self._panels.items():
|
||||
if rl.check_collision_point_rec(mouse_pos, panel_info.button_rect):
|
||||
self.set_current_panel(panel_type)
|
||||
return
|
||||
|
||||
def set_current_panel(self, panel_type: PanelType):
|
||||
if panel_type != self._current_panel:
|
||||
|
||||
@@ -1923,7 +1923,7 @@ def draw_metric_strip(
|
||||
)
|
||||
|
||||
|
||||
GROUP_HEADER_HEIGHT = 26.0
|
||||
GROUP_HEADER_HEIGHT = 30.0
|
||||
GROUP_HEADER_GAP = 1.0
|
||||
GROUP_HEADER_LINE_GAP = 1.0
|
||||
GROUP_OVERHEAD = 8.0 + GROUP_HEADER_HEIGHT + GROUP_HEADER_LINE_GAP + GROUP_HEADER_GAP
|
||||
@@ -1932,7 +1932,7 @@ GROUP_HEADER_COLOR = AetherListColors.HEADER
|
||||
|
||||
|
||||
def draw_group_header(x: float, y: float, width: float, label: str) -> float:
|
||||
gui_label(rl.Rectangle(x, y, max(1.0, width), GROUP_HEADER_HEIGHT), label, 20, GROUP_HEADER_COLOR, FontWeight.MEDIUM)
|
||||
gui_label(rl.Rectangle(x, y, max(1.0, width), GROUP_HEADER_HEIGHT), label, 26, GROUP_HEADER_COLOR, FontWeight.MEDIUM)
|
||||
y += GROUP_HEADER_HEIGHT + GROUP_HEADER_LINE_GAP
|
||||
rl.draw_line(int(x), int(y), int(x + width), int(y), GROUP_HAIRLINE_COLOR)
|
||||
return y + GROUP_HEADER_GAP
|
||||
@@ -2620,27 +2620,16 @@ class AetherAdjustorRow(Widget):
|
||||
current_border=current_border,
|
||||
)
|
||||
|
||||
title_fs = 28
|
||||
sub_fs = 24
|
||||
bar_val_fs = 20
|
||||
bar_h = max(74, min(94, int(rect.height * 0.87)))
|
||||
title_fs = max(38, int(bar_h * 0.53))
|
||||
value_fs = max(24, int(bar_h * 0.34))
|
||||
|
||||
content_left = rect.x + 24
|
||||
content_width = max(120.0, rect.width - 48)
|
||||
|
||||
title_y = rect.y + 10
|
||||
title_h = 30
|
||||
gui_label(rl.Rectangle(content_left, title_y, content_width, title_h), self._title, title_fs, self._style.title_color, FontWeight.MEDIUM)
|
||||
|
||||
sub_y = rect.y + 44
|
||||
sub_h = 28
|
||||
if self._subtitle:
|
||||
gui_label(rl.Rectangle(content_left, sub_y, content_width, sub_h), self._subtitle, sub_fs, self._style.subtitle_color, FontWeight.NORMAL)
|
||||
|
||||
bar_h = 30
|
||||
bar_y = (sub_y + sub_h + 6) if self._subtitle else (title_y + title_h + 8)
|
||||
bar_rect = snap_rect(rl.Rectangle(content_left, bar_y, rect.x + rect.width - 24 - content_left, bar_h))
|
||||
bar_width = max(120.0, rect.width - 48)
|
||||
bar_y = rect.y + (rect.height - bar_h) / 2
|
||||
bar_rect = snap_rect(rl.Rectangle(content_left, bar_y, bar_width, bar_h))
|
||||
self._progress_bar_rect = bar_rect
|
||||
self._header_rect = rl.Rectangle(rect.x, rect.y, rect.width, min(rect.height, bar_y + bar_h - rect.y))
|
||||
self._header_rect = bar_rect
|
||||
|
||||
draw_rounded_fill(bar_rect, rl.Color(255, 255, 255, 8), radius_px=bar_h // 2)
|
||||
draw_rounded_stroke(bar_rect, rl.Color(255, 255, 255, 14), radius_px=bar_h // 2)
|
||||
@@ -2648,17 +2637,27 @@ class AetherAdjustorRow(Widget):
|
||||
fill_frac = self._scrubber._value_fraction(self._current_value())
|
||||
if fill_frac > 0:
|
||||
fill_rect = snap_rect(rl.Rectangle(bar_rect.x, bar_rect.y, max(1.0, bar_rect.width * fill_frac), bar_h))
|
||||
draw_rounded_fill(fill_rect, with_alpha(self._color, 180 if active else 120), radius_px=bar_h // 2)
|
||||
fill_alpha = 200 if self._pressed_zone == "header" else (180 if active else 140)
|
||||
draw_rounded_fill(fill_rect, with_alpha(self._color, fill_alpha), radius_px=bar_h // 2)
|
||||
|
||||
draw_text_fit_common(
|
||||
self._font_value,
|
||||
self.formatted_value(),
|
||||
rl.Vector2(bar_rect.x + 12, bar_rect.y + (bar_h - bar_val_fs) / 2),
|
||||
max(1.0, bar_rect.width - 24),
|
||||
bar_val_fs,
|
||||
align_center=True,
|
||||
color=self._style.title_color,
|
||||
)
|
||||
inset = 18
|
||||
title_y = bar_rect.y + (bar_h - title_fs) / 2
|
||||
rl.draw_text_ex(self._font_title, self._title,
|
||||
rl.Vector2(bar_rect.x + inset, title_y),
|
||||
title_fs, 0, self._style.title_color)
|
||||
|
||||
value_str = self.formatted_value()
|
||||
value_w = measure_text_cached(self._font_value, value_str, value_fs).x
|
||||
rl.draw_text_ex(self._font_value, value_str,
|
||||
rl.Vector2(bar_rect.x + bar_rect.width - inset - value_w,
|
||||
bar_rect.y + (bar_h - value_fs) / 2),
|
||||
value_fs, 0, self._style.title_color)
|
||||
|
||||
if self._subtitle:
|
||||
sub_fs = 20
|
||||
sub_y = bar_rect.y - sub_fs - 4
|
||||
gui_label(rl.Rectangle(content_left, sub_y, bar_width, sub_fs),
|
||||
self._subtitle, sub_fs, self._style.subtitle_color, FontWeight.NORMAL)
|
||||
|
||||
if not active:
|
||||
return
|
||||
@@ -5550,7 +5549,7 @@ class AetherSegmentedControl(Widget):
|
||||
|
||||
label = str(_resolve_value(option, ""))
|
||||
status = str(_resolve_value(self._statuses[i], ""))
|
||||
title_size = max(26, min(35, int(face_rect.height * (0.28 if has_status else 0.36))))
|
||||
title_size = max(26, min(50, int(face_rect.height * (0.28 if has_status else 0.36))))
|
||||
status_size = max(20, min(25, int(face_rect.height * 0.22)))
|
||||
|
||||
if has_status:
|
||||
|
||||
@@ -239,19 +239,16 @@ class SoundsManagerView(PanelManagerView):
|
||||
self._adjustor_rows[self._controller.COOLDOWN_KEY].custom_row_height = None
|
||||
|
||||
hdr_h = GROUP_HEADER_HEIGHT + GROUP_HEADER_GAP + GROUP_HEADER_LINE_GAP
|
||||
vol_overhead = 4 + 24 + 4 # top pad + "Reset All" label + gap
|
||||
|
||||
if self._scroll_rect:
|
||||
available_container_h = self._scroll_rect.height - 6.0
|
||||
else:
|
||||
available_container_h = 0.0
|
||||
|
||||
left_available_for_rows = available_container_h - 12.0 - 4.0 - hdr_h
|
||||
left_row_h = max(80.0, min(107.0, left_available_for_rows / (len(self._controller.VOLUME_KEYS) + 1)))
|
||||
available_h = max(72.0, (self._scroll_rect.height if self._scroll_rect else 0.0) - 6.0)
|
||||
rows_available = max(72.0 * (len(self._controller.VOLUME_KEYS) + 1), available_h - vol_overhead)
|
||||
ROW_HEIGHT = rows_available / (len(self._controller.VOLUME_KEYS) + 1)
|
||||
for key in self._controller.VOLUME_KEYS:
|
||||
self._adjustor_rows[key].custom_row_height = left_row_h
|
||||
self._adjustor_rows[self._controller.COOLDOWN_KEY].custom_row_height = left_row_h
|
||||
self._adjustor_rows[key].custom_row_height = ROW_HEIGHT
|
||||
self._adjustor_rows[self._controller.COOLDOWN_KEY].custom_row_height = ROW_HEIGHT
|
||||
|
||||
left_content_h = (len(self._controller.VOLUME_KEYS) + 1) * left_row_h + 12 + 4 + hdr_h
|
||||
left_content_h = (len(self._controller.VOLUME_KEYS) + 1) * ROW_HEIGHT + vol_overhead
|
||||
tiles_needed_h = self.measure_page_grid_height(self._toggle_grid, col_width - 24) + 24 + 4 + hdr_h
|
||||
max_content_h = max(left_content_h, tiles_needed_h)
|
||||
|
||||
@@ -271,15 +268,7 @@ class SoundsManagerView(PanelManagerView):
|
||||
self._draw_utility_column(y, rect.x + col_width + SECTION_GAP, col_width)
|
||||
|
||||
def _draw_volume_column(self, y: float, x: float, width: float):
|
||||
safety_keys = ["WarningImmediateVolume", "WarningSoftVolume", "RefuseVolume", "PromptDistractedVolume"]
|
||||
system_keys = ["EngageVolume", "DisengageVolume"]
|
||||
info_keys = ["PromptVolume", "BelowSteerSpeedVolume"]
|
||||
|
||||
groups = [
|
||||
(None, safety_keys),
|
||||
(tr("SYSTEM STATE"), system_keys),
|
||||
(tr("INFORMATIONAL"), info_keys + [self._controller.COOLDOWN_KEY]),
|
||||
]
|
||||
all_keys = self._controller.VOLUME_KEYS + [self._controller.COOLDOWN_KEY]
|
||||
|
||||
draw_list_group_shell(
|
||||
rl.Rectangle(x, y, width, self._left_container_h),
|
||||
@@ -287,30 +276,21 @@ class SoundsManagerView(PanelManagerView):
|
||||
)
|
||||
|
||||
current_y = y + 4
|
||||
current_y = draw_group_header(x + 24, current_y, width - 48, tr("VOLUME"))
|
||||
|
||||
label_rect = rl.Rectangle(x + 24, current_y - GROUP_HEADER_HEIGHT - GROUP_HEADER_LINE_GAP - GROUP_HEADER_GAP, width - 48, GROUP_HEADER_HEIGHT)
|
||||
gui_label(label_rect, tr("Reset All"), 20, AetherListColors.MUTED, FontWeight.NORMAL,
|
||||
label_rect = rl.Rectangle(x + 24, current_y, width - 48, 24)
|
||||
gui_label(label_rect, tr("Reset All"), 24, AetherListColors.MUTED, FontWeight.NORMAL,
|
||||
alignment=rl.GuiTextAlignment.TEXT_ALIGN_RIGHT)
|
||||
self._reset_rect = rl.Rectangle(label_rect.x + label_rect.width - 80, label_rect.y, 80, 45)
|
||||
self._reset_rect = rl.Rectangle(label_rect.x + label_rect.width - 140, label_rect.y, 140, 24)
|
||||
self._interactive_rects["action:restore_defaults"] = self._reset_rect
|
||||
for i, (label, keys) in enumerate(groups):
|
||||
if label is not None:
|
||||
divider_h = 3
|
||||
divider_color = rl.Color(173, 78, 90, 30) if i == 1 else rl.Color(139, 92, 246, 25)
|
||||
rl.draw_rectangle_rec(
|
||||
rl.Rectangle(x + 24, current_y, width - 48, divider_h),
|
||||
divider_color
|
||||
)
|
||||
current_y += divider_h + 3
|
||||
for index, key in enumerate(keys):
|
||||
adjustor = self._adjustor_rows[key]
|
||||
row_h = adjustor.measure_height(width)
|
||||
row_rect = rl.Rectangle(x, current_y, width, row_h)
|
||||
adjustor.set_is_last(index == len(keys) - 1)
|
||||
adjustor.set_parent_rect(self._scroll_rect)
|
||||
adjustor.render(row_rect)
|
||||
current_y += row_h
|
||||
current_y += 28
|
||||
for index, key in enumerate(all_keys):
|
||||
adjustor = self._adjustor_rows[key]
|
||||
row_h = adjustor.measure_height(width)
|
||||
row_rect = rl.Rectangle(x, current_y, width, row_h)
|
||||
adjustor.set_is_last(index == len(all_keys) - 1)
|
||||
adjustor.set_parent_rect(self._scroll_rect)
|
||||
adjustor.render(row_rect)
|
||||
current_y += row_h
|
||||
|
||||
def _draw_utility_column(self, y: float, x: float, width: float):
|
||||
draw_list_group_shell(rl.Rectangle(x, y, width, self._tiles_container_h), style=PANEL_STYLE)
|
||||
|
||||
@@ -107,8 +107,8 @@ class SystemSettingsManagerView(PanelManagerView):
|
||||
TAB_BOTTOM_GAP = 26
|
||||
ACTION_PILL_WIDTH = 132
|
||||
DANGER_PILL_WIDTH = 112
|
||||
_TOPBAR_HEIGHT = 76.0
|
||||
_TOPBAR_GAP = 16.0
|
||||
_TOPBAR_HEIGHT = 120.0
|
||||
_TOPBAR_GAP = 0.0
|
||||
METRICS = SYSTEM_PANEL_METRICS
|
||||
|
||||
@property
|
||||
|
||||
Reference in New Issue
Block a user