biome format --write
This commit is contained in:
parent
8372348148
commit
9262e803ec
415 changed files with 54076 additions and 17419 deletions
|
|
@ -11,34 +11,36 @@ export default {
|
|||
acceptTypes: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: 'image/*'
|
||||
}
|
||||
default: 'image/*',
|
||||
},
|
||||
},
|
||||
components: {
|
||||
...Setting.components,
|
||||
MediaUpload,
|
||||
Attachment
|
||||
Attachment,
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
attachment () {
|
||||
attachment() {
|
||||
const path = this.realDraftMode ? this.draft : this.state
|
||||
// The "server" part is primarily for local dev, but could be useful for alt-domain or multiuser usage.
|
||||
const url = path.includes('://') ? path : this.$store.state.instance.server + path
|
||||
const url = path.includes('://')
|
||||
? path
|
||||
: this.$store.state.instance.server + path
|
||||
return {
|
||||
mimetype: fileTypeExt(url),
|
||||
url
|
||||
url,
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
setMediaFile (fileInfo) {
|
||||
setMediaFile(fileInfo) {
|
||||
if (this.realDraftMode) {
|
||||
this.draft = fileInfo.url
|
||||
} else {
|
||||
this.configSink(this.path, fileInfo.url)
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,27 +5,27 @@ export default {
|
|||
...Setting,
|
||||
props: {
|
||||
...Setting.props,
|
||||
indeterminateState: [String, Object]
|
||||
indeterminateState: [String, Object],
|
||||
},
|
||||
components: {
|
||||
...Setting.components,
|
||||
Checkbox
|
||||
Checkbox,
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
isIndeterminate () {
|
||||
isIndeterminate() {
|
||||
return this.visibleState === this.indeterminateState
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue (e) {
|
||||
getValue(e) {
|
||||
// Basic tri-state toggle implementation
|
||||
if (!!this.indeterminateState && !e && this.visibleState === true) {
|
||||
// If we have indeterminate state, switching from true to false first goes through indeterminate
|
||||
return this.indeterminateState
|
||||
}
|
||||
return e
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,50 +5,50 @@ export default {
|
|||
...Setting,
|
||||
components: {
|
||||
...Setting.components,
|
||||
Select
|
||||
Select,
|
||||
},
|
||||
props: {
|
||||
...Setting.props,
|
||||
overrideOptions: {
|
||||
type: Boolean,
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
options: {
|
||||
type: Array,
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
optionLabelMap: {
|
||||
type: Object,
|
||||
required: false,
|
||||
default: {}
|
||||
}
|
||||
default: {},
|
||||
},
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
realOptions () {
|
||||
realOptions() {
|
||||
if (this.overrideOptions) {
|
||||
return this.options
|
||||
}
|
||||
if (this.realSource === 'admin') {
|
||||
if (
|
||||
!this.backendDescriptionSuggestions?.length ||
|
||||
this.backendDescriptionSuggestions?.length === 0
|
||||
this.backendDescriptionSuggestions?.length === 0
|
||||
) {
|
||||
return this.options
|
||||
}
|
||||
return this.backendDescriptionSuggestions.map(x => ({
|
||||
return this.backendDescriptionSuggestions.map((x) => ({
|
||||
key: x,
|
||||
value: x,
|
||||
label: this.optionLabelMap[x] || x
|
||||
label: this.optionLabelMap[x] || x,
|
||||
}))
|
||||
}
|
||||
return this.options
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue (e) {
|
||||
getValue(e) {
|
||||
return e
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,12 +5,12 @@ export default {
|
|||
...Setting,
|
||||
components: {
|
||||
...Setting.components,
|
||||
ColorInput
|
||||
ColorInput,
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue (e) {
|
||||
getValue(e) {
|
||||
return e
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -61,13 +61,11 @@ import Popover from 'src/components/popover/popover.vue'
|
|||
import { library } from '@fortawesome/fontawesome-svg-core'
|
||||
import { faWrench } from '@fortawesome/free-solid-svg-icons'
|
||||
|
||||
library.add(
|
||||
faWrench
|
||||
)
|
||||
library.add(faWrench)
|
||||
|
||||
export default {
|
||||
components: { Popover },
|
||||
props: ['changed']
|
||||
props: ['changed'],
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -160,53 +160,53 @@ export default {
|
|||
props: {
|
||||
placement: {
|
||||
type: String,
|
||||
required: true
|
||||
required: true,
|
||||
},
|
||||
|
||||
newUpload: Boolean,
|
||||
|
||||
title: {
|
||||
type: String,
|
||||
required: true
|
||||
required: true,
|
||||
},
|
||||
packName: {
|
||||
type: String,
|
||||
required: true
|
||||
required: true,
|
||||
},
|
||||
shortcode: {
|
||||
type: String,
|
||||
// Only exists when this is not a new upload
|
||||
default: ''
|
||||
default: '',
|
||||
},
|
||||
file: {
|
||||
type: String,
|
||||
// Only exists when this is not a new upload
|
||||
default: ''
|
||||
default: '',
|
||||
},
|
||||
|
||||
// Only exists for emojis from remote packs
|
||||
remote: {
|
||||
type: Object,
|
||||
default: undefined
|
||||
default: undefined,
|
||||
},
|
||||
knownLocalPacks: {
|
||||
type: Object,
|
||||
default: undefined
|
||||
}
|
||||
default: undefined,
|
||||
},
|
||||
},
|
||||
emits: ['updatePackFiles', 'displayError'],
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
uploadFile: [],
|
||||
uploadURL: '',
|
||||
editedShortcode: this.shortcode,
|
||||
editedFile: this.file,
|
||||
deleteModalVisible: false,
|
||||
copyToPack: ''
|
||||
copyToPack: '',
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
emojiPreview () {
|
||||
emojiPreview() {
|
||||
if (this.newUpload && this.uploadFile.length > 0) {
|
||||
return URL.createObjectURL(this.uploadFile[0])
|
||||
} else if (this.newUpload && this.uploadURL !== '') {
|
||||
|
|
@ -217,73 +217,92 @@ export default {
|
|||
|
||||
return null
|
||||
},
|
||||
isEdited () {
|
||||
return !this.newUpload && (this.editedShortcode !== this.shortcode || this.editedFile !== this.file)
|
||||
isEdited() {
|
||||
return (
|
||||
!this.newUpload &&
|
||||
(this.editedShortcode !== this.shortcode ||
|
||||
this.editedFile !== this.file)
|
||||
)
|
||||
},
|
||||
saveButtonDisabled() {
|
||||
if (this.remote === undefined)
|
||||
return this.newUpload ? (this.uploadURL === "" && this.uploadFile.length == 0) : !this.isEdited
|
||||
else
|
||||
return this.copyToPack === ""
|
||||
}
|
||||
return this.newUpload
|
||||
? this.uploadURL === '' && this.uploadFile.length == 0
|
||||
: !this.isEdited
|
||||
else return this.copyToPack === ''
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
saveEditedEmoji () {
|
||||
saveEditedEmoji() {
|
||||
if (!this.isEdited) return
|
||||
|
||||
this.$store.state.api.backendInteractor.updateEmojiFile(
|
||||
{ packName: this.packName, shortcode: this.shortcode, newShortcode: this.editedShortcode, newFilename: this.editedFile, force: false }
|
||||
).then(resp => {
|
||||
if (resp.error !== undefined) {
|
||||
this.$emit('displayError', resp.error)
|
||||
return Promise.reject(resp.error)
|
||||
}
|
||||
this.$store.state.api.backendInteractor
|
||||
.updateEmojiFile({
|
||||
packName: this.packName,
|
||||
shortcode: this.shortcode,
|
||||
newShortcode: this.editedShortcode,
|
||||
newFilename: this.editedFile,
|
||||
force: false,
|
||||
})
|
||||
.then((resp) => {
|
||||
if (resp.error !== undefined) {
|
||||
this.$emit('displayError', resp.error)
|
||||
return Promise.reject(resp.error)
|
||||
}
|
||||
|
||||
return resp.json()
|
||||
}).then(resp => this.$emit('updatePackFiles', resp))
|
||||
return resp.json()
|
||||
})
|
||||
.then((resp) => this.$emit('updatePackFiles', resp))
|
||||
},
|
||||
uploadEmoji () {
|
||||
uploadEmoji() {
|
||||
let packName = this.remote === undefined ? this.packName : this.copyToPack
|
||||
this.$store.state.api.backendInteractor.addNewEmojiFile({
|
||||
packName: packName,
|
||||
file: this.remote === undefined
|
||||
? (this.uploadURL !== "" ? this.uploadURL : this.uploadFile[0])
|
||||
: this.emojiAddr(this.file),
|
||||
shortcode: this.editedShortcode,
|
||||
filename: this.editedFile
|
||||
}).then(resp => resp.json()).then(resp => {
|
||||
if (resp.error !== undefined) {
|
||||
this.$emit('displayError', resp.error)
|
||||
return
|
||||
}
|
||||
this.$store.state.api.backendInteractor
|
||||
.addNewEmojiFile({
|
||||
packName: packName,
|
||||
file:
|
||||
this.remote === undefined
|
||||
? this.uploadURL !== ''
|
||||
? this.uploadURL
|
||||
: this.uploadFile[0]
|
||||
: this.emojiAddr(this.file),
|
||||
shortcode: this.editedShortcode,
|
||||
filename: this.editedFile,
|
||||
})
|
||||
.then((resp) => resp.json())
|
||||
.then((resp) => {
|
||||
if (resp.error !== undefined) {
|
||||
this.$emit('displayError', resp.error)
|
||||
return
|
||||
}
|
||||
|
||||
this.$emit('updatePackFiles', resp, packName)
|
||||
this.$refs.emojiPopover.hidePopover()
|
||||
this.$emit('updatePackFiles', resp, packName)
|
||||
this.$refs.emojiPopover.hidePopover()
|
||||
|
||||
this.editedFile = ''
|
||||
this.editedShortcode = ''
|
||||
this.uploadFile = []
|
||||
})
|
||||
this.editedFile = ''
|
||||
this.editedShortcode = ''
|
||||
this.uploadFile = []
|
||||
})
|
||||
},
|
||||
revertEmoji () {
|
||||
revertEmoji() {
|
||||
this.editedFile = this.file
|
||||
this.editedShortcode = this.shortcode
|
||||
},
|
||||
deleteEmoji () {
|
||||
deleteEmoji() {
|
||||
this.deleteModalVisible = false
|
||||
|
||||
this.$store.state.api.backendInteractor.deleteEmojiFile(
|
||||
{ packName: this.packName, shortcode: this.shortcode }
|
||||
).then(resp => resp.json()).then(resp => {
|
||||
if (resp.error !== undefined) {
|
||||
this.$emit('displayError', resp.error)
|
||||
return
|
||||
}
|
||||
this.$store.state.api.backendInteractor
|
||||
.deleteEmojiFile({ packName: this.packName, shortcode: this.shortcode })
|
||||
.then((resp) => resp.json())
|
||||
.then((resp) => {
|
||||
if (resp.error !== undefined) {
|
||||
this.$emit('displayError', resp.error)
|
||||
return
|
||||
}
|
||||
|
||||
this.$emit('updatePackFiles', resp, this.packName)
|
||||
})
|
||||
}
|
||||
}
|
||||
this.$emit('updatePackFiles', resp, this.packName)
|
||||
})
|
||||
},
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@
|
|||
import NumberSetting from './number_setting.vue'
|
||||
export default {
|
||||
components: {
|
||||
NumberSetting
|
||||
}
|
||||
NumberSetting,
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
|
|
|||
|
|
@ -22,12 +22,10 @@ import Popover from 'src/components/popover/popover.vue'
|
|||
import { library } from '@fortawesome/fontawesome-svg-core'
|
||||
import { faCircleQuestion } from '@fortawesome/free-solid-svg-icons'
|
||||
|
||||
library.add(
|
||||
faCircleQuestion
|
||||
)
|
||||
library.add(faCircleQuestion)
|
||||
|
||||
export default {
|
||||
components: { Popover }
|
||||
components: { Popover },
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@
|
|||
import NumberSetting from './number_setting.vue'
|
||||
export default {
|
||||
components: {
|
||||
NumberSetting
|
||||
}
|
||||
NumberSetting,
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
|
|
|||
|
|
@ -3,43 +3,43 @@ import Setting from './setting.js'
|
|||
|
||||
export default {
|
||||
...Setting,
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
newValue: '',
|
||||
}
|
||||
},
|
||||
components: {
|
||||
...Setting.components,
|
||||
Checkbox
|
||||
Checkbox,
|
||||
},
|
||||
props: {
|
||||
...Setting.props,
|
||||
ignoreSuggestions: {
|
||||
required: false,
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
overrideAvailableOptions: {
|
||||
required: false,
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
options: {
|
||||
required: false,
|
||||
type: Set
|
||||
type: Set,
|
||||
},
|
||||
allowNew: {
|
||||
required: false,
|
||||
type: Boolean,
|
||||
default: true
|
||||
default: true,
|
||||
},
|
||||
forceNew: {
|
||||
required: false,
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
default: false,
|
||||
},
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
showNew () {
|
||||
showNew() {
|
||||
if (this.forceNew) return true
|
||||
if (!this.allowNew) return false
|
||||
|
||||
|
|
@ -52,10 +52,10 @@ export default {
|
|||
return true
|
||||
}
|
||||
},
|
||||
valueSet () {
|
||||
valueSet() {
|
||||
return new Set(this.visibleState)
|
||||
},
|
||||
suggestionsSet () {
|
||||
suggestionsSet() {
|
||||
const suggestions = this.backendDescriptionSuggestions
|
||||
if (suggestions) {
|
||||
return new Set(suggestions)
|
||||
|
|
@ -63,14 +63,14 @@ export default {
|
|||
return new Set()
|
||||
}
|
||||
},
|
||||
extraEntries () {
|
||||
extraEntries() {
|
||||
if (this.ignoreSuggestions) return [...this.valueSet.values()]
|
||||
if (!this.suggestionsSet) return []
|
||||
return [...this.valueSet.values()].filter((x) => {
|
||||
return !this.builtinEntriesValueSet.has(x)
|
||||
})
|
||||
},
|
||||
builtinEntries () {
|
||||
builtinEntries() {
|
||||
if (this.ignoreSuggestions) return []
|
||||
if (this.overrideAvailableOptions) {
|
||||
return [...this.options]
|
||||
|
|
@ -80,19 +80,19 @@ export default {
|
|||
const builtins = [...this.suggestionsSet.values()]
|
||||
return builtins.map((option) => ({
|
||||
label: option,
|
||||
value: option
|
||||
value: option,
|
||||
}))
|
||||
},
|
||||
builtinEntriesValueSet () {
|
||||
return new Set(this.builtinEntries.map(x => x.value))
|
||||
}
|
||||
builtinEntriesValueSet() {
|
||||
return new Set(this.builtinEntries.map((x) => x.value))
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
optionPresent (option) {
|
||||
optionPresent(option) {
|
||||
return this.valueSet.has(option)
|
||||
},
|
||||
getValue ({ event, value, index, eventType }) {
|
||||
getValue({ event, value, index, eventType }) {
|
||||
switch (eventType) {
|
||||
case 'toggle': {
|
||||
this.newValue = ''
|
||||
|
|
@ -128,6 +128,6 @@ export default {
|
|||
return [...pre, string, ...post]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2,14 +2,14 @@ import ListSetting from './list_setting.js'
|
|||
|
||||
export default {
|
||||
...ListSetting,
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
newValue: ['','']
|
||||
newValue: ['', ''],
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
...ListSetting.methods,
|
||||
getValue ({ event, index, eventType, tuple }) {
|
||||
getValue({ event, index, eventType, tuple }) {
|
||||
switch (eventType) {
|
||||
case 'add': {
|
||||
if (!this.newValue[0] || !this.newValue[1]) return this.visibleState
|
||||
|
|
@ -39,6 +39,6 @@ export default {
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -7,28 +7,31 @@ export default {
|
|||
allowNew: {
|
||||
required: false,
|
||||
type: Boolean,
|
||||
default: true
|
||||
}
|
||||
default: true,
|
||||
},
|
||||
},
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
newValue: ['',''] // avoiding extra complexity by just using an array instead of an object
|
||||
newValue: ['', ''], // avoiding extra complexity by just using an array instead of an object
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
// state that we'll show in the UI, i.e. transforming map into list
|
||||
displayState () {
|
||||
displayState() {
|
||||
return Object.entries(this.visibleState)
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue ({ event, key, eventType, isKey }) {
|
||||
getValue({ event, key, eventType, isKey }) {
|
||||
switch (eventType) {
|
||||
case 'add': {
|
||||
if (key === '') return this.visibleState
|
||||
const res = {...this.visibleState, ...Object.fromEntries([this.newValue])}
|
||||
const res = {
|
||||
...this.visibleState,
|
||||
...Object.fromEntries([this.newValue]),
|
||||
}
|
||||
this.newValue = ['', '']
|
||||
return res
|
||||
}
|
||||
|
|
@ -36,35 +39,35 @@ export default {
|
|||
case 'remove': {
|
||||
// initial state for this type is empty array
|
||||
if (Array.isArray(this.visibleState)) return this.visibleState
|
||||
const newEntries = Object.entries(this.visibleState).filter(([k]) => k !== key)
|
||||
const newEntries = Object.entries(this.visibleState).filter(
|
||||
([k]) => k !== key,
|
||||
)
|
||||
|
||||
if (newEntries.length === 0 ) return []
|
||||
if (newEntries.length === 0) return []
|
||||
return Object.fromEntries(newEntries)
|
||||
}
|
||||
|
||||
case 'edit': {
|
||||
const string = event.target.value
|
||||
const newEntries = Object
|
||||
.entries(this.visibleState)
|
||||
.map(([k, v]) => {
|
||||
if (isKey) {
|
||||
if (k === key) {
|
||||
return [string, v]
|
||||
} else {
|
||||
return [k, v]
|
||||
}
|
||||
const newEntries = Object.entries(this.visibleState).map(([k, v]) => {
|
||||
if (isKey) {
|
||||
if (k === key) {
|
||||
return [string, v]
|
||||
} else {
|
||||
if (k === key) {
|
||||
return [k, string]
|
||||
} else {
|
||||
return [k, v]
|
||||
}
|
||||
return [k, v]
|
||||
}
|
||||
})
|
||||
} else {
|
||||
if (k === key) {
|
||||
return [k, string]
|
||||
} else {
|
||||
return [k, v]
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
return Object.fromEntries(newEntries)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -27,9 +27,7 @@ import Popover from 'src/components/popover/popover.vue'
|
|||
import { library } from '@fortawesome/fontawesome-svg-core'
|
||||
import { faWrench } from '@fortawesome/free-solid-svg-icons'
|
||||
|
||||
library.add(
|
||||
faWrench
|
||||
)
|
||||
library.add(faWrench)
|
||||
|
||||
export default {
|
||||
components: { Popover },
|
||||
|
|
@ -37,9 +35,9 @@ export default {
|
|||
changed: Boolean,
|
||||
messageKey: {
|
||||
type: String,
|
||||
default: 'settings.setting_changed'
|
||||
}
|
||||
}
|
||||
default: 'settings.setting_changed',
|
||||
},
|
||||
},
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -7,33 +7,33 @@ export default {
|
|||
min: {
|
||||
type: Number,
|
||||
required: false,
|
||||
default: 1
|
||||
default: 1,
|
||||
},
|
||||
max: {
|
||||
type: Number,
|
||||
required: false,
|
||||
default: 1
|
||||
default: 1,
|
||||
},
|
||||
step: {
|
||||
type: Number,
|
||||
required: false,
|
||||
default: 1
|
||||
default: 1,
|
||||
},
|
||||
truncate: {
|
||||
type: Number,
|
||||
required: false,
|
||||
default: 1
|
||||
}
|
||||
default: 1,
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue (e) {
|
||||
getValue(e) {
|
||||
if (!this.truncate === 1) {
|
||||
return parseInt(e.target.value)
|
||||
} else if (this.truncate > 1) {
|
||||
return Math.trunc(e.target.value / this.truncate) * this.truncate
|
||||
}
|
||||
return parseFloat(e.target.value)
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -27,13 +27,11 @@ import Popover from 'src/components/popover/popover.vue'
|
|||
import { library } from '@fortawesome/fontawesome-svg-core'
|
||||
import { faServer } from '@fortawesome/free-solid-svg-icons'
|
||||
|
||||
library.add(
|
||||
faServer
|
||||
)
|
||||
library.add(faServer)
|
||||
|
||||
export default {
|
||||
components: { Popover },
|
||||
props: ['isProfile']
|
||||
props: ['isProfile'],
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -1,18 +1,19 @@
|
|||
import Checkbox from 'src/components/checkbox/checkbox.vue'
|
||||
import Setting from './setting.js'
|
||||
|
||||
const getUrl = state => state?.tuple ? state.tuple[1] + ':' + state.tuple[2] : state
|
||||
const getSocks = state => state?.tuple
|
||||
const getUrl = (state) =>
|
||||
state?.tuple ? state.tuple[1] + ':' + state.tuple[2] : state
|
||||
const getSocks = (state) => state?.tuple
|
||||
|
||||
export default {
|
||||
...Setting,
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
urlField: '',
|
||||
socksField: false
|
||||
socksField: false,
|
||||
}
|
||||
},
|
||||
created () {
|
||||
created() {
|
||||
Setting.created()
|
||||
this.urlField = getUrl(this.realDraftMode ? this.draft : this.state)
|
||||
this.socksField = getSocks(this.realDraftMode ? this.draft : this.state)
|
||||
|
|
@ -20,23 +21,23 @@ export default {
|
|||
computed: {
|
||||
...Setting.computed,
|
||||
// state that we'll show in the UI, i.e. transforming map into list
|
||||
displayState () {
|
||||
displayState() {
|
||||
if (this.visibleState?.tuple) {
|
||||
return this.visibleState.tuple[1] + ':' + this.visibleState.tuple[2]
|
||||
}
|
||||
return this.visibleState
|
||||
},
|
||||
socksState () {
|
||||
socksState() {
|
||||
return getSocks(this.visibleState)
|
||||
}
|
||||
},
|
||||
},
|
||||
components: {
|
||||
...Setting.components,
|
||||
Checkbox
|
||||
Checkbox,
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue ({ event, isProxy}) {
|
||||
getValue({ event, isProxy }) {
|
||||
if (isProxy) {
|
||||
this.socksField = event
|
||||
} else {
|
||||
|
|
@ -44,10 +45,10 @@ export default {
|
|||
}
|
||||
|
||||
if (this.socksField) {
|
||||
return { tuple: [ ':socks5', ...this.urlField.split(':') ] }
|
||||
return { tuple: [':socks5', ...this.urlField.split(':')] }
|
||||
} else {
|
||||
return this.urlField
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,60 +12,62 @@ export default {
|
|||
...Setting.components,
|
||||
Select,
|
||||
Attachment,
|
||||
MediaUpload
|
||||
MediaUpload,
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
purposeOptions () {
|
||||
return ['any','monochrome','maskable'].map(value => ({
|
||||
purposeOptions() {
|
||||
return ['any', 'monochrome', 'maskable'].map((value) => ({
|
||||
value,
|
||||
key: value,
|
||||
label: this.$t('admin_dash.instance.pwa.icon.' + value)
|
||||
label: this.$t('admin_dash.instance.pwa.icon.' + value),
|
||||
}))
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
attachment (e) {
|
||||
attachment(e) {
|
||||
const path = e[':src']
|
||||
if (!path) {
|
||||
return {
|
||||
mimetype: '',
|
||||
url: ''
|
||||
url: '',
|
||||
}
|
||||
}
|
||||
const url = path.includes('://') ? path : this.$store.state.instance.server + path
|
||||
const url = path.includes('://')
|
||||
? path
|
||||
: this.$store.state.instance.server + path
|
||||
|
||||
return {
|
||||
mimetype: fileTypeExt(url),
|
||||
url
|
||||
url,
|
||||
}
|
||||
},
|
||||
setMediaFile ({ event, index }) {
|
||||
setMediaFile({ event, index }) {
|
||||
this.update({
|
||||
event: {
|
||||
target: {
|
||||
value: event.url
|
||||
value: event.url,
|
||||
},
|
||||
},
|
||||
index,
|
||||
eventType: 'edit',
|
||||
field: ':src'
|
||||
field: ':src',
|
||||
})
|
||||
},
|
||||
setPurpose ({ event, index }) {
|
||||
setPurpose({ event, index }) {
|
||||
this.update({
|
||||
event: {
|
||||
target: {
|
||||
value: event
|
||||
value: event,
|
||||
},
|
||||
},
|
||||
index,
|
||||
eventType: 'edit',
|
||||
field: ':purpose'
|
||||
field: ':purpose',
|
||||
})
|
||||
},
|
||||
getValue ({ event, field, index, eventType }) {
|
||||
getValue({ event, field, index, eventType }) {
|
||||
switch (eventType) {
|
||||
case 'add': {
|
||||
const res = [...this.visibleState, {}]
|
||||
|
|
@ -85,7 +87,7 @@ export default {
|
|||
const item = clone(this.visibleState[index])
|
||||
const string = event.target.value
|
||||
|
||||
if (!string) {
|
||||
if (!string) {
|
||||
delete item[field]
|
||||
} else {
|
||||
item[field] = string
|
||||
|
|
@ -94,6 +96,6 @@ export default {
|
|||
return [...pre, item, ...post]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -3,40 +3,40 @@ import Setting from './setting.js'
|
|||
|
||||
export default {
|
||||
...Setting,
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
newValue: '',
|
||||
}
|
||||
},
|
||||
components: {
|
||||
...Setting.components,
|
||||
Checkbox
|
||||
Checkbox,
|
||||
},
|
||||
props: {
|
||||
...Setting.props
|
||||
...Setting.props,
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
isSeparate () {
|
||||
isSeparate() {
|
||||
// [[a1, b1], [a2, b2]] vs [a, b]
|
||||
return Array.isArray(this.visibleState[0])
|
||||
},
|
||||
normalizedState () {
|
||||
normalizedState() {
|
||||
if (this.isSeparate) {
|
||||
return this.visibleState.map(y => y.map(x => Number(x) || 0))
|
||||
return this.visibleState.map((y) => y.map((x) => Number(x) || 0))
|
||||
} else {
|
||||
return [this.visibleState.map(x => Number(x) || 0)]
|
||||
return [this.visibleState.map((x) => Number(x) || 0)]
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue ({ event, side, index, eventType }) {
|
||||
getValue({ event, side, index, eventType }) {
|
||||
if (eventType === 'edit') {
|
||||
const value = Number(event.target.value)
|
||||
if (Number.isNaN(value)) return this.visibleState
|
||||
|
||||
const newVal = [...this.normalizedState.map(x => [...x])]
|
||||
const newVal = [...this.normalizedState.map((x) => [...x])]
|
||||
newVal[side][index] = value
|
||||
return newVal
|
||||
}
|
||||
|
|
@ -48,6 +48,6 @@ export default {
|
|||
return [this.normalizedState[0]]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -7,119 +7,126 @@ export default {
|
|||
components: {
|
||||
ModifiedIndicator,
|
||||
DraftButtons,
|
||||
ProfileSettingIndicator
|
||||
ProfileSettingIndicator,
|
||||
},
|
||||
props: {
|
||||
modelValue: {
|
||||
type: String,
|
||||
default: null
|
||||
default: null,
|
||||
},
|
||||
path: {
|
||||
type: [String, Array],
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
showDescription: {
|
||||
type: Boolean,
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
descriptionPathOverride: {
|
||||
type: [String, Array],
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
suggestions: {
|
||||
type: [String, Array],
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
subgroup: {
|
||||
type: String,
|
||||
required: false
|
||||
required: false,
|
||||
},
|
||||
disabled: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
default: false,
|
||||
},
|
||||
parentPath: {
|
||||
type: [String, Array]
|
||||
type: [String, Array],
|
||||
},
|
||||
parentInvert: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
default: false,
|
||||
},
|
||||
expert: {
|
||||
type: [Number, String],
|
||||
default: 0
|
||||
default: 0,
|
||||
},
|
||||
source: {
|
||||
type: String,
|
||||
default: undefined
|
||||
default: undefined,
|
||||
},
|
||||
hideDraftButtons: { // this is for the weird backend hybrid (Boolean|String or Boolean|Number) settings
|
||||
hideDraftButtons: {
|
||||
// this is for the weird backend hybrid (Boolean|String or Boolean|Number) settings
|
||||
required: false,
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
hideLabel: {
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
hideDescription: {
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
swapDescriptionAndLabel: {
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
backendDescriptionPath: {
|
||||
type: [String, Array]
|
||||
type: [String, Array],
|
||||
},
|
||||
overrideBackendDescription: {
|
||||
type: Boolean
|
||||
type: Boolean,
|
||||
},
|
||||
overrideBackendDescriptionLabel: {
|
||||
type: [Boolean, String]
|
||||
type: [Boolean, String],
|
||||
},
|
||||
draftMode: {
|
||||
type: Boolean,
|
||||
default: undefined
|
||||
default: undefined,
|
||||
},
|
||||
timedApplyMode: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
default: false,
|
||||
},
|
||||
},
|
||||
inject: {
|
||||
defaultSource: {
|
||||
default: 'default'
|
||||
default: 'default',
|
||||
},
|
||||
defaultDraftMode: {
|
||||
default: false
|
||||
}
|
||||
default: false,
|
||||
},
|
||||
},
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
localDraft: null
|
||||
localDraft: null,
|
||||
}
|
||||
},
|
||||
created () {
|
||||
if (this.realDraftMode && (this.realSource !== 'admin' || this.path == null)) {
|
||||
created() {
|
||||
if (
|
||||
this.realDraftMode &&
|
||||
(this.realSource !== 'admin' || this.path == null)
|
||||
) {
|
||||
this.draft = cloneDeep(this.state)
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
draft: {
|
||||
get () {
|
||||
get() {
|
||||
if (this.realSource === 'admin' || this.path == null) {
|
||||
return get(this.$store.state.adminSettings.draft, this.canonPath)
|
||||
} else {
|
||||
return this.localDraft
|
||||
}
|
||||
},
|
||||
set (value) {
|
||||
set(value) {
|
||||
if (this.realSource === 'admin' || this.path == null) {
|
||||
this.$store.commit('updateAdminDraft', { path: this.canonPath, value })
|
||||
this.$store.commit('updateAdminDraft', {
|
||||
path: this.canonPath,
|
||||
value,
|
||||
})
|
||||
} else {
|
||||
this.localDraft = value
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
state () {
|
||||
state() {
|
||||
if (this.path == null) {
|
||||
return this.modelValue
|
||||
}
|
||||
|
|
@ -130,71 +137,93 @@ export default {
|
|||
return value
|
||||
}
|
||||
},
|
||||
visibleState () {
|
||||
visibleState() {
|
||||
return this.realDraftMode ? this.draft : this.state
|
||||
},
|
||||
realSource () {
|
||||
realSource() {
|
||||
return this.source || this.defaultSource
|
||||
},
|
||||
realDraftMode () {
|
||||
return typeof this.draftMode === 'undefined' ? this.defaultDraftMode : this.draftMode
|
||||
realDraftMode() {
|
||||
return typeof this.draftMode === 'undefined'
|
||||
? this.defaultDraftMode
|
||||
: this.draftMode
|
||||
},
|
||||
backendDescription () {
|
||||
return get(this.$store.state.adminSettings.descriptions, this.descriptionPath)
|
||||
backendDescription() {
|
||||
return get(
|
||||
this.$store.state.adminSettings.descriptions,
|
||||
this.descriptionPath,
|
||||
)
|
||||
},
|
||||
backendDescriptionLabel () {
|
||||
backendDescriptionLabel() {
|
||||
if (this.realSource !== 'admin') return ''
|
||||
if (this.overrideBackendDescriptionLabel !== '' && typeof this.overrideBackendDescriptionLabel === 'string') {
|
||||
if (
|
||||
this.overrideBackendDescriptionLabel !== '' &&
|
||||
typeof this.overrideBackendDescriptionLabel === 'string'
|
||||
) {
|
||||
return this.overrideBackendDescriptionLabel
|
||||
}
|
||||
if (!this.backendDescription || this.overrideBackendDescriptionLabel) {
|
||||
return this.$t([
|
||||
'admin_dash',
|
||||
'temp_overrides',
|
||||
...this.canonPath.map(p => p.replace(/\./g, '_DOT_')),
|
||||
'label'
|
||||
].join('.'))
|
||||
return this.$t(
|
||||
[
|
||||
'admin_dash',
|
||||
'temp_overrides',
|
||||
...this.canonPath.map((p) => p.replace(/\./g, '_DOT_')),
|
||||
'label',
|
||||
].join('.'),
|
||||
)
|
||||
} else {
|
||||
return this.swapDescriptionAndLabel
|
||||
? this.backendDescription?.description
|
||||
: this.backendDescription?.label
|
||||
}
|
||||
},
|
||||
backendDescriptionDescription () {
|
||||
backendDescriptionDescription() {
|
||||
if (this.description) return this.description
|
||||
if (this.realSource !== 'admin') return ''
|
||||
if (this.hideDescription) return null
|
||||
if (!this.backendDescription || this.overrideBackendDescription) {
|
||||
return this.$t([
|
||||
'admin_dash',
|
||||
'temp_overrides',
|
||||
...this.canonPath.map(p => p.replace(/\./g, '_DOT_')),
|
||||
'description'
|
||||
].join('.'))
|
||||
return this.$t(
|
||||
[
|
||||
'admin_dash',
|
||||
'temp_overrides',
|
||||
...this.canonPath.map((p) => p.replace(/\./g, '_DOT_')),
|
||||
'description',
|
||||
].join('.'),
|
||||
)
|
||||
} else {
|
||||
return this.swapDescriptionAndLabel
|
||||
? this.backendDescription?.label
|
||||
: this.backendDescription?.description
|
||||
}
|
||||
},
|
||||
backendDescriptionSuggestions () {
|
||||
backendDescriptionSuggestions() {
|
||||
return this.backendDescription?.suggestions || this.suggestions
|
||||
},
|
||||
shouldBeDisabled () {
|
||||
shouldBeDisabled() {
|
||||
if (this.path == null) {
|
||||
return this.disabled
|
||||
}
|
||||
let parentValue = null
|
||||
if (this.parentPath !== undefined && this.realSource === 'admin') {
|
||||
if (this.realDraftMode) {
|
||||
parentValue = get(this.$store.state.adminSettings.draft, this.parentPath)
|
||||
parentValue = get(
|
||||
this.$store.state.adminSettings.draft,
|
||||
this.parentPath,
|
||||
)
|
||||
} else {
|
||||
parentValue = get(this.configSource, this.parentPath)
|
||||
}
|
||||
}
|
||||
return this.disabled || (parentValue !== null ? (this.parentInvert ? parentValue : !parentValue) : false)
|
||||
return (
|
||||
this.disabled ||
|
||||
(parentValue !== null
|
||||
? this.parentInvert
|
||||
? parentValue
|
||||
: !parentValue
|
||||
: false)
|
||||
)
|
||||
},
|
||||
configSource () {
|
||||
configSource() {
|
||||
switch (this.realSource) {
|
||||
case 'profile':
|
||||
return this.$store.state.profileConfig
|
||||
|
|
@ -204,24 +233,31 @@ export default {
|
|||
return this.$store.getters.mergedConfig
|
||||
}
|
||||
},
|
||||
configSink () {
|
||||
configSink() {
|
||||
if (this.path == null) {
|
||||
return (k, v) => this.$emit('update:modelValue', v)
|
||||
}
|
||||
switch (this.realSource) {
|
||||
case 'profile':
|
||||
return (k, v) => this.$store.dispatch('setProfileOption', { name: k, value: v })
|
||||
return (k, v) =>
|
||||
this.$store.dispatch('setProfileOption', { name: k, value: v })
|
||||
case 'admin':
|
||||
return (k, v) => this.$store.dispatch('pushAdminSetting', { path: k, value: v })
|
||||
return (k, v) =>
|
||||
this.$store.dispatch('pushAdminSetting', { path: k, value: v })
|
||||
default:
|
||||
if (this.timedApplyMode) {
|
||||
return (k, v) => this.$store.dispatch('setOptionTemporarily', { name: k, value: v })
|
||||
return (k, v) =>
|
||||
this.$store.dispatch('setOptionTemporarily', {
|
||||
name: k,
|
||||
value: v,
|
||||
})
|
||||
} else {
|
||||
return (k, v) => this.$store.dispatch('setOption', { name: k, value: v })
|
||||
return (k, v) =>
|
||||
this.$store.dispatch('setOption', { name: k, value: v })
|
||||
}
|
||||
}
|
||||
},
|
||||
defaultState () {
|
||||
defaultState() {
|
||||
switch (this.realSource) {
|
||||
case 'profile':
|
||||
return {}
|
||||
|
|
@ -229,10 +265,10 @@ export default {
|
|||
return get(this.$store.getters.defaultConfig, this.path)
|
||||
}
|
||||
},
|
||||
isProfileSetting () {
|
||||
isProfileSetting() {
|
||||
return this.realSource === 'profile'
|
||||
},
|
||||
isChanged () {
|
||||
isChanged() {
|
||||
if (this.path == null) return false
|
||||
switch (this.realSource) {
|
||||
case 'profile':
|
||||
|
|
@ -242,24 +278,24 @@ export default {
|
|||
return this.state !== this.defaultState
|
||||
}
|
||||
},
|
||||
canonPath () {
|
||||
canonPath() {
|
||||
if (this.path == null) return null
|
||||
return Array.isArray(this.path) ? this.path : this.path.split('.')
|
||||
},
|
||||
descriptionPath () {
|
||||
descriptionPath() {
|
||||
if (this.path == null) return null
|
||||
if (this.descriptionPathOverride) return this.descriptionPathOverride
|
||||
const path = Array.isArray(this.path) ? this.path : this.path.split('.')
|
||||
if (this.subgroup) {
|
||||
return [
|
||||
...path.slice(0, path.length - 1),
|
||||
':subgroup,' + this.subgroup,
|
||||
...path.slice(path.length - 1)
|
||||
...path.slice(0, path.length - 1),
|
||||
':subgroup,' + this.subgroup,
|
||||
...path.slice(path.length - 1),
|
||||
]
|
||||
}
|
||||
return path
|
||||
},
|
||||
isDirty () {
|
||||
isDirty() {
|
||||
if (this.path == null) return false
|
||||
if (this.realSource === 'admin' && this.canonPath.length > 3) {
|
||||
return false // should not show draft buttons for "grouped" values
|
||||
|
|
@ -267,47 +303,59 @@ export default {
|
|||
return this.realDraftMode && !isEqual(this.draft, this.state)
|
||||
}
|
||||
},
|
||||
canHardReset () {
|
||||
return this.realSource === 'admin' && this.$store.state.adminSettings.modifiedPaths?.has(this.canonPath.join(' -> '))
|
||||
canHardReset() {
|
||||
return (
|
||||
this.realSource === 'admin' &&
|
||||
this.$store.state.adminSettings.modifiedPaths?.has(
|
||||
this.canonPath.join(' -> '),
|
||||
)
|
||||
)
|
||||
},
|
||||
matchesExpertLevel () {
|
||||
matchesExpertLevel() {
|
||||
const settingExpertLevel = this.expert || 0
|
||||
const userToggleExpert = this.$store.state.config.expertLevel || 0
|
||||
|
||||
return settingExpertLevel <= userToggleExpert
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
getValue (e) {
|
||||
getValue(e) {
|
||||
return e.target.value
|
||||
},
|
||||
update (e) {
|
||||
update(e) {
|
||||
if (this.realDraftMode) {
|
||||
this.draft = this.getValue(e)
|
||||
} else {
|
||||
this.configSink(this.path, this.getValue(e))
|
||||
}
|
||||
},
|
||||
commitDraft () {
|
||||
commitDraft() {
|
||||
if (this.realDraftMode) {
|
||||
this.configSink(this.path, this.draft)
|
||||
}
|
||||
},
|
||||
reset () {
|
||||
reset() {
|
||||
if (this.realDraftMode) {
|
||||
this.draft = cloneDeep(this.state)
|
||||
} else {
|
||||
set(this.$store.getters.mergedConfig, this.path, cloneDeep(this.defaultState))
|
||||
set(
|
||||
this.$store.getters.mergedConfig,
|
||||
this.path,
|
||||
cloneDeep(this.defaultState),
|
||||
)
|
||||
}
|
||||
},
|
||||
hardReset () {
|
||||
hardReset() {
|
||||
switch (this.realSource) {
|
||||
case 'admin':
|
||||
return this.$store.dispatch('resetAdminSetting', { path: this.path })
|
||||
.then(() => { this.draft = this.state })
|
||||
return this.$store
|
||||
.dispatch('resetAdminSetting', { path: this.path })
|
||||
.then(() => {
|
||||
this.draft = this.state
|
||||
})
|
||||
default:
|
||||
console.warn('Hard reset not implemented yet!')
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,19 +1,19 @@
|
|||
const SharedComputedObject = () => ({
|
||||
user () {
|
||||
user() {
|
||||
return this.$store.state.users.currentUser
|
||||
},
|
||||
expertLevel () {
|
||||
expertLevel() {
|
||||
return this.$store.getters.mergedConfig.expertLevel > 0
|
||||
},
|
||||
mergedConfig () {
|
||||
mergedConfig() {
|
||||
return this.$store.getters.mergedConfig
|
||||
},
|
||||
adminConfig () {
|
||||
adminConfig() {
|
||||
return this.$store.state.adminSettings.config
|
||||
},
|
||||
adminDraft () {
|
||||
adminDraft() {
|
||||
return this.$store.state.adminSettings.draft
|
||||
}
|
||||
},
|
||||
})
|
||||
|
||||
export default SharedComputedObject
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import Setting from './setting.js'
|
||||
|
||||
export default {
|
||||
...Setting
|
||||
...Setting,
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,13 +4,13 @@ export default {
|
|||
...Setting,
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getValue ({ e, side }) {
|
||||
getValue({ e, side }) {
|
||||
const [a, b] = this.visibleState || []
|
||||
if (side === 0) {
|
||||
return { tuple: [e.target.value, b]}
|
||||
return { tuple: [e.target.value, b] }
|
||||
} else {
|
||||
return { tuple: [a, e.target.value]}
|
||||
return { tuple: [a, e.target.value] }
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,7 +1,23 @@
|
|||
import Select from 'src/components/select/select.vue'
|
||||
import Setting from './setting.js'
|
||||
|
||||
export const allCssUnits = ['cm', 'mm', 'in', 'px', 'pt', 'pc', 'em', 'ex', 'ch', 'rem', 'vw', 'vh', 'vmin', 'vmax', '%']
|
||||
export const allCssUnits = [
|
||||
'cm',
|
||||
'mm',
|
||||
'in',
|
||||
'px',
|
||||
'pt',
|
||||
'pc',
|
||||
'em',
|
||||
'ex',
|
||||
'ch',
|
||||
'rem',
|
||||
'vw',
|
||||
'vh',
|
||||
'vmin',
|
||||
'vmax',
|
||||
'%',
|
||||
]
|
||||
export const defaultHorizontalUnits = ['px', 'rem', 'vw']
|
||||
export const defaultVerticalUnits = ['px', 'rem', 'vh']
|
||||
|
||||
|
|
@ -9,47 +25,51 @@ export default {
|
|||
...Setting,
|
||||
components: {
|
||||
...Setting.components,
|
||||
Select
|
||||
Select,
|
||||
},
|
||||
props: {
|
||||
...Setting.props,
|
||||
min: Number,
|
||||
units: {
|
||||
type: Array,
|
||||
default: () => allCssUnits
|
||||
default: () => allCssUnits,
|
||||
},
|
||||
unitSet: {
|
||||
type: String,
|
||||
default: 'none'
|
||||
default: 'none',
|
||||
},
|
||||
step: {
|
||||
type: Number,
|
||||
default: 1
|
||||
default: 1,
|
||||
},
|
||||
resetDefault: {
|
||||
type: Object,
|
||||
default: null
|
||||
}
|
||||
default: null,
|
||||
},
|
||||
},
|
||||
computed: {
|
||||
...Setting.computed,
|
||||
stateUnit () {
|
||||
return typeof this.state === 'string' ? this.state.replace(/[0-9,.]+/, '') : ''
|
||||
stateUnit() {
|
||||
return typeof this.state === 'string'
|
||||
? this.state.replace(/[0-9,.]+/, '')
|
||||
: ''
|
||||
},
|
||||
stateValue() {
|
||||
return typeof this.state === 'string'
|
||||
? this.state.replace(/[^0-9,.]+/, '')
|
||||
: ''
|
||||
},
|
||||
stateValue () {
|
||||
return typeof this.state === 'string' ? this.state.replace(/[^0-9,.]+/, '') : ''
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
...Setting.methods,
|
||||
getUnitString (value) {
|
||||
getUnitString(value) {
|
||||
if (this.unitSet === 'none') return value
|
||||
return this.$t(['settings', 'units', this.unitSet, value].join('.'))
|
||||
},
|
||||
updateValue (e) {
|
||||
updateValue(e) {
|
||||
this.configSink(this.path, parseFloat(e.target.value) + this.stateUnit)
|
||||
},
|
||||
updateUnit (e) {
|
||||
updateUnit(e) {
|
||||
let value = this.stateValue
|
||||
const newUnit = e.target.value
|
||||
if (this.resetDefault) {
|
||||
|
|
@ -59,6 +79,6 @@ export default {
|
|||
}
|
||||
}
|
||||
this.configSink(this.path, value + newUnit)
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ import { FontAwesomeIcon as FAIcon } from '@fortawesome/vue-fontawesome'
|
|||
import './vertical_tab_switcher.scss'
|
||||
import { useInterfaceStore } from 'src/stores/interface'
|
||||
|
||||
const findFirstUsable = (slots) => slots.findIndex(_ => _.props)
|
||||
const findFirstUsable = (slots) => slots.findIndex((_) => _.props)
|
||||
|
||||
export default {
|
||||
name: 'VerticalTabSwitcher',
|
||||
|
|
@ -16,30 +16,30 @@ export default {
|
|||
renderOnlyFocused: {
|
||||
required: false,
|
||||
type: Boolean,
|
||||
default: false
|
||||
default: false,
|
||||
},
|
||||
onSwitch: {
|
||||
required: false,
|
||||
type: Function,
|
||||
default: undefined
|
||||
default: undefined,
|
||||
},
|
||||
activeTab: {
|
||||
required: false,
|
||||
type: String,
|
||||
default: undefined
|
||||
default: undefined,
|
||||
},
|
||||
bodyScrollLock: {
|
||||
required: false,
|
||||
type: Boolean,
|
||||
default: false
|
||||
default: false,
|
||||
},
|
||||
parentCollapsed: {
|
||||
required: false,
|
||||
type: Boolean,
|
||||
default: null
|
||||
}
|
||||
default: null,
|
||||
},
|
||||
},
|
||||
data () {
|
||||
data() {
|
||||
return {
|
||||
active: findFirstUsable(this.slots()),
|
||||
resizeHandler: null,
|
||||
|
|
@ -47,82 +47,89 @@ export default {
|
|||
}
|
||||
},
|
||||
computed: {
|
||||
activeIndex () {
|
||||
activeIndex() {
|
||||
// In case of controlled component
|
||||
if (this.activeTab) {
|
||||
return this.slots().findIndex(slot => slot && slot.props && this.activeTab === slot.props.key)
|
||||
return this.slots().findIndex(
|
||||
(slot) => slot && slot.props && this.activeTab === slot.props.key,
|
||||
)
|
||||
} else {
|
||||
return this.active
|
||||
}
|
||||
},
|
||||
isActive () {
|
||||
return tabName => {
|
||||
const isWanted = slot => slot.props && slot.props['data-tab-name'] === tabName
|
||||
isActive() {
|
||||
return (tabName) => {
|
||||
const isWanted = (slot) =>
|
||||
slot.props && slot.props['data-tab-name'] === tabName
|
||||
return this.$slots.default().findIndex(isWanted) === this.activeIndex
|
||||
}
|
||||
},
|
||||
...mapPiniaState(useInterfaceStore, {
|
||||
mobileLayout: store => store.layoutType === 'mobile'
|
||||
mobileLayout: (store) => store.layoutType === 'mobile',
|
||||
}),
|
||||
},
|
||||
beforeUpdate () {
|
||||
beforeUpdate() {
|
||||
const currentSlot = this.slots()[this.active]
|
||||
if (!currentSlot.props) {
|
||||
this.active = findFirstUsable(this.slots())
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
clickTab (index) {
|
||||
clickTab(index) {
|
||||
return (e) => {
|
||||
e.preventDefault()
|
||||
this.setTab(index)
|
||||
}
|
||||
},
|
||||
setTab (index) {
|
||||
setTab(index) {
|
||||
if (typeof this.onSwitch === 'function') {
|
||||
this.onSwitch.call(null, this.slots()[index].key)
|
||||
}
|
||||
this.active = index
|
||||
this.changeNavSide('content')
|
||||
},
|
||||
changeNavSide (side) {
|
||||
changeNavSide(side) {
|
||||
if (this.navSide !== side) {
|
||||
this.navSide = side
|
||||
}
|
||||
},
|
||||
// DO NOT put it to computed, it doesn't work (caching?)
|
||||
slots () {
|
||||
slots() {
|
||||
if (this.$slots.default()[0].type === Fragment) {
|
||||
return this.$slots.default()[0].children
|
||||
}
|
||||
return this.$slots.default()
|
||||
}
|
||||
},
|
||||
},
|
||||
render () {
|
||||
const tabs = this.slots()
|
||||
.map((slot, index) => {
|
||||
const props = slot.props
|
||||
if (!props) return
|
||||
const classesTab = ['vertical-tab', 'menu-item']
|
||||
if (this.activeIndex === index && useInterfaceStore().layoutType !== 'mobile') {
|
||||
classesTab.push('-active')
|
||||
}
|
||||
return (
|
||||
<button
|
||||
disabled={props.disabled}
|
||||
onClick={this.clickTab(index)}
|
||||
class={classesTab.join(' ')}
|
||||
type="button"
|
||||
role="tab"
|
||||
title={props.label}
|
||||
>
|
||||
{!props.icon ? '' : (<FAIcon class="tab-icon" size="1x" fixed-width icon={props.icon}/>)}
|
||||
<span class="text">
|
||||
{props.label}
|
||||
</span>
|
||||
</button>
|
||||
)
|
||||
})
|
||||
render() {
|
||||
const tabs = this.slots().map((slot, index) => {
|
||||
const props = slot.props
|
||||
if (!props) return
|
||||
const classesTab = ['vertical-tab', 'menu-item']
|
||||
if (
|
||||
this.activeIndex === index &&
|
||||
useInterfaceStore().layoutType !== 'mobile'
|
||||
) {
|
||||
classesTab.push('-active')
|
||||
}
|
||||
return (
|
||||
<button
|
||||
disabled={props.disabled}
|
||||
onClick={this.clickTab(index)}
|
||||
class={classesTab.join(' ')}
|
||||
type="button"
|
||||
role="tab"
|
||||
title={props.label}
|
||||
>
|
||||
{!props.icon ? (
|
||||
''
|
||||
) : (
|
||||
<FAIcon class="tab-icon" size="1x" fixed-width icon={props.icon} />
|
||||
)}
|
||||
<span class="text">{props.label}</span>
|
||||
</button>
|
||||
)
|
||||
})
|
||||
|
||||
const contents = this.slots().map((slot, index) => {
|
||||
const props = slot.props
|
||||
|
|
@ -134,9 +141,8 @@ export default {
|
|||
slot.props['delay-render'] = false
|
||||
delayRender = false
|
||||
}
|
||||
const renderSlot = (!delayRender && (!this.renderOnlyFocused || active))
|
||||
? slot
|
||||
: ''
|
||||
const renderSlot =
|
||||
!delayRender && (!this.renderOnlyFocused || active) ? slot : ''
|
||||
|
||||
const headerClasses = ['tab-content-label']
|
||||
const header = (
|
||||
|
|
@ -147,17 +153,16 @@ export default {
|
|||
title={this.$t('nav.back')}
|
||||
class="button-unstyled"
|
||||
>
|
||||
<FAIcon
|
||||
size="lg"
|
||||
class="back-button-icon"
|
||||
icon="chevron-left"
|
||||
/>
|
||||
<FAIcon size="lg" class="back-button-icon" icon="chevron-left" />
|
||||
</button>
|
||||
{props.label}
|
||||
</h2>
|
||||
)
|
||||
|
||||
const wrapperClasses = ['tab-content-wrapper', active ? '-active' : '-hidden' ]
|
||||
const wrapperClasses = [
|
||||
'tab-content-wrapper',
|
||||
active ? '-active' : '-hidden',
|
||||
]
|
||||
const contentClasses = ['tab-content']
|
||||
if (props['full-width'] || props['full-width'] === '') {
|
||||
contentClasses.push('-full-width')
|
||||
|
|
@ -168,14 +173,10 @@ export default {
|
|||
wrapperClasses.push('-full-height')
|
||||
}
|
||||
return (
|
||||
<div class={wrapperClasses} >
|
||||
<div class="tab-mobile-header">
|
||||
{header}
|
||||
</div>
|
||||
<div class={wrapperClasses}>
|
||||
<div class="tab-mobile-header">{header}</div>
|
||||
<div class="tab-slot-wrapper">
|
||||
<div class={contentClasses} >
|
||||
{renderSlot}
|
||||
</div>
|
||||
<div class={contentClasses}>{renderSlot}</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
|
|
@ -193,12 +194,8 @@ export default {
|
|||
}
|
||||
|
||||
return (
|
||||
<div ref="root" class={ rootClasses.join(' ') }>
|
||||
<div
|
||||
class="tabs"
|
||||
role="tablist"
|
||||
ref="nav"
|
||||
>
|
||||
<div ref="root" class={rootClasses.join(' ')}>
|
||||
<div class="tabs" role="tablist" ref="nav">
|
||||
{tabs}
|
||||
</div>
|
||||
<div
|
||||
|
|
@ -211,5 +208,5 @@ export default {
|
|||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
},
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue