Skip to content

Commit

Permalink
Close #537 implement alphabetical sort in output
Browse files Browse the repository at this point in the history
  • Loading branch information
misode committed Oct 4, 2024
1 parent 22c8566 commit fab3088
Show file tree
Hide file tree
Showing 3 changed files with 37 additions and 6 deletions.
18 changes: 12 additions & 6 deletions src/app/components/generator/SourcePanel.tsx
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import { DataModel } from '@mcschema/core'
import { useCallback, useEffect, useRef, useState } from 'preact/hooks'
import { useLocale } from '../../contexts/index.js'
import { useModel } from '../../hooks/index.js'
import { useLocalStorage, useModel } from '../../hooks/index.js'
import { getOutput } from '../../schema/transformOutput.js'
import type { BlockStateRegistry } from '../../services/index.js'
import { getSourceFormats, getSourceIndent, getSourceIndents, parseSource, stringifySource } from '../../services/index.js'
import { getSourceFormats, getSourceIndent, getSourceIndents, parseSource, sortData, stringifySource } from '../../services/index.js'
import { Store } from '../../Store.js'
import { message } from '../../Utils.js'
import { Btn, BtnMenu } from '../index.js'
Expand All @@ -30,6 +30,7 @@ export function SourcePanel({ name, model, blockStates, doCopy, doDownload, doIm
const { locale } = useLocale()
const [indent, setIndent] = useState(Store.getIndent())
const [format, setFormat] = useState(Store.getFormat())
const [sort, setSort] = useLocalStorage('misode_output_sort', 'schema')
const [highlighting, setHighlighting] = useState(Store.getHighlighting())
const [braceLoaded, setBraceLoaded] = useState(false)
const download = useRef<HTMLAnchorElement>(null)
Expand All @@ -40,9 +41,12 @@ export function SourcePanel({ name, model, blockStates, doCopy, doDownload, doIm
const editor = useRef<Editor>()

const getSerializedOutput = useCallback((model: DataModel, blockStates: BlockStateRegistry) => {
const data = getOutput(model, blockStates)
let data = getOutput(model, blockStates)
if (sort === 'alphabetically') {
data = sortData(data)
}
return stringifySource(data, format, indent)
}, [indent, format])
}, [indent, format, sort])

useEffect(() => {
retransform.current = () => {
Expand Down Expand Up @@ -80,7 +84,7 @@ export function SourcePanel({ name, model, blockStates, doCopy, doDownload, doIm
console.error(e)
}
}
}, [model, blockStates, indent, format, highlighting])
}, [model, blockStates, indent, format, sort, highlighting])

useEffect(() => {
if (highlighting) {
Expand Down Expand Up @@ -156,7 +160,7 @@ export function SourcePanel({ name, model, blockStates, doCopy, doDownload, doIm
editor.current.configure(indent, format === 'snbt' ? 'yaml' : format)
retransform.current()
}
}, [indent, format, highlighting, braceLoaded])
}, [indent, format, sort, highlighting, braceLoaded])

useEffect(() => {
if (doCopy && model && blockStates) {
Expand Down Expand Up @@ -210,6 +214,8 @@ export function SourcePanel({ name, model, blockStates, doCopy, doDownload, doIm
<Btn label={locale(`format.${key}`)} active={format === key}
onClick={() => changeFormat(key)} />)}
<hr />
<Btn icon={sort === 'alphabetically' ? 'square_fill' : 'square'} label={locale('sort_alphabetically')}
onClick={() => setSort(sort === 'alphabetically' ? 'schema' : 'alphabetically')} />
<Btn icon={highlighting ? 'square_fill' : 'square'} label={locale('highlighting')}
onClick={() => changeHighlighting(!highlighting)} />
</BtnMenu>
Expand Down
24 changes: 24 additions & 0 deletions src/app/services/Source.ts
Original file line number Diff line number Diff line change
Expand Up @@ -60,3 +60,27 @@ export function getSourceIndents() {
export function getSourceFormats() {
return Object.keys(FORMATS)
}

export function sortData(data: any): any {
if (typeof data !== 'object' || data === null) {
return data
}
if (Array.isArray(data)) {
return data.map(sortData)
}
const ordered = Object.create(null)
for (const symbol of Object.getOwnPropertySymbols(data)) {
ordered[symbol] = data[symbol]
}
const orderedKeys = Object.keys(data).sort(customOrder)
for (const key of orderedKeys) {
ordered[key] = sortData(data[key])
}
return ordered
}

const priority = ['type', 'parent']
function customOrder(a: string, b: string) {
return (priority.indexOf(a) + 1 || Infinity) - (priority.indexOf(b) + 1 || Infinity)
|| a.localeCompare(b)
}
1 change: 1 addition & 0 deletions src/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -235,6 +235,7 @@
"show_output": "Show output",
"show_preview": "Show preview",
"show_project": "Show project",
"sort_alphabetically": "Sort alphabetically",
"sounds.add_sound": "Add sound",
"sounds.copy_command": "Copy command",
"sounds.delay": "Delay",
Expand Down

0 comments on commit fab3088

Please sign in to comment.