(),
{
scrollback: Infinity,
+ minLogHeight: undefined,
showInput: false,
disableInput: false,
disableInputTooltip: undefined,
diff --git a/packages/ui/src/components/base/IntlFormatted.vue b/packages/ui/src/components/base/IntlFormatted.vue
index 7edebb2064c..a6a944bcb27 100644
--- a/packages/ui/src/components/base/IntlFormatted.vue
+++ b/packages/ui/src/components/base/IntlFormatted.vue
@@ -55,7 +55,9 @@ const formattedParts = computed(() => {
for (const slotName of slotNames) {
const normalizedName = slotName.startsWith('~') ? slotName.slice(1) : slotName
- slotHandlers[normalizedName] = (chunks) => {
+ let handlerName = `intlSlot${Object.keys(slotHandlers).length}`
+ while (Object.prototype.hasOwnProperty.call(props.values ?? {}, handlerName)) handlerName += '_'
+ slotHandlers[handlerName] = (chunks) => {
const slot = slots[slotName]
if (slot) {
const nodes = slot({
@@ -69,10 +71,12 @@ const formattedParts = computed(() => {
return markRaw(chunks) as VNode[]
}
- msg = msg.replace(
- new RegExp(`\\{${normalizedName}\\}`, 'g'),
- `<${normalizedName}>${normalizedName}>`,
- )
+ msg = msg
+ .replaceAll(`<${normalizedName}>`, `<${handlerName}>`)
+ .replaceAll(`${normalizedName}>`, `${handlerName}>`)
+ if (!Object.prototype.hasOwnProperty.call(props.values ?? {}, normalizedName)) {
+ msg = msg.replaceAll(`{${normalizedName}}`, `<${handlerName}>${handlerName}>`)
+ }
}
try {
diff --git a/packages/ui/src/components/base/NavTabs.vue b/packages/ui/src/components/base/NavTabs.vue
index 1958a4498b8..b74ecd34e6a 100644
--- a/packages/ui/src/components/base/NavTabs.vue
+++ b/packages/ui/src/components/base/NavTabs.vue
@@ -182,6 +182,8 @@ function computeActiveIndex(): { index: number; isSubpage: boolean } {
}
}
+ let subpageIndex = -1
+
for (let i = filteredLinks.value.length - 1; i >= 0; i--) {
const link = filteredLinks.value[i]
const decodedPath = decodeURIComponent(route.path)
@@ -204,12 +206,12 @@ function computeActiveIndex(): { index: number; isSubpage: boolean } {
(decodedPath.length === decodedHref.length || decodedPath[decodedHref.length] === '/')) ||
link.subpages?.some((subpage) => decodedPath.includes(subpage))
- if (isSubpageMatch) {
- return { index: i, isSubpage: true }
+ if (isSubpageMatch && subpageIndex === -1) {
+ subpageIndex = i
}
}
- return { index: -1, isSubpage: false }
+ return { index: subpageIndex, isSubpage: subpageIndex !== -1 }
}
function getTabElement(index: number): HTMLElement | null {
diff --git a/packages/ui/src/components/base/Toggle.vue b/packages/ui/src/components/base/Toggle.vue
index 4ffa62d33ca..ddc0153102f 100644
--- a/packages/ui/src/components/base/Toggle.vue
+++ b/packages/ui/src/components/base/Toggle.vue
@@ -3,12 +3,12 @@
:id="id"
type="button"
role="switch"
- :aria-checked="modelValue"
+ :aria-checked="indeterminate ? 'mixed' : modelValue"
:disabled="disabled"
class="group inline-flex shrink-0 touch-manipulation items-center rounded-full m-0 p-1 transition-all duration-200 cursor-pointer border border-solid border-surface-5"
:class="[
small ? 'h-5 !w-[40px]' : 'h-6 !w-[48px]',
- modelValue ? 'bg-brand' : 'bg-button-bg',
+ indeterminate || modelValue ? 'bg-brand' : 'bg-button-bg',
disabled ? 'opacity-50 cursor-not-allowed' : '',
]"
@click="toggle"
@@ -16,17 +16,24 @@
@@ -37,6 +44,7 @@ const props = defineProps<{
id?: string
disabled?: boolean
small?: boolean
+ indeterminate?: boolean
}>()
const modelValue = defineModel
()
diff --git a/packages/ui/src/components/base/inputs/Input.vue b/packages/ui/src/components/base/inputs/Input.vue
index ab805a9aa0f..9f1b5d5cf71 100644
--- a/packages/ui/src/components/base/inputs/Input.vue
+++ b/packages/ui/src/components/base/inputs/Input.vue
@@ -28,35 +28,52 @@
-
+
+ {{ hasValue ? model : placeholder || ' ' }}
+
+
+
+
+