mirror of
https://github.com/AvengeMedia/DankMaterialShell.git
synced 2025-12-06 05:25:41 -05:00
consistency in top bar tab of settings
This commit is contained in:
117
CLAUDE.md
117
CLAUDE.md
@@ -62,6 +62,7 @@ quickshell -p shell.qml
|
||||
qs -p .
|
||||
|
||||
# Code formatting and linting
|
||||
./qmlformat-all.sh # Format all QML files using project script
|
||||
qmlformat -i **/*.qml # Format all QML files in place
|
||||
qmllint **/*.qml # Lint all QML files for syntax errors
|
||||
```
|
||||
@@ -74,27 +75,43 @@ The shell follows a clean modular architecture reduced from 4,830 lines to ~250
|
||||
|
||||
```
|
||||
shell.qml # Main entry point (minimal orchestration)
|
||||
├── Common/ # Shared resources
|
||||
├── Common/ # Shared resources (12 files)
|
||||
│ ├── Theme.qml # Material Design 3 theme singleton
|
||||
│ └── Utilities.js # Shared utility functions
|
||||
├── Services/ # System integration singletons
|
||||
│ ├── SettingsData.qml # User preferences and configuration
|
||||
│ ├── SessionData.qml # Session state management
|
||||
│ ├── Colors.qml # Dynamic color scheme
|
||||
│ └── [8 more utility files]
|
||||
├── Services/ # System integration singletons (20 files)
|
||||
│ ├── AudioService.qml
|
||||
│ ├── NetworkService.qml
|
||||
│ ├── BluetoothService.qml
|
||||
│ ├── BrightnessService.qml
|
||||
│ └── [9 total services]
|
||||
├── Modules/ # UI components
|
||||
│ ├── TopBar.qml
|
||||
│ ├── AppLauncher.qml
|
||||
│ ├── ControlCenter.qml
|
||||
│ └── [18 total modules]
|
||||
└── Widgets/ # Reusable UI controls
|
||||
│ ├── NotificationService.qml
|
||||
│ ├── WeatherService.qml
|
||||
│ └── [14 more services]
|
||||
├── Modules/ # UI components (93 files)
|
||||
│ ├── TopBar/ # Panel components (13 files)
|
||||
│ ├── ControlCenter/ # System controls (13 files)
|
||||
│ ├── Notifications/ # Notification system (12 files)
|
||||
│ ├── AppDrawer/ # Application launcher (3 files)
|
||||
│ ├── Settings/ # Configuration interface (11 files)
|
||||
│ ├── ProcessList/ # System monitoring (8 files)
|
||||
│ ├── Dock/ # Application dock (6 files)
|
||||
│ ├── Lock/ # Screen lock system (4 files)
|
||||
│ └── [23 more module files]
|
||||
├── Modals/ # Full-screen overlays (10 files)
|
||||
│ ├── SettingsModal.qml
|
||||
│ ├── ClipboardHistoryModal.qml
|
||||
│ ├── ProcessListModal.qml
|
||||
│ └── [7 more modals]
|
||||
└── Widgets/ # Reusable UI controls (19 files)
|
||||
├── DankIcon.qml
|
||||
├── DankSlider.qml
|
||||
├── DankToggle.qml
|
||||
├── DankTabBar.qml
|
||||
├── DankGridView.qml
|
||||
├── DankListView.qml
|
||||
└── [6 total widgets]
|
||||
└── [13 more widgets]
|
||||
```
|
||||
|
||||
### Component Organization
|
||||
@@ -112,21 +129,39 @@ shell.qml # Main entry point (minimal orchestration)
|
||||
3. **Services/** - System integration singletons
|
||||
- **Pattern**: All services use `Singleton` type with `id: root`
|
||||
- **Independence**: No cross-service dependencies
|
||||
- **Examples**: AudioService, NetworkService, BrightnessService, WeatherService
|
||||
- **Examples**: AudioService, NetworkService, BluetoothService, BrightnessService, WeatherService, NotificationService, CalendarService, BatteryService, NiriService, MprisController
|
||||
- Services handle system commands, state management, and hardware integration
|
||||
|
||||
4. **Modules/** - UI components
|
||||
- **Full-screen components**: AppLauncher, ClipboardHistoryModal, ControlCenter
|
||||
- **Panel components**: TopBar, SystemTray, NotificationPopup
|
||||
- **Layout components**: WorkspaceSwitcher
|
||||
4. **Modules/** - UI components (93 files)
|
||||
- **TopBar/**: Panel components with workspace switching, system indicators, media controls
|
||||
- **ControlCenter/**: System controls for WiFi, Bluetooth, audio, display settings
|
||||
- **Notifications/**: Complete notification system with center, popups, and keyboard navigation
|
||||
- **AppDrawer/**: Application launcher with grid/list views and category filtering
|
||||
- **Settings/**: Comprehensive configuration interface with multiple tabs
|
||||
- **ProcessList/**: System monitoring with process management and performance metrics
|
||||
- **Dock/**: Application dock with running apps and window management
|
||||
- **Lock/**: Screen lock system with authentication
|
||||
- **CentcomCenter/**: Calendar, weather, and media widgets
|
||||
|
||||
5. **Widgets/** - Reusable UI controls
|
||||
5. **Modals/** - Full-screen overlays (10 files)
|
||||
- Modal system for settings, clipboard history, file browser, network info, power menu
|
||||
- Unified modal management with consistent styling and keyboard navigation
|
||||
|
||||
6. **Widgets/** - Reusable UI controls (19 files)
|
||||
- **DankIcon**: Centralized icon component with Material Design font integration
|
||||
- **DankSlider**: Enhanced slider with animations and smart detection
|
||||
- **DankToggle**: Consistent toggle switch component
|
||||
- **DankTabBar**: Unified tab bar implementation
|
||||
- **DankGridView**: Reusable grid view with adaptive columns
|
||||
- **DankListView**: Reusable list view with configurable styling
|
||||
- **DankTextField**: Styled text input with validation
|
||||
- **DankDropdown**: Dropdown selection component
|
||||
- **DankPopout**: Base popout component for overlays
|
||||
- **StateLayer**: Material Design 3 interaction states
|
||||
- **StyledRect/StyledText**: Themed base components
|
||||
- **CachingImage**: Optimized image loading with caching
|
||||
- **DankLocationSearch**: Location picker with search
|
||||
- **SystemLogo**: Animated system branding component
|
||||
|
||||
### Key Architectural Patterns
|
||||
|
||||
@@ -183,7 +218,7 @@ shell.qml # Main entry point (minimal orchestration)
|
||||
- `id` should be the first property
|
||||
- Properties before signal handlers before child components
|
||||
- Prefer property bindings over imperative code
|
||||
- **IMPORTANT**: Be very conservative with comments - add comments only when absolutely necessary for understanding complex logic
|
||||
- **CRITICAL**: NEVER add comments unless absolutely essential for complex logic understanding. Code should be self-documenting through clear naming and structure. Comments are a code smell indicating unclear implementation.
|
||||
|
||||
2. **Naming Conventions**:
|
||||
- **Services**: Use `Singleton` type with `id: root`
|
||||
@@ -243,7 +278,14 @@ shell.qml # Main entry point (minimal orchestration)
|
||||
|
||||
### Component Development Patterns
|
||||
|
||||
1. **Smart Feature Detection**:
|
||||
1. **Code Reuse - Search Before Writing**:
|
||||
- **ALWAYS** search the codebase for existing functions before writing new ones
|
||||
- Use `Grep` or `Glob` tools to find existing implementations (e.g., search for "getWifiIcon", "getDeviceIcon")
|
||||
- Many utility functions already exist in Services/ and Common/ - reuse them instead of duplicating
|
||||
- Examples of existing utility functions: `Theme.getBatteryIcon()`, `BluetoothService.getDeviceIcon()`, `WeatherService.getWeatherIcon()`
|
||||
- If similar functionality exists, extend or refactor rather than duplicate
|
||||
|
||||
2. **Smart Feature Detection**:
|
||||
```qml
|
||||
// In services - detect capabilities
|
||||
property bool brightnessAvailable: false
|
||||
@@ -256,12 +298,12 @@ shell.qml # Main entry point (minimal orchestration)
|
||||
}
|
||||
```
|
||||
|
||||
2. **Reusable Components**:
|
||||
3. **Reusable Components**:
|
||||
- Create reusable widgets for common patterns (like DankSlider)
|
||||
- Use configurable properties for different use cases
|
||||
- Include proper signal handling with unique names (avoid `valueChanged`)
|
||||
|
||||
3. **Service Integration**:
|
||||
4. **Service Integration**:
|
||||
- Services expose properties and functions
|
||||
- Modules and Widgets bind to service properties for reactive updates
|
||||
- Use service functions for actions: `ServiceName.performAction(value)`
|
||||
@@ -305,7 +347,7 @@ The shell uses Quickshell's `Variants` pattern for multi-monitor support:
|
||||
|
||||
When modifying the shell:
|
||||
1. **Test changes**: `qs -p .` (automatic reload on file changes)
|
||||
2. **Code quality**: Run `qmlformat -i **/*.qml` and `qmllint **/*.qml` to ensure proper formatting and syntax
|
||||
2. **Code quality**: Run `./qmlformat-all.sh` or `qmlformat -i **/*.qml` and `qmllint **/*.qml` to ensure proper formatting and syntax
|
||||
3. **Performance**: Ensure animations remain smooth (60 FPS target)
|
||||
4. **Theming**: Use `Theme.propertyName` for Material Design 3 consistency
|
||||
5. **Wayland compatibility**: Test on Wayland session
|
||||
@@ -396,6 +438,8 @@ When modifying the shell:
|
||||
|
||||
### Best Practices Summary
|
||||
|
||||
- **Code Reuse**: ALWAYS search existing codebase before writing new functions - avoid duplication at all costs
|
||||
- **No Comments**: Code should be self-documenting - comments indicate poor naming/structure
|
||||
- **Modularity**: Keep components focused and independent
|
||||
- **Reusability**: Create reusable components for common patterns using Widgets/
|
||||
- **Responsiveness**: Use property bindings for reactive UI
|
||||
@@ -405,6 +449,9 @@ When modifying the shell:
|
||||
- **Icon Management**: Use `DankIcon` for all icons instead of manual Text components
|
||||
- **Widget System**: Leverage existing widgets (DankSlider, DankToggle, etc.) for consistency
|
||||
- **NO WRAPPER HELL**: Avoid creating unnecessary wrapper functions - bind directly to underlying APIs for better reactivity and performance
|
||||
- **Function Discovery**: Use grep/search tools to find existing utility functions before implementing new ones
|
||||
- **Modern QML Patterns**: Leverage new widgets like DankTextField, DankDropdown, CachingImage
|
||||
- **Structured Organization**: Follow the established Services/Modules/Widgets/Modals separation
|
||||
|
||||
### Common Widget Patterns
|
||||
|
||||
@@ -414,3 +461,29 @@ When modifying the shell:
|
||||
4. **Tab Bars**: Use `DankTabBar` for tabbed interfaces
|
||||
5. **Lists**: Use `DankListView` for scrollable lists
|
||||
6. **Grids**: Use `DankGridView` for grid layouts
|
||||
7. **Text Fields**: Use `DankTextField` for text input with validation
|
||||
8. **Dropdowns**: Use `DankDropdown` for selection menus
|
||||
9. **Popouts**: Use `DankPopout` as base for overlay components
|
||||
10. **Images**: Use `CachingImage` for optimized image loading
|
||||
|
||||
### Essential Utility Functions
|
||||
|
||||
Before writing new utility functions, check these existing ones:
|
||||
|
||||
**Theme.qml utilities:**
|
||||
- `getBatteryIcon(level, isCharging, batteryAvailable)` - Battery status icons
|
||||
- `getPowerProfileIcon(profile)` - Power profile indicators
|
||||
|
||||
**Service utilities:**
|
||||
- `BluetoothService.getDeviceIcon(device)` - Bluetooth device type icons
|
||||
- `BluetoothService.getSignalIcon(device)` - Signal strength indicators
|
||||
- `WeatherService.getWeatherIcon(code)` - Weather condition icons
|
||||
- `AppSearchService.getCategoryIcon(category)` - Application category icons
|
||||
- `DgopService.getProcessIcon(command)` - Process type icons
|
||||
- `SettingsData.getWorkspaceNameIcon(workspaceName)` - Workspace icons
|
||||
|
||||
**Always search for existing functions using:**
|
||||
```bash
|
||||
grep -r "function.*get.*Icon" Services/ Common/
|
||||
grep -r "function.*" path/to/relevant/directory/
|
||||
```
|
||||
|
||||
@@ -879,6 +879,68 @@ Item {
|
||||
|
||||
}
|
||||
|
||||
// Corner Radius
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
height: cornerRadiusSection.implicitHeight + Theme.spacingL * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
Column {
|
||||
id: cornerRadiusSection
|
||||
|
||||
anchors.fill: parent
|
||||
anchors.margins: Theme.spacingL
|
||||
spacing: Theme.spacingM
|
||||
|
||||
Row {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingM
|
||||
|
||||
DankIcon {
|
||||
name: "rounded_corner"
|
||||
size: Theme.iconSize
|
||||
color: Theme.primary
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
StyledText {
|
||||
text: "Corner Radius"
|
||||
font.pixelSize: Theme.fontSizeLarge
|
||||
font.weight: Font.Medium
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingS
|
||||
|
||||
StyledText {
|
||||
text: "Bar & Widget Corner Roundness"
|
||||
font.pixelSize: Theme.fontSizeSmall
|
||||
color: Theme.surfaceText
|
||||
font.weight: Font.Medium
|
||||
}
|
||||
|
||||
DankSlider {
|
||||
width: parent.width
|
||||
height: 24
|
||||
value: SettingsData.cornerRadius
|
||||
minimum: 0
|
||||
maximum: 32
|
||||
unit: ""
|
||||
showValue: true
|
||||
onSliderValueChanged: (newValue) => {
|
||||
SettingsData.setCornerRadius(newValue);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import QtQuick
|
||||
import QtQuick.Controls
|
||||
import QtQuick.Layouts
|
||||
import qs.Common
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
@@ -512,326 +513,6 @@ Item {
|
||||
|
||||
}
|
||||
|
||||
Row {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingM
|
||||
|
||||
DankIcon {
|
||||
name: "widgets"
|
||||
size: Theme.iconSize
|
||||
color: Theme.primary
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
StyledText {
|
||||
text: "Widget Management"
|
||||
font.pixelSize: Theme.fontSizeLarge
|
||||
font.weight: Font.Medium
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
Item {
|
||||
width: parent.width - 400
|
||||
height: 1
|
||||
}
|
||||
|
||||
Rectangle {
|
||||
width: 80
|
||||
height: 28
|
||||
radius: Theme.cornerRadius
|
||||
color: resetArea.containsMouse ? Theme.surfacePressed : Theme.surfaceVariant
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
border.width: 1
|
||||
border.color: resetArea.containsMouse ? Theme.outline : Qt.rgba(
|
||||
Theme.outline.r,
|
||||
Theme.outline.g,
|
||||
Theme.outline.b, 0.5)
|
||||
|
||||
Row {
|
||||
anchors.centerIn: parent
|
||||
spacing: Theme.spacingXS
|
||||
|
||||
DankIcon {
|
||||
name: "refresh"
|
||||
size: 14
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
StyledText {
|
||||
text: "Reset"
|
||||
font.pixelSize: Theme.fontSizeSmall
|
||||
font.weight: Font.Medium
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
}
|
||||
|
||||
MouseArea {
|
||||
id: resetArea
|
||||
|
||||
anchors.fill: parent
|
||||
hoverEnabled: true
|
||||
cursorShape: Qt.PointingHandCursor
|
||||
onClicked: {
|
||||
SettingsData.setTopBarLeftWidgets(defaultLeftWidgets)
|
||||
SettingsData.setTopBarCenterWidgets(defaultCenterWidgets)
|
||||
SettingsData.setTopBarRightWidgets(defaultRightWidgets)
|
||||
}
|
||||
}
|
||||
|
||||
Behavior on color {
|
||||
ColorAnimation {
|
||||
duration: Theme.shortDuration
|
||||
easing.type: Theme.standardEasing
|
||||
}
|
||||
}
|
||||
|
||||
Behavior on border.color {
|
||||
ColorAnimation {
|
||||
duration: Theme.shortDuration
|
||||
easing.type: Theme.standardEasing
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Rectangle {
|
||||
width: parent.width
|
||||
height: messageText.contentHeight + Theme.spacingM * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g,
|
||||
Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g,
|
||||
Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
StyledText {
|
||||
id: messageText
|
||||
|
||||
anchors.centerIn: parent
|
||||
text: "Drag widgets to reorder within sections. Use the eye icon to hide/show widgets (maintains spacing), or X to remove them completely."
|
||||
font.pixelSize: Theme.fontSizeSmall
|
||||
color: Theme.outline
|
||||
width: parent.width - Theme.spacingM * 2
|
||||
wrapMode: Text.WordWrap
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingL
|
||||
|
||||
WidgetsTabSection {
|
||||
width: parent.width
|
||||
title: "Left Section"
|
||||
titleIcon: "format_align_left"
|
||||
sectionId: "left"
|
||||
allWidgets: topBarTab.baseWidgetDefinitions
|
||||
items: topBarTab.getItemsForSection("left")
|
||||
onItemEnabledChanged: (sectionId, itemId, enabled) => {
|
||||
topBarTab.handleItemEnabledChanged(sectionId,
|
||||
itemId,
|
||||
enabled)
|
||||
}
|
||||
onItemOrderChanged: newOrder => {
|
||||
topBarTab.handleItemOrderChanged("left",
|
||||
newOrder)
|
||||
}
|
||||
onAddWidget: sectionId => {
|
||||
widgetSelectionPopup.allWidgets = topBarTab.baseWidgetDefinitions
|
||||
widgetSelectionPopup.targetSection = sectionId
|
||||
widgetSelectionPopup.safeOpen()
|
||||
}
|
||||
onRemoveWidget: (sectionId, widgetIndex) => {
|
||||
topBarTab.removeWidgetFromSection(sectionId,
|
||||
widgetIndex)
|
||||
}
|
||||
onSpacerSizeChanged: (sectionId, itemId, newSize) => {
|
||||
topBarTab.handleSpacerSizeChanged(sectionId,
|
||||
itemId,
|
||||
newSize)
|
||||
}
|
||||
onCompactModeChanged: (widgetId, value) => {
|
||||
if (widgetId === "clock") {
|
||||
SettingsData.setClockCompactMode(value)
|
||||
} else if (widgetId === "music") {
|
||||
SettingsData.setMediaSize(value)
|
||||
} else if (widgetId === "focusedWindow") {
|
||||
SettingsData.setFocusedWindowCompactMode(value)
|
||||
} else if (widgetId === "runningApps") {
|
||||
SettingsData.setRunningAppsCompactMode(value)
|
||||
}
|
||||
}
|
||||
onGpuSelectionChanged: (sectionId, widgetIndex, selectedIndex) => {
|
||||
topBarTab.handleGpuSelectionChanged(
|
||||
sectionId, widgetIndex, selectedIndex)
|
||||
}
|
||||
}
|
||||
|
||||
WidgetsTabSection {
|
||||
width: parent.width
|
||||
title: "Center Section"
|
||||
titleIcon: "format_align_center"
|
||||
sectionId: "center"
|
||||
allWidgets: topBarTab.baseWidgetDefinitions
|
||||
items: topBarTab.getItemsForSection("center")
|
||||
onItemEnabledChanged: (sectionId, itemId, enabled) => {
|
||||
topBarTab.handleItemEnabledChanged(sectionId,
|
||||
itemId,
|
||||
enabled)
|
||||
}
|
||||
onItemOrderChanged: newOrder => {
|
||||
topBarTab.handleItemOrderChanged("center",
|
||||
newOrder)
|
||||
}
|
||||
onAddWidget: sectionId => {
|
||||
widgetSelectionPopup.allWidgets = topBarTab.baseWidgetDefinitions
|
||||
widgetSelectionPopup.targetSection = sectionId
|
||||
widgetSelectionPopup.safeOpen()
|
||||
}
|
||||
onRemoveWidget: (sectionId, widgetIndex) => {
|
||||
topBarTab.removeWidgetFromSection(sectionId,
|
||||
widgetIndex)
|
||||
}
|
||||
onSpacerSizeChanged: (sectionId, itemId, newSize) => {
|
||||
topBarTab.handleSpacerSizeChanged(sectionId,
|
||||
itemId,
|
||||
newSize)
|
||||
}
|
||||
onCompactModeChanged: (widgetId, value) => {
|
||||
if (widgetId === "clock") {
|
||||
SettingsData.setClockCompactMode(value)
|
||||
} else if (widgetId === "music") {
|
||||
SettingsData.setMediaSize(value)
|
||||
} else if (widgetId === "focusedWindow") {
|
||||
SettingsData.setFocusedWindowCompactMode(value)
|
||||
} else if (widgetId === "runningApps") {
|
||||
SettingsData.setRunningAppsCompactMode(value)
|
||||
}
|
||||
}
|
||||
onGpuSelectionChanged: (sectionId, widgetIndex, selectedIndex) => {
|
||||
topBarTab.handleGpuSelectionChanged(
|
||||
sectionId, widgetIndex, selectedIndex)
|
||||
}
|
||||
}
|
||||
|
||||
WidgetsTabSection {
|
||||
width: parent.width
|
||||
title: "Right Section"
|
||||
titleIcon: "format_align_right"
|
||||
sectionId: "right"
|
||||
allWidgets: topBarTab.baseWidgetDefinitions
|
||||
items: topBarTab.getItemsForSection("right")
|
||||
onItemEnabledChanged: (sectionId, itemId, enabled) => {
|
||||
topBarTab.handleItemEnabledChanged(sectionId,
|
||||
itemId,
|
||||
enabled)
|
||||
}
|
||||
onItemOrderChanged: newOrder => {
|
||||
topBarTab.handleItemOrderChanged("right",
|
||||
newOrder)
|
||||
}
|
||||
onAddWidget: sectionId => {
|
||||
widgetSelectionPopup.allWidgets = topBarTab.baseWidgetDefinitions
|
||||
widgetSelectionPopup.targetSection = sectionId
|
||||
widgetSelectionPopup.safeOpen()
|
||||
}
|
||||
onRemoveWidget: (sectionId, widgetIndex) => {
|
||||
topBarTab.removeWidgetFromSection(sectionId,
|
||||
widgetIndex)
|
||||
}
|
||||
onSpacerSizeChanged: (sectionId, itemId, newSize) => {
|
||||
topBarTab.handleSpacerSizeChanged(sectionId,
|
||||
itemId,
|
||||
newSize)
|
||||
}
|
||||
onCompactModeChanged: (widgetId, value) => {
|
||||
if (widgetId === "clock") {
|
||||
SettingsData.setClockCompactMode(value)
|
||||
} else if (widgetId === "music") {
|
||||
SettingsData.setMediaSize(value)
|
||||
} else if (widgetId === "focusedWindow") {
|
||||
SettingsData.setFocusedWindowCompactMode(value)
|
||||
} else if (widgetId === "runningApps") {
|
||||
SettingsData.setRunningAppsCompactMode(value)
|
||||
}
|
||||
}
|
||||
onGpuSelectionChanged: (sectionId, widgetIndex, selectedIndex) => {
|
||||
topBarTab.handleGpuSelectionChanged(
|
||||
sectionId, widgetIndex, selectedIndex)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Corner Radius
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
height: cornerRadiusSection.implicitHeight + Theme.spacingL * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
Column {
|
||||
id: cornerRadiusSection
|
||||
|
||||
anchors.fill: parent
|
||||
anchors.margins: Theme.spacingL
|
||||
spacing: Theme.spacingM
|
||||
|
||||
Row {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingM
|
||||
|
||||
DankIcon {
|
||||
name: "rounded_corner"
|
||||
size: Theme.iconSize
|
||||
color: Theme.primary
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
StyledText {
|
||||
text: "Corner Radius"
|
||||
font.pixelSize: Theme.fontSizeLarge
|
||||
font.weight: Font.Medium
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Column {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingS
|
||||
|
||||
StyledText {
|
||||
text: "Bar & Widget Corner Roundness"
|
||||
font.pixelSize: Theme.fontSizeSmall
|
||||
color: Theme.surfaceText
|
||||
font.weight: Font.Medium
|
||||
}
|
||||
|
||||
DankSlider {
|
||||
width: parent.width
|
||||
height: 24
|
||||
value: SettingsData.cornerRadius
|
||||
minimum: 0
|
||||
maximum: 32
|
||||
unit: ""
|
||||
showValue: true
|
||||
onSliderValueChanged: (newValue) => {
|
||||
SettingsData.setCornerRadius(newValue);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Spacing
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
@@ -908,6 +589,302 @@ Item {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Widget Management Section
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
height: widgetManagementSection.implicitHeight + Theme.spacingL * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
Column {
|
||||
id: widgetManagementSection
|
||||
|
||||
anchors.fill: parent
|
||||
anchors.margins: Theme.spacingL
|
||||
spacing: Theme.spacingM
|
||||
|
||||
RowLayout {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingM
|
||||
|
||||
DankIcon {
|
||||
id: widgetIcon
|
||||
name: "widgets"
|
||||
size: Theme.iconSize
|
||||
color: Theme.primary
|
||||
Layout.alignment: Qt.AlignVCenter
|
||||
}
|
||||
|
||||
StyledText {
|
||||
id: widgetTitle
|
||||
text: "Widget Management"
|
||||
font.pixelSize: Theme.fontSizeLarge
|
||||
font.weight: Font.Medium
|
||||
color: Theme.surfaceText
|
||||
Layout.alignment: Qt.AlignVCenter
|
||||
}
|
||||
|
||||
Item {
|
||||
height: 1
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
|
||||
Rectangle {
|
||||
id: resetButton
|
||||
width: 80
|
||||
height: 28
|
||||
radius: Theme.cornerRadius
|
||||
color: resetArea.containsMouse ? Theme.surfacePressed : Theme.surfaceVariant
|
||||
Layout.alignment: Qt.AlignVCenter
|
||||
border.width: 1
|
||||
border.color: resetArea.containsMouse ? Theme.outline : Qt.rgba(
|
||||
Theme.outline.r,
|
||||
Theme.outline.g,
|
||||
Theme.outline.b, 0.5)
|
||||
|
||||
Row {
|
||||
anchors.centerIn: parent
|
||||
spacing: Theme.spacingXS
|
||||
|
||||
DankIcon {
|
||||
name: "refresh"
|
||||
size: 14
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
|
||||
StyledText {
|
||||
text: "Reset"
|
||||
font.pixelSize: Theme.fontSizeSmall
|
||||
font.weight: Font.Medium
|
||||
color: Theme.surfaceText
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
}
|
||||
}
|
||||
|
||||
MouseArea {
|
||||
id: resetArea
|
||||
|
||||
anchors.fill: parent
|
||||
hoverEnabled: true
|
||||
cursorShape: Qt.PointingHandCursor
|
||||
onClicked: {
|
||||
SettingsData.setTopBarLeftWidgets(defaultLeftWidgets)
|
||||
SettingsData.setTopBarCenterWidgets(defaultCenterWidgets)
|
||||
SettingsData.setTopBarRightWidgets(defaultRightWidgets)
|
||||
}
|
||||
}
|
||||
|
||||
Behavior on color {
|
||||
ColorAnimation {
|
||||
duration: Theme.shortDuration
|
||||
easing.type: Theme.standardEasing
|
||||
}
|
||||
}
|
||||
|
||||
Behavior on border.color {
|
||||
ColorAnimation {
|
||||
duration: Theme.shortDuration
|
||||
easing.type: Theme.standardEasing
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
StyledText {
|
||||
width: parent.width
|
||||
text: "Drag widgets to reorder within sections. Use the eye icon to hide/show widgets (maintains spacing), or X to remove them completely."
|
||||
font.pixelSize: Theme.fontSizeSmall
|
||||
color: Theme.surfaceVariantText
|
||||
wrapMode: Text.WordWrap
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Column {
|
||||
width: parent.width
|
||||
spacing: Theme.spacingL
|
||||
|
||||
// Left Section
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
height: leftSection.implicitHeight + Theme.spacingL * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
WidgetsTabSection {
|
||||
id: leftSection
|
||||
anchors.fill: parent
|
||||
anchors.margins: Theme.spacingL
|
||||
title: "Left Section"
|
||||
titleIcon: "format_align_left"
|
||||
sectionId: "left"
|
||||
allWidgets: topBarTab.baseWidgetDefinitions
|
||||
items: topBarTab.getItemsForSection("left")
|
||||
onItemEnabledChanged: (sectionId, itemId, enabled) => {
|
||||
topBarTab.handleItemEnabledChanged(sectionId,
|
||||
itemId,
|
||||
enabled)
|
||||
}
|
||||
onItemOrderChanged: newOrder => {
|
||||
topBarTab.handleItemOrderChanged("left",
|
||||
newOrder)
|
||||
}
|
||||
onAddWidget: sectionId => {
|
||||
widgetSelectionPopup.allWidgets = topBarTab.baseWidgetDefinitions
|
||||
widgetSelectionPopup.targetSection = sectionId
|
||||
widgetSelectionPopup.safeOpen()
|
||||
}
|
||||
onRemoveWidget: (sectionId, widgetIndex) => {
|
||||
topBarTab.removeWidgetFromSection(sectionId,
|
||||
widgetIndex)
|
||||
}
|
||||
onSpacerSizeChanged: (sectionId, itemId, newSize) => {
|
||||
topBarTab.handleSpacerSizeChanged(sectionId,
|
||||
itemId,
|
||||
newSize)
|
||||
}
|
||||
onCompactModeChanged: (widgetId, value) => {
|
||||
if (widgetId === "clock") {
|
||||
SettingsData.setClockCompactMode(value)
|
||||
} else if (widgetId === "music") {
|
||||
SettingsData.setMediaSize(value)
|
||||
} else if (widgetId === "focusedWindow") {
|
||||
SettingsData.setFocusedWindowCompactMode(value)
|
||||
} else if (widgetId === "runningApps") {
|
||||
SettingsData.setRunningAppsCompactMode(value)
|
||||
}
|
||||
}
|
||||
onGpuSelectionChanged: (sectionId, widgetIndex, selectedIndex) => {
|
||||
topBarTab.handleGpuSelectionChanged(
|
||||
sectionId, widgetIndex, selectedIndex)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Center Section
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
height: centerSection.implicitHeight + Theme.spacingL * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
WidgetsTabSection {
|
||||
id: centerSection
|
||||
anchors.fill: parent
|
||||
anchors.margins: Theme.spacingL
|
||||
title: "Center Section"
|
||||
titleIcon: "format_align_center"
|
||||
sectionId: "center"
|
||||
allWidgets: topBarTab.baseWidgetDefinitions
|
||||
items: topBarTab.getItemsForSection("center")
|
||||
onItemEnabledChanged: (sectionId, itemId, enabled) => {
|
||||
topBarTab.handleItemEnabledChanged(sectionId,
|
||||
itemId,
|
||||
enabled)
|
||||
}
|
||||
onItemOrderChanged: newOrder => {
|
||||
topBarTab.handleItemOrderChanged("center",
|
||||
newOrder)
|
||||
}
|
||||
onAddWidget: sectionId => {
|
||||
widgetSelectionPopup.allWidgets = topBarTab.baseWidgetDefinitions
|
||||
widgetSelectionPopup.targetSection = sectionId
|
||||
widgetSelectionPopup.safeOpen()
|
||||
}
|
||||
onRemoveWidget: (sectionId, widgetIndex) => {
|
||||
topBarTab.removeWidgetFromSection(sectionId,
|
||||
widgetIndex)
|
||||
}
|
||||
onSpacerSizeChanged: (sectionId, itemId, newSize) => {
|
||||
topBarTab.handleSpacerSizeChanged(sectionId,
|
||||
itemId,
|
||||
newSize)
|
||||
}
|
||||
onCompactModeChanged: (widgetId, value) => {
|
||||
if (widgetId === "clock") {
|
||||
SettingsData.setClockCompactMode(value)
|
||||
} else if (widgetId === "music") {
|
||||
SettingsData.setMediaSize(value)
|
||||
} else if (widgetId === "focusedWindow") {
|
||||
SettingsData.setFocusedWindowCompactMode(value)
|
||||
} else if (widgetId === "runningApps") {
|
||||
SettingsData.setRunningAppsCompactMode(value)
|
||||
}
|
||||
}
|
||||
onGpuSelectionChanged: (sectionId, widgetIndex, selectedIndex) => {
|
||||
topBarTab.handleGpuSelectionChanged(
|
||||
sectionId, widgetIndex, selectedIndex)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Right Section
|
||||
StyledRect {
|
||||
width: parent.width
|
||||
height: rightSection.implicitHeight + Theme.spacingL * 2
|
||||
radius: Theme.cornerRadius
|
||||
color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, Theme.surfaceVariant.b, 0.3)
|
||||
border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, Theme.outline.b, 0.2)
|
||||
border.width: 1
|
||||
|
||||
WidgetsTabSection {
|
||||
id: rightSection
|
||||
anchors.fill: parent
|
||||
anchors.margins: Theme.spacingL
|
||||
title: "Right Section"
|
||||
titleIcon: "format_align_right"
|
||||
sectionId: "right"
|
||||
allWidgets: topBarTab.baseWidgetDefinitions
|
||||
items: topBarTab.getItemsForSection("right")
|
||||
onItemEnabledChanged: (sectionId, itemId, enabled) => {
|
||||
topBarTab.handleItemEnabledChanged(sectionId,
|
||||
itemId,
|
||||
enabled)
|
||||
}
|
||||
onItemOrderChanged: newOrder => {
|
||||
topBarTab.handleItemOrderChanged("right",
|
||||
newOrder)
|
||||
}
|
||||
onAddWidget: sectionId => {
|
||||
widgetSelectionPopup.allWidgets = topBarTab.baseWidgetDefinitions
|
||||
widgetSelectionPopup.targetSection = sectionId
|
||||
widgetSelectionPopup.safeOpen()
|
||||
}
|
||||
onRemoveWidget: (sectionId, widgetIndex) => {
|
||||
topBarTab.removeWidgetFromSection(sectionId,
|
||||
widgetIndex)
|
||||
}
|
||||
onSpacerSizeChanged: (sectionId, itemId, newSize) => {
|
||||
topBarTab.handleSpacerSizeChanged(sectionId,
|
||||
itemId,
|
||||
newSize)
|
||||
}
|
||||
onCompactModeChanged: (widgetId, value) => {
|
||||
if (widgetId === "clock") {
|
||||
SettingsData.setClockCompactMode(value)
|
||||
} else if (widgetId === "music") {
|
||||
SettingsData.setMediaSize(value)
|
||||
} else if (widgetId === "focusedWindow") {
|
||||
SettingsData.setFocusedWindowCompactMode(value)
|
||||
} else if (widgetId === "runningApps") {
|
||||
SettingsData.setRunningAppsCompactMode(value)
|
||||
}
|
||||
}
|
||||
onGpuSelectionChanged: (sectionId, widgetIndex, selectedIndex) => {
|
||||
topBarTab.handleGpuSelectionChanged(
|
||||
sectionId, widgetIndex, selectedIndex)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user