nitro-v36-with-renderer-v36
/
src /
components /
wired /
views /
actions /
WiredActionOverrideHeightView.tsx
WiredActionOverrideHeightView.tsx 3.7 Ko
Télécharger le fichier
import { FC, useEffect, useState } from 'react';
import { localizeWithFallback, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredSliderSection } from '../WiredSliderSection';
import { WiredSourcesSelector } from '../WiredSourcesSelector';
import { slotFurniSource } from '../WiredSourceSlots';
import { WiredActionBaseView } from './WiredActionBaseView';
import { Radio } from '../../../../common/Radio';
import { NativeTextTree } from '../../../../common/native-text/NativeTextTree';
/**
* Puts the selected furni at a height you type, or hands them back their stacking height.
*
* Official: the two-way choice in its section, then a slider section over 0 to 8000 (thousandths of
* a tile, shown as they are) that is disabled for "back to the stacking height". Ints: [height, type];
* the furni source is the official source slot.
*/
const MIN_HEIGHT = 0;
const MAX_HEIGHT = 8000;
const MODE_SET = 0;
const MODE_RELEASE = 1;
const MODE_LABELS: Record<number, { key: string; fallback: string }> = {
[MODE_SET]: { key: 'wiredfurni.params.override_height.type.0', fallback: 'Set this height' },
[MODE_RELEASE]: { key: 'wiredfurni.params.override_height.type.1', fallback: 'Back to the stacking height' }
};
const clampHeight = (value: number) => {
if (!Number.isFinite(value)) return MIN_HEIGHT;
return Math.min(MAX_HEIGHT, Math.max(MIN_HEIGHT, Math.round(value)));
};
export const WiredActionOverrideHeightView: FC<{}> = () => {
const { trigger = null, setIntParams = null, setSourceTypes = null } = useWired();
const [height, setHeight] = useState<number>(0);
const [mode, setMode] = useState<number>(MODE_SET);
const [furniSource, setFurniSource] = useState<number>(0);
useEffect(() => {
if (!trigger) return;
const data = trigger.intData ?? [];
setHeight(clampHeight(data.length > 0 ? data[0] : 0));
setMode(data.length > 1 && data[1] === MODE_RELEASE ? MODE_RELEASE : MODE_SET);
setFurniSource(slotFurniSource(trigger));
}, [trigger]);
const save = () => {
setIntParams([height, mode]);
setSourceTypes({ furni: [furniSource], users: [] });
};
return (
<NativeTextTree>
<WiredActionBaseView
hasSpecialInput={true}
requiresFurni={WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT}
save={save}
footer={<WiredSourcesSelector showFurni={true} furniSource={furniSource} onChangeFurni={setFurniSource} />}
>
<div className="flex flex-col gap-2">
<Text bold>{localizeWithFallback('wiredfurni.params.override_height.type', 'Height')}</Text>
{[MODE_SET, MODE_RELEASE].map((value) => (
<label key={value} className="flex items-center gap-1">
<Radio checked={mode === value} name="overrideHeightMode" onCheckedChange={() => setMode(value)} />
<Text>{localizeWithFallback(MODE_LABELS[value].key, MODE_LABELS[value].fallback)}</Text>
</label>
))}
</div>
<div className={mode === MODE_RELEASE ? 'pointer-events-none opacity-50' : ''}>
<WiredSliderSection
max={MAX_HEIGHT}
min={MIN_HEIGHT}
title={localizeWithFallback('wiredfurni.params.override_height.height', 'Height')}
value={height}
onChange={(value) => setHeight(clampHeight(value))}
/>
</div>
</WiredActionBaseView>
</NativeTextTree>
);
};
