diff --git a/src/app/components/generator/McdocRenderer.tsx b/src/app/components/generator/McdocRenderer.tsx index c37af4f0..34e605e7 100644 --- a/src/app/components/generator/McdocRenderer.tsx +++ b/src/app/components/generator/McdocRenderer.tsx @@ -14,6 +14,8 @@ import { useFocus } from '../../hooks/useFocus.js' import { generateColor, hexId } from '../../Utils.js' import { Octicon } from '../Octicon.jsx' +const SPECIAL_UNSET = '__unset__' + export interface McdocContext extends core.CheckerContext {} type MakeEdit = (edit: (range: core.Range) => JsonNode | undefined) => void @@ -47,7 +49,7 @@ interface HeadProps extends Props { } function Head({ type, optional, node, makeEdit, ctx }: HeadProps) { if (type.kind === 'string') { - return + return } if (type.kind === 'enum') { return @@ -76,10 +78,10 @@ function Head({ type, optional, node, makeEdit, ctx }: HeadProps) { return <> } -interface StringHeadProps extends Props { +interface StringHeadProps extends HeadProps { type: StringType } -function StringHead({ type, node, makeEdit, ctx }: StringHeadProps) { +function StringHead({ type, optional, node, makeEdit, ctx }: StringHeadProps) { const { locale } = useLocale() const value = JsonStringNode.is(node) ? node.value : undefined @@ -89,7 +91,7 @@ function StringHead({ type, node, makeEdit, ctx }: StringHeadProps) { return } makeEdit((range) => { - if (newValue.length === 0) { + if (newValue.length === 0 && optional) { return undefined } return { @@ -100,7 +102,7 @@ function StringHead({ type, node, makeEdit, ctx }: StringHeadProps) { valueMap: [{ inner: core.Range.create(0), outer: core.Range.create(range.start) }], } }) - }, [node, makeEdit]) + }, [optional, node, makeEdit]) const idAttribute = type.attributes?.find(a => a.name === 'id')?.value const idRegistry = idAttribute?.kind === 'literal' && idAttribute.value.kind === 'string' @@ -127,7 +129,9 @@ function StringHead({ type, node, makeEdit, ctx }: StringHeadProps) { return <> {isSelect ? <> - onChangeValue((e.target as HTMLInputElement).value)}> + {(value === undefined || optional) && } + {(value !== undefined && !completions.map(c => c.value).includes(value)) && } {completions.map(c => )} : <> @@ -147,14 +151,16 @@ interface EnumHeadProps extends HeadProps { type: SimplifiedEnum, } function EnumHead({ type, optional, node, makeEdit }: EnumHeadProps) { - const value = JsonStringNode.is(node) ? node.value : undefined + const { locale } = useLocale() + + const value = JsonStringNode.is(node) ? node.value : (node && JsonNumberNode.is(node)) ? Number(node.value.value) : undefined const onChangeValue = useCallback((newValue: string) => { if (value === newValue) { return } makeEdit((range) => { - if (newValue === '__unset__') { + if (newValue === SPECIAL_UNSET) { return undefined } if (type.enumKind === 'string') { @@ -182,8 +188,9 @@ function EnumHead({ type, optional, node, makeEdit }: EnumHeadProps) { }) }, [type.enumKind, value, makeEdit]) - return onChangeValue((e.target as HTMLSelectElement).value)}> + {(value === undefined || optional) && } + {(value !== undefined && !type.values.map(v => v.value).includes(value)) && } {type.values.map(value => )} @@ -268,11 +275,13 @@ interface UnionHeadProps extends HeadProps { type: UnionType } function UnionHead({ type, optional, node, makeEdit, ctx }: UnionHeadProps) { + const { locale } = useLocale() + const selectedType = findSelectedMember(type, node) const onSelect = useCallback((newValue: string) => { makeEdit((range) => { - if (newValue === '__unset__') { + if (newValue === SPECIAL_UNSET) { return undefined } const newSelected = type.members[parseInt(newValue)] @@ -283,8 +292,8 @@ function UnionHead({ type, optional, node, makeEdit, ctx }: UnionHeadProps) { const memberIndex = type.members.findIndex(m => quickEqualTypes(m, selectedType)) return <> - -1 ? memberIndex : SPECIAL_UNSET} onInput={(e) => onSelect((e.target as HTMLSelectElement).value)}> + {optional && } {type.members.map((member, index) => )} @@ -605,19 +614,19 @@ function Errors({ type, node, ctx }: ErrorsProps) { if (node === undefined) { return [] } - return ctx.err.errors + const errors = ctx.err.errors // Get all errors inside the current node .filter(e => core.Range.containsRange(node.range, e.range, true)) // Unless they are inside a child node .filter(e => !node.children?.some(c => (c.type === 'item' || c.type === 'pair') && core.Range.containsRange(c.range, e.range, true))) // Filter out "Missing key" errors .filter(e => !(core.Range.length(e.range) === 1 && (type.kind === 'struct' || (type.kind === 'union' && findSelectedMember(type, node).kind === 'struct')))) + // Hide warnings if there are errors + return errors.find(e => e.severity === 3) + ? errors.filter(e => e.severity === 3) + : errors }, [type, node, ctx]) - if (errors.length > 0) { - console.log(type, node, errors) - } - return <> {errors.map(e => )} @@ -631,7 +640,7 @@ function ErrorIndicator({ error }: ErrorIndicatorProps) { return
setActive()}> {Octicon.issue_opened} - {error.message} + {error.message.replace(/ \(rule: [a-zA-Z]+\)$/, '')}
} diff --git a/src/locales/en.json b/src/locales/en.json index 1be96c3e..0806963b 100644 --- a/src/locales/en.json +++ b/src/locales/en.json @@ -289,6 +289,7 @@ "transformation.scale": "Scale", "transformation.translation": "Translation", "undo": "Undo", + "unset": "-- unset --", "version_diff.word_wrap": "Word wrap", "versions.all": "All versions", "versions.article": "Article",