diff --git a/core/internal/qmlchecks/greeter_auth_test.go b/core/internal/qmlchecks/greeter_auth_test.go new file mode 100644 index 000000000..98047a9ea --- /dev/null +++ b/core/internal/qmlchecks/greeter_auth_test.go @@ -0,0 +1,25 @@ +package qmlchecks + +import ( + "os" + "strings" + "testing" +) + +func TestGreeterExternalAuthStatusUsesEffectiveFingerprintAvailability(t *testing.T) { + data, err := os.ReadFile("../../../quickshell/Modules/Greetd/GreeterContent.qml") + if err != nil { + t.Fatalf("read greeter QML: %v", err) + } + + content := string(data) + for _, required := range []string{ + "readonly property bool greeterPamHasExternalAuth: greeterPamHasFprint || greeterPamHasU2f", + "if (greeterPamHasFprint && greeterPamHasU2f)", + "if (greeterPamHasFprint)", + } { + if !strings.Contains(content, required) { + t.Fatalf("greeter external-auth status must contain %q", required) + } + } +} diff --git a/core/internal/qmlchecks/lockscreen_input_test.go b/core/internal/qmlchecks/lockscreen_input_test.go index 0e234096e..c82e320cf 100644 --- a/core/internal/qmlchecks/lockscreen_input_test.go +++ b/core/internal/qmlchecks/lockscreen_input_test.go @@ -31,8 +31,8 @@ func TestLockScreenAuthenticationCardOwnsFactorControls(t *testing.T) { } content := string(data) - authCard := strings.Index(content, `title: I18n.tr("Lock Screen Authentication")`) - behaviorCard := strings.Index(content, `title: I18n.tr("Lock Screen behaviour")`) + authCard := strings.Index(content, `title: I18n.tr("Authentication")`) + behaviorCard := strings.Index(content, `title: I18n.tr("Behavior")`) fingerprintToggle := strings.Index(content, `settingKey: "enableFprint"`) u2fToggle := strings.Index(content, `settingKey: "enableU2f"`) u2fSource := strings.Index(content, `settingKey: "lockU2fPamPath"`) diff --git a/quickshell/Common/settings/Processes.qml b/quickshell/Common/settings/Processes.qml index b6f12a9e6..e6acd4a10 100644 --- a/quickshell/Common/settings/Processes.qml +++ b/quickshell/Common/settings/Processes.qml @@ -247,6 +247,10 @@ Singleton { readonly property var _pamProbeCommand: ["sh", "-c", "for module in pam_fprintd.so pam_u2f.so; do found=false; for dir in /usr/lib64/security /usr/lib/security /lib/security /lib/x86_64-linux-gnu/security /usr/lib/x86_64-linux-gnu/security /usr/lib/aarch64-linux-gnu/security /run/current-system/sw/lib/security; do if [ -f \"$dir/$module\" ]; then found=true; break; fi; done; printf '%s:%s\\n' \"$module\" \"$found\"; done"] function detectAuthCapabilities() { + // FileView cannot watch paths that do not exist yet, so reload the U2F PAM + dankshellU2fPamWatcher.reload(); + u2fKeysWatcher.reload(); + if (forcedFprintAvailable === null) { fingerprintProbeFinalized = false; Proc.runCommand("fprint-probe", _fprintProbeCommand, (output, exitCode) => { @@ -600,7 +604,7 @@ Singleton { let details = out; if (err !== "") details = details !== "" ? details + "\n\nstderr:\n" + err : "stderr:\n" + err; - ToastService.showInfo(I18n.tr("Authentication changes applied."), details, "", "auth-sync"); + ToastService.showInfo(I18n.tr("Authentication changes applied"), details, "", "auth-sync"); root.detectAuthCapabilities(); root.finishAuthApply(); return; @@ -723,6 +727,7 @@ Singleton { FileView { id: dankshellU2fPamWatcher path: "/etc/pam.d/dankshell-u2f" + watchChanges: true printErrors: false onLoaded: root.dankshellU2fPamText = text() onLoadFailed: root.dankshellU2fPamText = "" @@ -737,6 +742,7 @@ Singleton { FileView { id: u2fKeysWatcher path: root.u2fKeysPath + watchChanges: true printErrors: false onLoaded: root.u2fKeysText = text() onLoadFailed: root.u2fKeysText = "" diff --git a/quickshell/Modules/Greetd/GreeterContent.qml b/quickshell/Modules/Greetd/GreeterContent.qml index 87973289f..81566fd51 100644 --- a/quickshell/Modules/Greetd/GreeterContent.qml +++ b/quickshell/Modules/Greetd/GreeterContent.qml @@ -73,14 +73,14 @@ Item { readonly property bool greeterPamHasFprint: greeterPamStackHasFprint && (!fprintdProbeComplete || fprintdHasDevice) readonly property bool greeterPamHasU2f: greeterPamStackHasModule("pam_u2f") readonly property bool greeterExternalAuthAvailable: (greeterPamHasFprint && GreetdSettings.greeterEnableFprint) || (greeterPamHasU2f && GreetdSettings.greeterEnableU2f) - readonly property bool greeterPamHasExternalAuth: greeterPamStackHasFprint || greeterPamHasU2f + readonly property bool greeterPamHasExternalAuth: greeterPamHasFprint || greeterPamHasU2f readonly property bool externalAuthInProgress: awaitingExternalAuth || (Greetd.state !== GreetdState.Inactive && passwordSubmitRequested && greeterPamHasExternalAuth && !pendingPasswordResponse) readonly property string externalAuthStatusMessage: { if (!externalAuthInProgress) return ""; - if (greeterPamStackHasFprint && greeterPamHasU2f) + if (greeterPamHasFprint && greeterPamHasU2f) return I18n.tr("Awaiting fingerprint or security key authentication"); - if (greeterPamStackHasFprint) + if (greeterPamHasFprint) return I18n.tr("Awaiting fingerprint authentication"); return I18n.tr("Awaiting security key authentication"); } diff --git a/quickshell/Modules/Lock/Pam.qml b/quickshell/Modules/Lock/Pam.qml index 8938a5d81..84f8f096b 100644 --- a/quickshell/Modules/Lock/Pam.qml +++ b/quickshell/Modules/Lock/Pam.qml @@ -113,6 +113,7 @@ Scope { id: u2fConfigWatcher path: "/etc/pam.d/dankshell-u2f" + watchChanges: true printErrors: false } @@ -488,6 +489,9 @@ Scope { root.resetAuthFlows(); if (!SettingsData.lockPamExternallyManaged && !dankshellConfigWatcher.loaded && !userPamWatcher.loaded) ensureUserPamConfig(); + // FileView cannot watch a path that does not exist yet; re-read so a + // dedicated service created after startup is used on the next lock. + u2fConfigWatcher.reload(); fprint.checkAvail(); u2f.checkAvail(); } diff --git a/quickshell/Modules/Settings/GreeterTab.qml b/quickshell/Modules/Settings/GreeterTab.qml index 85c88b199..397f40834 100644 --- a/quickshell/Modules/Settings/GreeterTab.qml +++ b/quickshell/Modules/Settings/GreeterTab.qml @@ -19,39 +19,39 @@ Item { function greeterFingerprintDescription() { if (SettingsData.greeterPamExternallyManaged) - return "greetd PAM is externally managed"; + return I18n.tr("Managed by the primary PAM source", "factor managed by PAM source status"); if (SettingsData.greeterFingerprintSource === "pam") return I18n.tr("PAM already provides fingerprint auth. Enable this to show it at login.", "greeter fingerprint login setting"); switch (SettingsData.greeterFingerprintReason) { case "ready": - return I18n.tr("Authentication changes apply automatically.", "greeter auth setting description"); + return I18n.tr("Authentication changes apply automatically", "greeter auth setting description"); case "missing_enrollment": return I18n.tr("Fingerprint reader detected, but no prints are enrolled yet. You can enable this now and run Sync later.", "greeter fingerprint login setting"); case "missing_reader": - return I18n.tr("No fingerprint reader detected.", "fingerprint setting status"); + return I18n.tr("No fingerprint reader detected", "fingerprint setting status"); case "missing_pam_support": return I18n.tr("Not available — install fprintd and pam_fprintd, or configure greetd PAM.", "greeter fingerprint login setting"); default: - return I18n.tr("Fingerprint availability could not be confirmed.", "fingerprint setting status"); + return I18n.tr("Fingerprint availability could not be confirmed", "fingerprint setting status"); } } function greeterU2fDescription() { if (SettingsData.greeterPamExternallyManaged) - return "greetd PAM is externally managed"; + return I18n.tr("Managed by the primary PAM source", "factor managed by PAM source status"); if (SettingsData.greeterU2fSource === "pam") return I18n.tr("PAM already provides security-key auth. Enable this to show it at login.", "greeter security key login setting"); switch (SettingsData.greeterU2fReason) { case "ready": - return I18n.tr("Authentication changes apply automatically.", "greeter auth setting description"); + return I18n.tr("Authentication changes apply automatically", "greeter auth setting description"); case "missing_key_registration": return I18n.tr("Security-key support was detected, but no registered key was found yet. You can enable this now and register one later.", "security key setting status"); case "missing_pam_support": return I18n.tr("Not available — install or configure pam_u2f, or configure greetd PAM.", "greeter security key login setting"); default: - return I18n.tr("Security-key availability could not be confirmed.", "security key setting status"); + return I18n.tr("Security-key availability could not be confirmed", "security key setting status"); } } @@ -305,7 +305,7 @@ Item { onExited: exitCode => { root.greeterSyncRunning = false; if (exitCode === 0) { - var launched = root.greeterTerminalFallbackFromPrecheck ? I18n.tr("Terminal opened. Complete sync authentication there; it will close automatically when done.") : I18n.tr("Terminal fallback opened. Complete sync there; it will close automatically when done."); + var launched = root.greeterTerminalFallbackFromPrecheck ? I18n.tr("Terminal opened. Complete authentication there; it will close automatically when done.") : I18n.tr("Terminal fallback opened. Complete authentication there; it will close automatically when done."); root.greeterStatusText = root.greeterStatusText ? root.greeterStatusText + "\n\n" + launched : launched; SettingsData.clearGreeterSyncPending(); return; @@ -396,11 +396,11 @@ Item { SettingsCard { width: parent.width iconName: "info" - title: I18n.tr("Greeter Status") + title: I18n.tr("Status") settingKey: "greeterStatus" StyledText { - text: I18n.tr("Sync applies your theme and settings to the login screen. Other users should run dms greeter sync --profile instead of a full sync. Authentication changes apply automatically.") + text: I18n.tr("Sync applies your theme and settings to the login screen. Shared users should run dms greeter sync --profile instead of a primary user sync.") font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText width: parent.width @@ -470,11 +470,11 @@ Item { SettingsCard { width: parent.width iconName: "fingerprint" - title: I18n.tr("Login Authentication") + title: I18n.tr("Authentication") settingKey: "greeterAuth" StyledText { - text: I18n.tr("Enable fingerprint or security key for DMS Greeter. Authentication changes apply automatically.") + text: I18n.tr("Enable fingerprint or security key for DMS Greeter") font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText width: parent.width @@ -485,8 +485,8 @@ Item { SettingsToggleRow { settingKey: "greeterPamExternallyManaged" tags: ["greeter", "pam", "managed", "external", "greetd", "auth"] - text: "greetd PAM is externally managed" - description: "DMS removes its managed block from /etc/pam.d/greetd and stops writing to it" + text: I18n.tr("Use system PAM authentication", "system PAM policy toggle") + description: I18n.tr("DMS removes its managed block from /etc/pam.d/greetd and stops write services", "greeter system PAM toggle description") checked: SettingsData.greeterPamExternallyManaged onToggled: checked => SettingsData.set("greeterPamExternallyManaged", checked) } @@ -517,7 +517,7 @@ Item { SettingsCard { width: parent.width iconName: "palette" - title: I18n.tr("Greeter Appearance") + title: I18n.tr("Appearance") settingKey: "greeterAppearance" StyledText { @@ -553,12 +553,12 @@ Item { settingKey: "greeterLockDateFormat" tags: ["greeter", "date", "format"] text: I18n.tr("Date Format") - description: I18n.tr("Greeter only — format for the date on the login screen") + description: I18n.tr("Format the date on the login screen") options: root._lockDateFormatPresets.map(p => p.label) currentValue: { var current = (SettingsData.greeterLockDateFormat !== undefined && SettingsData.greeterLockDateFormat !== "") ? SettingsData.greeterLockDateFormat : SettingsData.lockDateFormat || ""; var match = root._lockDateFormatPresets.find(p => p.format === current); - return match ? match.label : (current ? I18n.tr("Custom: ") + current : root._lockDateFormatPresets[0].label); + return match ? match.label : (current ? I18n.tr("Custom") + ": " + current : root._lockDateFormatPresets[0].label); } onValueChanged: value => { var preset = root._lockDateFormatPresets.find(p => p.label === value); @@ -577,7 +577,7 @@ Item { } StyledText { - text: I18n.tr("Use a custom image for the login screen, or leave empty to use your desktop wallpaper.") + text: I18n.tr("Use a custom image for the login screen, or leave empty to use desktop wallpaper") font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText width: parent.width @@ -601,11 +601,11 @@ Item { SettingsCard { width: parent.width iconName: "history" - title: I18n.tr("Greeter Behavior") + title: I18n.tr("Behavior") settingKey: "greeterBehavior" StyledText { - text: I18n.tr("Convenience options for the login screen. Sync to apply.") + text: I18n.tr("Convenience options for the login screen") font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText width: parent.width @@ -649,7 +649,7 @@ Item { settingKey: "greeterDeps" StyledText { - text: I18n.tr("Requires greetd, dms-greeter, and your user in the greeter group (plus fprintd/pam_fprintd for fingerprint, pam_u2f for security keys). Auth changes apply automatically and may open a terminal for sudo.") + text: I18n.tr("Requires greetd, dms-greeter, and your user in the greeter group (plus fprintd/pam_fprintd for fingerprint, pam_u2f for security keys).") font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText width: parent.width @@ -658,7 +658,7 @@ Item { } StyledText { - text: I18n.tr("Installation and PAM setup: see the ") + "DankGreeter docs " + I18n.tr("or run ") + "'dms greeter install'." + text: I18n.tr("Installation and PAM setup are documented in the ") + "DankGreeter docs. " textFormat: Text.RichText font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText diff --git a/quickshell/Modules/Settings/LockScreenTab.qml b/quickshell/Modules/Settings/LockScreenTab.qml index ef319e863..b650e6771 100644 --- a/quickshell/Modules/Settings/LockScreenTab.qml +++ b/quickshell/Modules/Settings/LockScreenTab.qml @@ -96,28 +96,28 @@ Item { function lockFingerprintDescription() { switch (SettingsData.lockFingerprintReason) { case "ready": - return I18n.tr("Use fingerprint authentication for the lock screen.", "lock screen fingerprint setting"); + return I18n.tr("Use fingerprint authentication for the lock screen", "lock screen fingerprint setting"); case "missing_enrollment": return I18n.tr("Fingerprint reader detected, but no prints are enrolled yet. You can enable this now and enroll later.", "lock screen fingerprint setting"); case "missing_reader": - return I18n.tr("No fingerprint reader detected.", "fingerprint setting status"); + return I18n.tr("No fingerprint reader detected", "fingerprint setting status"); case "missing_pam_support": - return I18n.tr("Not available — install fprintd and pam_fprintd.", "lock screen fingerprint setting"); + return I18n.tr("Not available - install fprintd and pam_fprintd", "lock screen fingerprint setting"); default: - return I18n.tr("Fingerprint availability could not be confirmed.", "fingerprint setting status"); + return I18n.tr("Fingerprint availability could not be confirmed", "fingerprint setting status"); } } function lockU2fDescription() { switch (SettingsData.lockU2fReason) { case "ready": - return I18n.tr("Use a security key for lock screen authentication.", "lock screen U2F security key setting"); + return I18n.tr("Use a security key for lock screen authentication", "lock screen U2F security key setting"); case "missing_key_registration": return I18n.tr("Security-key support was detected, but no registered key was found yet. You can enable this now and register one later.", "security key setting status"); case "missing_pam_support": - return I18n.tr("Not available — install or configure pam_u2f.", "lock screen security key setting"); + return I18n.tr("Not available - install or configure pam_u2f", "lock screen security key setting"); default: - return I18n.tr("Security-key availability could not be confirmed.", "security key setting status"); + return I18n.tr("Security-key availability could not be confirmed", "security key setting status"); } } @@ -192,12 +192,12 @@ Item { } catch (e) {} if (!data) { - root.authValidateMessage = "Validation failed — is DMS in PATH?"; + root.authValidateMessage = I18n.tr("Config validation failed"); return; } if (!data.valid) { const errs = Array.isArray(data.errors) ? data.errors : []; - root.authValidateMessage = ["Not applied.", ...errs].join("\n"); + root.authValidateMessage = [I18n.tr("Config validation failed"), ...errs].join("\n"); return; } @@ -207,7 +207,7 @@ Item { const warns = Array.isArray(data.warnings) ? data.warnings : []; root.authValidateOk = true; root.authValidateWarn = warns.length > 0; - root.authValidateMessage = warns.length > 0 ? ["Applied with warnings.", ...warns].join("\n") : "Applied."; + root.authValidateMessage = [I18n.tr("Authentication changes applied"), ...warns].join("\n"); } } @@ -232,12 +232,12 @@ Item { } catch (e) {} if (!data) { - root.u2fValidateMessage = "Validation failed — is DMS in PATH?"; + root.u2fValidateMessage = I18n.tr("Config validation failed"); return; } if (!data.valid) { const errs = Array.isArray(data.errors) ? data.errors : []; - root.u2fValidateMessage = ["Not applied.", ...errs].join("\n"); + root.u2fValidateMessage = [I18n.tr("Config validation failed"), ...errs].join("\n"); return; } @@ -245,7 +245,7 @@ Item { const warns = Array.isArray(data.warnings) ? data.warnings : []; root.u2fValidateOk = true; root.u2fValidateWarn = warns.length > 0; - root.u2fValidateMessage = warns.length > 0 ? ["Applied with warnings.", ...warns].join("\n") : "Applied."; + root.u2fValidateMessage = [I18n.tr("Authentication changes applied"), ...warns].join("\n"); root.refreshAuthDetection(); } } @@ -266,7 +266,7 @@ Item { SettingsCard { width: parent.width iconName: "lock" - title: I18n.tr("Lock Screen layout") + title: I18n.tr("Layout") settingKey: "lockLayout" SettingsToggleRow { @@ -345,7 +345,7 @@ Item { SettingsCard { width: parent.width iconName: "palette" - title: I18n.tr("Lock Screen Appearance") + title: I18n.tr("Appearance") settingKey: "lockAppearance" StyledText { @@ -396,11 +396,11 @@ Item { SettingsCard { width: parent.width iconName: "key" - title: I18n.tr("Lock Screen Authentication") + title: I18n.tr("Authentication") settingKey: "lockAuthSource" StyledText { - text: I18n.tr("Changes apply automatically") + text: I18n.tr("Authentication changes apply automatically") font.pixelSize: Theme.fontSizeSmall color: Theme.surfaceVariantText width: parent.width @@ -410,8 +410,8 @@ Item { SettingsDropdownRow { settingKey: "lockPamPath" tags: ["lock", "screen", "pam", "authentication", "source", "service"] - text: "Authentication Source" - description: SettingsData.lockPamPath !== "" ? SettingsData.lockPamPath : "Which PAM service the lock screen uses to authenticate" + text: I18n.tr("Authentication Source", "lock screen PAM source setting") + description: SettingsData.lockPamPath !== "" ? SettingsData.lockPamPath : I18n.tr("Which PAM service the lock screen uses to authenticate", "lock screen PAM source setting") options: root.authOptions currentValue: root.authCurrentValue onValueChanged: value => { @@ -472,21 +472,10 @@ Item { } } - StyledText { - visible: !SettingsData.lockPamExternallyManaged && (root.primaryPamHasFprint || root.primaryPamHasU2f) - text: I18n.tr("Selected PAM source already manages the detected factors.") - font.pixelSize: Theme.fontSizeSmall - color: Theme.warning - width: parent.width - wrapMode: Text.Wrap - topPadding: Theme.spacingS - } - SettingsToggleRow { settingKey: "lockPamExternallyManaged" tags: ["lock", "screen", "pam", "managed", "external", "authentication", "policy"] - text: I18n.tr("Use system PAM authentication") - description: SettingsData.lockPamExternallyManaged ? I18n.tr("System PAM sets the authentication policy.") : I18n.tr("DMS manages the factors below.") + text: I18n.tr("Use system PAM authentication", "system PAM policy toggle") checked: SettingsData.lockPamExternallyManaged onToggled: checked => SettingsData.set("lockPamExternallyManaged", checked) } @@ -495,7 +484,7 @@ Item { settingKey: "enableFprint" tags: ["lock", "screen", "fingerprint", "authentication", "biometric", "fprint"] text: I18n.tr("Enable fingerprint authentication") - description: root.lockFprintControlledByPrimary ? I18n.tr("Managed by the primary PAM source.") : root.lockFingerprintDescription() + description: root.lockFprintControlledByPrimary ? I18n.tr("Managed by the primary PAM source", "factor managed by PAM source status") : root.lockFingerprintDescription() descriptionColor: root.lockFprintControlledByPrimary || SettingsData.lockFingerprintReason === "ready" ? Theme.surfaceVariantText : Theme.warning checked: SettingsData.enableFprint || root.primaryPamHasFprint enabled: root.lockFprintToggleAvailable && !root.lockFprintControlledByPrimary @@ -506,7 +495,7 @@ Item { settingKey: "enableU2f" tags: ["lock", "screen", "u2f", "yubikey", "security", "key", "fido", "authentication", "hardware"] text: I18n.tr("Enable security key authentication", "Enable FIDO2/U2F hardware security key for lock screen") - description: root.lockU2fControlledByPrimary ? I18n.tr("Managed by the primary PAM source.") : root.lockU2fDescription() + description: root.lockU2fControlledByPrimary ? I18n.tr("Managed by the primary PAM source", "factor managed by PAM source status") : root.lockU2fDescription() descriptionColor: root.lockU2fControlledByPrimary || SettingsData.lockU2fReason === "ready" ? Theme.surfaceVariantText : Theme.warning checked: SettingsData.enableU2f || root.primaryPamHasU2f enabled: root.lockU2fToggleAvailable && !root.lockU2fControlledByPrimary @@ -517,7 +506,7 @@ Item { settingKey: "u2fMode" tags: ["lock", "screen", "u2f", "yubikey", "security", "key", "mode", "factor", "second"] text: I18n.tr("Security key mode", "lock screen U2F security key mode setting") - description: I18n.tr("Alternative uses the passkey button. Second factor follows password or fingerprint.", "lock screen U2F security key mode setting") + description: I18n.tr("'Alternative' lets the key unlock on its own. 'Second factor' requires password or fingerprint first, then the key.", "lock screen U2F security key mode setting") visible: SettingsData.enableU2f && !root.lockU2fControlledByPrimary options: [I18n.tr("Alternative (OR)", "U2F mode option: key works as standalone unlock method"), I18n.tr("Second Factor (AND)", "U2F mode option: key required after password or fingerprint")] currentValue: SettingsData.u2fMode === "and" ? I18n.tr("Second Factor (AND)", "U2F mode option: key required after password or fingerprint") : I18n.tr("Alternative (OR)", "U2F mode option: key works as standalone unlock method") @@ -532,8 +521,8 @@ Item { SettingsDropdownRow { settingKey: "lockU2fPamPath" tags: ["lock", "screen", "pam", "u2f", "security", "key", "source", "service"] - text: I18n.tr("Security Key PAM Source") - description: SettingsData.lockU2fPamPath !== "" ? SettingsData.lockU2fPamPath : I18n.tr("Auto uses an installed or bundled key-only service.") + text: I18n.tr("Security Key PAM Source", "lock screen dedicated U2F PAM source setting") + description: SettingsData.lockU2fPamPath !== "" ? SettingsData.lockU2fPamPath : I18n.tr("Auto uses an installed or bundled key-only service.", "lock screen dedicated U2F PAM source setting") visible: !root.lockU2fControlledByPrimary options: [root.authAutoLabel, root.authCustomLabel] currentValue: root.u2fAuthCurrentValue @@ -592,7 +581,7 @@ Item { SettingsCard { width: parent.width iconName: "lock" - title: I18n.tr("Lock Screen behaviour") + title: I18n.tr("Behavior") settingKey: "lockBehavior" StyledText { @@ -731,7 +720,7 @@ Item { SettingsCard { width: parent.width iconName: "monitor" - title: I18n.tr("Lock Screen Display") + title: I18n.tr("Display Assignment") settingKey: "lockDisplay" StyledText { diff --git a/quickshell/translations/settings_search_index.json b/quickshell/translations/settings_search_index.json index ba857ce69..4d1d7b110 100644 --- a/quickshell/translations/settings_search_index.json +++ b/quickshell/translations/settings_search_index.json @@ -4655,21 +4655,70 @@ ] }, { - "section": "lockPamPath", - "label": "Authentication Source", + "section": "lockAppearance", + "label": "Appearance", "tabIndex": 11, "category": "Lock Screen", "keywords": [ + "appearance", + "clock", + "date", + "font", + "lock", + "lockscreen", + "login", + "password", + "screen", + "security", + "time", + "typography", + "watch" + ], + "icon": "palette", + "description": "Font used for the clock and date on the lock screen" + }, + { + "section": "lockAuthSource", + "label": "Authentication", + "tabIndex": 11, + "category": "Lock Screen", + "keywords": [ + "authenticate", "authentication", "lock", + "lockscreen", "login", "pam", "password", "screen", "security", "service", - "source" - ] + "source", + "uses" + ], + "icon": "key", + "description": "Which PAM service the lock screen uses to authenticate" + }, + { + "section": "lockPamPath", + "label": "Authentication Source", + "tabIndex": 11, + "category": "Lock Screen", + "keywords": [ + "authenticate", + "authentication", + "lock", + "lockscreen", + "login", + "pam", + "password", + "screen", + "security", + "service", + "source", + "uses" + ], + "description": "Which PAM service the lock screen uses to authenticate" }, { "section": "lockScreenVideoCycling", @@ -4696,6 +4745,48 @@ ], "description": "Pick a different random video each time from the same folder" }, + { + "section": "lockBehavior", + "label": "Behavior", + "tabIndex": 11, + "category": "Lock Screen", + "keywords": [ + "behavior", + "bind", + "dbus", + "disable", + "external", + "integration", + "lock", + "lockscreen", + "login", + "loginctl", + "password", + "screen", + "security", + "signals" + ], + "icon": "lock", + "description": "Bind lock screen to dbus signals from loginctl. Disable if using an external lock screen" + }, + { + "section": "lockDisplay", + "label": "Display Assignment", + "tabIndex": 11, + "category": "Lock Screen", + "keywords": [ + "assignment", + "display", + "lock", + "login", + "monitor", + "output", + "password", + "screen", + "security" + ], + "icon": "monitor" + }, { "section": "lockScreenVideoEnabled", "label": "Enable Video Screensaver", @@ -4737,7 +4828,7 @@ "security", "source" ], - "description": "Managed by the primary PAM source." + "description": "Managed by the primary PAM source" }, { "section": "loginctlLockIntegration", @@ -4784,7 +4875,32 @@ "u2f", "yubikey" ], - "description": "Managed by the primary PAM source." + "description": "Managed by the primary PAM source" + }, + { + "section": "lockLayout", + "label": "Layout", + "tabIndex": 11, + "category": "Lock Screen", + "keywords": [ + "actions", + "appear", + "field", + "hidden", + "layout", + "lock", + "login", + "password", + "power", + "pressed", + "reboot", + "screen", + "security", + "shutdown", + "soon" + ], + "icon": "lock", + "description": "If the field is hidden, it will appear as soon as a key is pressed." }, { "section": "_tab_11", @@ -4801,116 +4917,6 @@ ], "icon": "lock" }, - { - "section": "lockAppearance", - "label": "Lock Screen Appearance", - "tabIndex": 11, - "category": "Lock Screen", - "keywords": [ - "appearance", - "clock", - "date", - "font", - "lock", - "lockscreen", - "login", - "password", - "screen", - "security", - "time", - "typography", - "watch" - ], - "icon": "palette", - "description": "Font used for the clock and date on the lock screen" - }, - { - "section": "lockAuthSource", - "label": "Lock Screen Authentication", - "tabIndex": 11, - "category": "Lock Screen", - "keywords": [ - "authentication", - "lock", - "lockscreen", - "login", - "pam", - "password", - "screen", - "security", - "service", - "source" - ], - "icon": "key" - }, - { - "section": "lockDisplay", - "label": "Lock Screen Display", - "tabIndex": 11, - "category": "Lock Screen", - "keywords": [ - "display", - "lock", - "lockscreen", - "login", - "monitor", - "output", - "password", - "screen", - "security" - ], - "icon": "monitor" - }, - { - "section": "lockBehavior", - "label": "Lock Screen behaviour", - "tabIndex": 11, - "category": "Lock Screen", - "keywords": [ - "behaviour", - "bind", - "dbus", - "disable", - "external", - "integration", - "lock", - "lockscreen", - "login", - "loginctl", - "password", - "screen", - "security", - "signals" - ], - "icon": "lock", - "description": "Bind lock screen to dbus signals from loginctl. Disable if using an external lock screen" - }, - { - "section": "lockLayout", - "label": "Lock Screen layout", - "tabIndex": 11, - "category": "Lock Screen", - "keywords": [ - "actions", - "appear", - "field", - "hidden", - "layout", - "lock", - "lockscreen", - "login", - "password", - "power", - "pressed", - "reboot", - "screen", - "security", - "shutdown", - "soon" - ], - "icon": "lock", - "description": "If the field is hidden, it will appear as soon as a key is pressed." - }, { "section": "lockAtStartup", "label": "Lock at startup", @@ -5063,25 +5069,18 @@ "tabIndex": 11, "category": "Lock Screen", "keywords": [ - "alternative", - "button", "factor", - "fingerprint", - "follows", "key", "lock", "login", "mode", - "passkey", "password", "screen", "second", "security", "u2f", - "uses", "yubikey" - ], - "description": "Alternative uses the passkey button. Second factor follows password or fingerprint." + ] }, { "section": "lockScreenShowMediaPlayer", @@ -5234,10 +5233,8 @@ "policy", "screen", "security", - "sets", "system" - ], - "description": "System PAM sets the authentication policy." + ] }, { "section": "videoScreensaver", @@ -7909,6 +7906,48 @@ ], "description": "Change the locale used for date and time formatting, independent of the interface language." }, + { + "section": "greeterAppearance", + "label": "Appearance", + "tabIndex": 31, + "category": "Greeter", + "keywords": [ + "appearance", + "display manager", + "font", + "greetd", + "greeter", + "login", + "screen", + "typography" + ], + "icon": "palette", + "description": "Font used on the login screen" + }, + { + "section": "greeterAuth", + "label": "Authentication", + "tabIndex": 31, + "category": "Greeter", + "keywords": [ + "auth", + "authentication", + "block", + "display manager", + "external", + "greetd", + "greeter", + "login", + "managed", + "pam", + "removes", + "services", + "stops", + "write" + ], + "icon": "fingerprint", + "description": "DMS removes its managed block from /etc/pam.d/greetd and stops write services" + }, { "section": "greeterAutoLogin", "label": "Auto-login on startup", @@ -7942,6 +7981,25 @@ ], "description": "Skip the greeter password after boot until you sign out. Lock screen unlock is unchanged. Takes effect on the next reboot after sync." }, + { + "section": "greeterBehavior", + "label": "Behavior", + "tabIndex": 31, + "category": "Greeter", + "keywords": [ + "behavior", + "display manager", + "greetd", + "greeter", + "last", + "login", + "remember", + "select", + "session" + ], + "icon": "history", + "description": "Pre-select the last used session on the greeter" + }, { "section": "greeterLockDateFormat", "label": "Date Format", @@ -7956,7 +8014,7 @@ "login", "screen" ], - "description": "Greeter only — format for the date on the login screen" + "description": "Format the date on the login screen" }, { "section": "greeterDeps", @@ -8019,57 +8077,6 @@ ], "icon": "login" }, - { - "section": "greeterAppearance", - "label": "Greeter Appearance", - "tabIndex": 31, - "category": "Greeter", - "keywords": [ - "appearance", - "display manager", - "font", - "greetd", - "greeter", - "login", - "screen", - "typography" - ], - "icon": "palette", - "description": "Font used on the login screen" - }, - { - "section": "greeterBehavior", - "label": "Greeter Behavior", - "tabIndex": 31, - "category": "Greeter", - "keywords": [ - "behavior", - "display manager", - "greetd", - "greeter", - "last", - "login", - "remember", - "select", - "session" - ], - "icon": "history", - "description": "Pre-select the last used session on the greeter" - }, - { - "section": "greeterStatus", - "label": "Greeter Status", - "tabIndex": 31, - "category": "Greeter", - "keywords": [ - "display manager", - "greetd", - "greeter", - "login", - "status" - ], - "icon": "info" - }, { "section": "greeterFontFamily", "label": "Greeter font", @@ -8086,29 +8093,6 @@ ], "description": "Font used on the login screen" }, - { - "section": "greeterAuth", - "label": "Login Authentication", - "tabIndex": 31, - "category": "Greeter", - "keywords": [ - "auth", - "authentication", - "block", - "display manager", - "external", - "greetd", - "greeter", - "login", - "managed", - "pam", - "removes", - "stops", - "writing" - ], - "icon": "fingerprint", - "description": "DMS removes its managed block from /etc/pam.d/greetd and stops writing to it" - }, { "section": "greeterRememberLastSession", "label": "Remember last session", @@ -8145,27 +8129,43 @@ ], "description": "Pre-fill the last successful username on the greeter" }, + { + "section": "greeterStatus", + "label": "Status", + "tabIndex": 31, + "category": "Greeter", + "keywords": [ + "display manager", + "greetd", + "greeter", + "login", + "status" + ], + "icon": "info" + }, { "section": "greeterPamExternallyManaged", - "label": "greetd PAM is externally managed", + "label": "Use system PAM authentication", "tabIndex": 31, "category": "Greeter", "keywords": [ "auth", + "authentication", "block", "display manager", "external", - "externally", "greetd", "greeter", "login", "managed", "pam", "removes", + "services", "stops", - "writing" + "system", + "write" ], - "description": "DMS removes its managed block from /etc/pam.d/greetd and stops writing to it" + "description": "DMS removes its managed block from /etc/pam.d/greetd and stops write services" }, { "section": "muxType",