🆙 Init V3

This commit is contained in:
DuckieTM
2026-01-31 09:10:52 +01:00
commit 7feb10ab15
1733 changed files with 53405 additions and 0 deletions
@@ -0,0 +1,41 @@
import { WiredActionDefinition } from '@nitrots/nitro-renderer';
import { FC, PropsWithChildren, useEffect } from 'react';
import ReactSlider from 'react-slider';
import { GetWiredTimeLocale, LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredBaseView } from '../WiredBaseView';
export interface WiredActionBaseViewProps
{
hasSpecialInput: boolean;
requiresFurni: number;
save: () => void;
}
export const WiredActionBaseView: FC<PropsWithChildren<WiredActionBaseViewProps>> = props =>
{
const { requiresFurni = WiredFurniType.STUFF_SELECTION_OPTION_NONE, save = null, hasSpecialInput = false, children = null } = props;
const { trigger = null, actionDelay = 0, setActionDelay = null } = useWired();
useEffect(() =>
{
setActionDelay((trigger as WiredActionDefinition).delayInPulses);
}, [ trigger, setActionDelay ]);
return (
<WiredBaseView hasSpecialInput={ hasSpecialInput } requiresFurni={ requiresFurni } save={ save } wiredType="action">
{ children }
{ !!children && <hr className="m-0 bg-dark" /> }
<div className="flex flex-col">
<Text bold>{ LocalizeText('wiredfurni.params.delay', [ 'seconds' ], [ GetWiredTimeLocale(actionDelay) ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 20 }
min={ 0 }
value={ actionDelay }
onChange={ event => setActionDelay(event) } />
</div>
</WiredBaseView>
);
};
@@ -0,0 +1,39 @@
import { GetSessionDataManager } from '@nitrots/nitro-renderer';
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WIRED_STRING_DELIMETER, WiredFurniType } from '../../../../api';
import { Button, LayoutAvatarImageView, Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
const DEFAULT_FIGURE: string = 'hd-180-1.ch-210-66.lg-270-82.sh-290-81';
export const WiredActionBotChangeFigureView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const [ figure, setFigure ] = useState('');
const { trigger = null, setStringParam = null } = useWired();
const save = () => setStringParam((botName + WIRED_STRING_DELIMETER + figure));
useEffect(() =>
{
const data = trigger.stringData.split(WIRED_STRING_DELIMETER);
if(data.length > 0) setBotName(data[0]);
if(data.length > 1) setFigure(data[1].length > 0 ? data[1] : DEFAULT_FIGURE);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
<div className="flex items-center justify-center">
<LayoutAvatarImageView direction={ 4 } figure={ figure } />
<Button onClick={ event => setFigure(GetSessionDataManager().figure) }>{ LocalizeText('wiredfurni.params.capture.figure') }</Button>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,44 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionBotFollowAvatarView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const [ followMode, setFollowMode ] = useState(-1);
const { trigger = null, setStringParam = null, setIntParams = null } = useWired();
const save = () =>
{
setStringParam(botName);
setIntParams([ followMode ]);
};
useEffect(() =>
{
setBotName(trigger.stringData);
setFollowMode((trigger.intData.length > 0) ? trigger.intData[0] : 0);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
<div className="flex flex-col gap-1">
<div className="flex items-center gap-1">
<input checked={ (followMode === 1) } className="form-check-input" id="followMode1" name="followMode" type="radio" onChange={ event => setFollowMode(1) } />
<Text>{ LocalizeText('wiredfurni.params.start.following') }</Text>
</div>
<div className="flex items-center gap-1">
<input checked={ (followMode === 0) } className="form-check-input" id="followMode2" name="followMode" type="radio" onChange={ event => setFollowMode(0) } />
<Text>{ LocalizeText('wiredfurni.params.stop.following') }</Text>
</div>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,43 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
const ALLOWED_HAND_ITEM_IDS: number[] = [ 2, 5, 7, 8, 9, 10, 27 ];
export const WiredActionBotGiveHandItemView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const [ handItemId, setHandItemId ] = useState(-1);
const { trigger = null, setStringParam = null, setIntParams = null } = useWired();
const save = () =>
{
setStringParam(botName);
setIntParams([ handItemId ]);
};
useEffect(() =>
{
setBotName(trigger.stringData);
setHandItemId((trigger.intData.length > 0) ? trigger.intData[0] : 0);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.handitem') }</Text>
<select className="form-select form-select-sm" value={ handItemId } onChange={ event => setHandItemId(parseInt(event.target.value)) }>
<option value="0">------</option>
{ ALLOWED_HAND_ITEM_IDS.map(value => <option key={ value } value={ value }>{ LocalizeText(`handitem${ value }`) }</option>) }
</select>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,28 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionBotMoveView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const { trigger = null, setStringParam = null } = useWired();
const save = () => setStringParam(botName);
useEffect(() =>
{
setBotName(trigger.stringData);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,53 @@
import { FC, useEffect, useState } from 'react';
import { GetConfigurationValue, LocalizeText, WIRED_STRING_DELIMETER, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionBotTalkToAvatarView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const [ message, setMessage ] = useState('');
const [ talkMode, setTalkMode ] = useState(-1);
const { trigger = null, setStringParam = null, setIntParams = null } = useWired();
const save = () =>
{
setStringParam(botName + WIRED_STRING_DELIMETER + message);
setIntParams([ talkMode ]);
};
useEffect(() =>
{
const data = trigger.stringData.split(WIRED_STRING_DELIMETER);
if(data.length > 0) setBotName(data[0]);
if(data.length > 1) setMessage(data[1].length > 0 ? data[1] : '');
setTalkMode((trigger.intData.length > 0) ? trigger.intData[0] : 0);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.message') }</Text>
<NitroInput maxLength={ GetConfigurationValue<number>('wired.action.bot.talk.to.avatar.max.length', 64) } type="text" value={ message } onChange={ event => setMessage(event.target.value) } />
</div>
<div className="flex flex-col gap-1">
<div className="flex items-center gap-1">
<input checked={ (talkMode === 0) } className="form-check-input" id="talkMode1" name="talkMode" type="radio" onChange={ event => setTalkMode(0) } />
<Text>{ LocalizeText('wiredfurni.params.talk') }</Text>
</div>
<div className="flex items-center gap-1">
<input checked={ (talkMode === 1) } className="form-check-input" id="talkMode2" name="talkMode" type="radio" onChange={ event => setTalkMode(1) } />
<Text>{ LocalizeText('wiredfurni.params.whisper') }</Text>
</div>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,53 @@
import { FC, useEffect, useState } from 'react';
import { GetConfigurationValue, LocalizeText, WIRED_STRING_DELIMETER, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionBotTalkView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const [ message, setMessage ] = useState('');
const [ talkMode, setTalkMode ] = useState(-1);
const { trigger = null, setStringParam = null, setIntParams = null } = useWired();
const save = () =>
{
setStringParam(botName + WIRED_STRING_DELIMETER + message);
setIntParams([ talkMode ]);
};
useEffect(() =>
{
const data = trigger.stringData.split(WIRED_STRING_DELIMETER);
if(data.length > 0) setBotName(data[0]);
if(data.length > 1) setMessage(data[1].length > 0 ? data[1] : '');
setTalkMode((trigger.intData.length > 0) ? trigger.intData[0] : 0);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.message') }</Text>
<NitroInput maxLength={ GetConfigurationValue<number>('wired.action.bot.talk.max.length', 64) } type="text" value={ message } onChange={ event => setMessage(event.target.value) } />
</div>
<div className="flex flex-col gap-1">
<div className="flex items-center gap-1">
<input checked={ (talkMode === 0) } className="form-check-input" id="talkMode1" name="talkMode" type="radio" onChange={ event => setTalkMode(0) } />
<Text>{ LocalizeText('wiredfurni.params.talk') }</Text>
</div>
<div className="flex items-center gap-1">
<input checked={ (talkMode === 1) } className="form-check-input" id="talkMode2" name="talkMode" type="radio" onChange={ event => setTalkMode(1) } />
<Text>{ LocalizeText('wiredfurni.params.shout') }</Text>
</div>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,28 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionBotTeleportView: FC<{}> = props =>
{
const [ botName, setBotName ] = useState('');
const { trigger = null, setStringParam = null } = useWired();
const save = () => setStringParam(botName);
useEffect(() =>
{
setBotName(trigger.stringData);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.bot.name') }</Text>
<NitroInput maxLength={ 32 } type="text" value={ botName } onChange={ event => setBotName(event.target.value) } />
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionCallAnotherStackView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ null } />;
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionChaseView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ null } />;
};
@@ -0,0 +1,28 @@
import { FC, useEffect, useState } from 'react';
import { GetConfigurationValue, LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionChatView: FC<{}> = props =>
{
const [ message, setMessage ] = useState('');
const { trigger = null, setStringParam = null } = useWired();
const save = () => setStringParam(message);
useEffect(() =>
{
setMessage(trigger.stringData);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.message') }</Text>
<NitroInput maxLength={ GetConfigurationValue<number>('wired.action.chat.max.length', 100) } type="text" value={ message } onChange={ event => setMessage(event.target.value) } />
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionFleeView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ null } />;
};
@@ -0,0 +1,161 @@
import { FC, useEffect, useState } from 'react';
import { FaPlus, FaTrash } from 'react-icons/fa';
import ReactSlider from 'react-slider';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Button, Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionGiveRewardView: FC<{}> = props =>
{
const [ limitEnabled, setLimitEnabled ] = useState(false);
const [ rewardTime, setRewardTime ] = useState(1);
const [ uniqueRewards, setUniqueRewards ] = useState(false);
const [ rewardsLimit, setRewardsLimit ] = useState(1);
const [ limitationInterval, setLimitationInterval ] = useState(1);
const [ rewards, setRewards ] = useState<{ isBadge: boolean, itemCode: string, probability: number }[]>([]);
const { trigger = null, setIntParams = null, setStringParam = null } = useWired();
const addReward = () => setRewards(rewards => [ ...rewards, { isBadge: false, itemCode: '', probability: null } ]);
const removeReward = (index: number) =>
{
setRewards(prevValue =>
{
const newValues = Array.from(prevValue);
newValues.splice(index, 1);
return newValues;
});
};
const updateReward = (index: number, isBadge: boolean, itemCode: string, probability: number) =>
{
const rewardsClone = Array.from(rewards);
const reward = rewardsClone[index];
if(!reward) return;
reward.isBadge = isBadge;
reward.itemCode = itemCode;
reward.probability = probability;
setRewards(rewardsClone);
};
const save = () =>
{
let stringRewards = [];
for(const reward of rewards)
{
if(!reward.itemCode) continue;
const rewardsString = [ reward.isBadge ? '0' : '1', reward.itemCode, reward.probability.toString() ];
stringRewards.push(rewardsString.join(','));
}
if(stringRewards.length > 0)
{
setStringParam(stringRewards.join(';'));
setIntParams([ rewardTime, uniqueRewards ? 1 : 0, rewardsLimit, limitationInterval ]);
}
};
useEffect(() =>
{
const readRewards: { isBadge: boolean, itemCode: string, probability: number }[] = [];
if(trigger.stringData.length > 0 && trigger.stringData.includes(';'))
{
const splittedRewards = trigger.stringData.split(';');
for(const rawReward of splittedRewards)
{
const reward = rawReward.split(',');
if(reward.length !== 3) continue;
readRewards.push({ isBadge: reward[0] === '0', itemCode: reward[1], probability: Number(reward[2]) });
}
}
if(readRewards.length === 0) readRewards.push({ isBadge: false, itemCode: '', probability: null });
setRewardTime((trigger.intData.length > 0) ? trigger.intData[0] : 0);
setUniqueRewards((trigger.intData.length > 1) ? (trigger.intData[1] === 1) : false);
setRewardsLimit((trigger.intData.length > 2) ? trigger.intData[2] : 0);
setLimitationInterval((trigger.intData.length > 3) ? trigger.intData[3] : 0);
setLimitEnabled((trigger.intData.length > 3) ? trigger.intData[3] > 0 : false);
setRewards(readRewards);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex items-center gap-1">
<input className="form-check-input" id="limitEnabled" type="checkbox" onChange={ event => setLimitEnabled(event.target.checked) } />
<Text>{ LocalizeText('wiredfurni.params.prizelimit', [ 'amount' ], [ limitEnabled ? rewardsLimit.toString() : '' ]) }</Text>
</div>
{ !limitEnabled &&
<Text center small className="p-1 rounded bg-muted">
Reward limit not set. Make sure rewards are badges or non-tradeable items.
</Text> }
{ limitEnabled &&
<ReactSlider
className={ 'nitro-slider' }
max={ 1000 }
min={ 1 }
value={ rewardsLimit }
onChange={ event => setRewardsLimit(event) } /> }
<hr className="m-0 bg-dark" />
<div className="flex flex-col gap-1">
<Text bold>How often can a user be rewarded?</Text>
<div className="flex gap-1">
<select className="w-full form-select form-select-sm" value={ rewardTime } onChange={ (e) => setRewardTime(Number(e.target.value)) }>
<option value="0">Once</option>
<option value="3">Once every { limitationInterval } minutes</option>
<option value="2">Once every { limitationInterval } hours</option>
<option value="1">Once every { limitationInterval } days</option>
</select>
{ (rewardTime > 0) && <NitroInput type="number" value={ limitationInterval } onChange={ event => setLimitationInterval(Number(event.target.value)) } /> }
</div>
</div>
<hr className="m-0 bg-dark" />
<div className="flex items-center gap-1">
<input checked={ uniqueRewards } className="form-check-input" id="uniqueRewards" type="checkbox" onChange={ (e) => setUniqueRewards(e.target.checked) } />
<Text>Unique rewards</Text>
</div>
<Text center small className="p-1 rounded bg-muted">
If checked each reward will be given once to each user. This will disable the probabilities option.
</Text>
<hr className="m-0 bg-dark" />
<div className="flex items-center justify-between">
<Text bold>Rewards</Text>
<Button variant="success" onClick={ addReward }>
<FaPlus className="fa-icon" />
</Button>
</div>
<div className="flex flex-col gap-1">
{ rewards && rewards.map((reward, index) =>
{
return (
<div key={ index } className="flex gap-1">
<div className="flex items-center gap-1">
<input checked={ reward.isBadge } className="form-check-input" type="checkbox" onChange={ (e) => updateReward(index, e.target.checked, reward.itemCode, reward.probability) } />
<Text small>Badge?</Text>
</div>
<NitroInput placeholder="Item Code" type="text" value={ reward.itemCode } onChange={ e => updateReward(index, reward.isBadge, e.target.value, reward.probability) } />
<NitroInput placeholder="Probability" type="number" value={ reward.probability } onChange={ e => updateReward(index, reward.isBadge, reward.itemCode, Number(e.target.value)) } />
{ (index > 0) &&
<Button variant="danger" onClick={ event => removeReward(index) }>
<FaTrash className="fa-icon" />
</Button> }
</div>
);
}) }
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,67 @@
import { FC, useEffect, useState } from 'react';
import ReactSlider from 'react-slider';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionGiveScoreToPredefinedTeamView: FC<{}> = props =>
{
const [ points, setPoints ] = useState(1);
const [ time, setTime ] = useState(1);
const [ selectedTeam, setSelectedTeam ] = useState(1);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ points, time, selectedTeam ]);
useEffect(() =>
{
if(trigger.intData.length >= 2)
{
setPoints(trigger.intData[0]);
setTime(trigger.intData[1]);
setSelectedTeam(trigger.intData[2]);
}
else
{
setPoints(1);
setTime(1);
setSelectedTeam(1);
}
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.setpoints', [ 'points' ], [ points.toString() ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 100 }
min={ 1 }
value={ points }
onChange={ event => setPoints(event) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.settimesingame', [ 'times' ], [ time.toString() ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 10 }
min={ 1 }
value={ time }
onChange={ event => setTime(event) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.team') }</Text>
{ [ 1, 2, 3, 4 ].map(value =>
{
return (
<div key={ value } className="flex gap-1">
<input checked={ (selectedTeam === value) } className="form-check-input" id={ `selectedTeam${ value }` } name="selectedTeam" type="radio" onChange={ event => setSelectedTeam(value) } />
<Text>{ LocalizeText('wiredfurni.params.team.' + value) }</Text>
</div>
);
}) }
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,52 @@
import { FC, useEffect, useState } from 'react';
import ReactSlider from 'react-slider';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionGiveScoreView: FC<{}> = props =>
{
const [ points, setPoints ] = useState(1);
const [ time, setTime ] = useState(1);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ points, time ]);
useEffect(() =>
{
if(trigger.intData.length >= 2)
{
setPoints(trigger.intData[0]);
setTime(trigger.intData[1]);
}
else
{
setPoints(1);
setTime(1);
}
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.setpoints', [ 'points' ], [ points.toString() ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 100 }
min={ 1 }
value={ points }
onChange={ event => setPoints(event) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.settimesingame', [ 'times' ], [ time.toString() ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 10 }
min={ 1 }
value={ time }
onChange={ event => setTime(event) } />
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,35 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionJoinTeamView: FC<{}> = props =>
{
const [ selectedTeam, setSelectedTeam ] = useState(-1);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ selectedTeam ]);
useEffect(() =>
{
setSelectedTeam((trigger.intData.length > 0) ? trigger.intData[0] : 0);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.team') }</Text>
{ [ 1, 2, 3, 4 ].map(team =>
{
return (
<div key={ team } className="flex gap-1">
<input checked={ (selectedTeam === team) } className="form-check-input" id={ `selectedTeam${ team }` } name="selectedTeam" type="radio" onChange={ event => setSelectedTeam(team) } />
<Text>{ LocalizeText(`wiredfurni.params.team.${ team }`) }</Text>
</div>
);
}) }
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,28 @@
import { FC, useEffect, useState } from 'react';
import { GetConfigurationValue, LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionKickFromRoomView: FC<{}> = props =>
{
const [ message, setMessage ] = useState('');
const { trigger = null, setStringParam = null } = useWired();
const save = () => setStringParam(message);
useEffect(() =>
{
setMessage(trigger.stringData);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.message') }</Text>
<NitroInput maxLength={ GetConfigurationValue<number>('wired.action.kick.from.room.max.length', 100) } type="text" value={ message } onChange={ event => setMessage(event.target.value) } />
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,85 @@
import { WiredActionLayoutCode } from '../../../../api';
import { WiredActionBotChangeFigureView } from './WiredActionBotChangeFigureView';
import { WiredActionBotFollowAvatarView } from './WiredActionBotFollowAvatarView';
import { WiredActionBotGiveHandItemView } from './WiredActionBotGiveHandItemView';
import { WiredActionBotMoveView } from './WiredActionBotMoveView';
import { WiredActionBotTalkToAvatarView } from './WiredActionBotTalkToAvatarView';
import { WiredActionBotTalkView } from './WiredActionBotTalkView';
import { WiredActionBotTeleportView } from './WiredActionBotTeleportView';
import { WiredActionCallAnotherStackView } from './WiredActionCallAnotherStackView';
import { WiredActionChaseView } from './WiredActionChaseView';
import { WiredActionChatView } from './WiredActionChatView';
import { WiredActionFleeView } from './WiredActionFleeView';
import { WiredActionGiveRewardView } from './WiredActionGiveRewardView';
import { WiredActionGiveScoreToPredefinedTeamView } from './WiredActionGiveScoreToPredefinedTeamView';
import { WiredActionGiveScoreView } from './WiredActionGiveScoreView';
import { WiredActionJoinTeamView } from './WiredActionJoinTeamView';
import { WiredActionKickFromRoomView } from './WiredActionKickFromRoomView';
import { WiredActionLeaveTeamView } from './WiredActionLeaveTeamView';
import { WiredActionMoveAndRotateFurniView } from './WiredActionMoveAndRotateFurniView';
import { WiredActionMoveFurniToView } from './WiredActionMoveFurniToView';
import { WiredActionMoveFurniView } from './WiredActionMoveFurniView';
import { WiredActionMuteUserView } from './WiredActionMuteUserView';
import { WiredActionResetView } from './WiredActionResetView';
import { WiredActionSetFurniStateToView } from './WiredActionSetFurniStateToView';
import { WiredActionTeleportView } from './WiredActionTeleportView';
import { WiredActionToggleFurniStateView } from './WiredActionToggleFurniStateView';
export const WiredActionLayoutView = (code: number) =>
{
switch(code)
{
case WiredActionLayoutCode.BOT_CHANGE_FIGURE:
return <WiredActionBotChangeFigureView />;
case WiredActionLayoutCode.BOT_FOLLOW_AVATAR:
return <WiredActionBotFollowAvatarView />;
case WiredActionLayoutCode.BOT_GIVE_HAND_ITEM:
return <WiredActionBotGiveHandItemView />;
case WiredActionLayoutCode.BOT_MOVE:
return <WiredActionBotMoveView />;
case WiredActionLayoutCode.BOT_TALK:
return <WiredActionBotTalkView />;
case WiredActionLayoutCode.BOT_TALK_DIRECT_TO_AVTR:
return <WiredActionBotTalkToAvatarView />;
case WiredActionLayoutCode.BOT_TELEPORT:
return <WiredActionBotTeleportView />;
case WiredActionLayoutCode.CALL_ANOTHER_STACK:
return <WiredActionCallAnotherStackView />;
case WiredActionLayoutCode.CHASE:
return <WiredActionChaseView />;
case WiredActionLayoutCode.CHAT:
return <WiredActionChatView />;
case WiredActionLayoutCode.FLEE:
return <WiredActionFleeView />;
case WiredActionLayoutCode.GIVE_REWARD:
return <WiredActionGiveRewardView />;
case WiredActionLayoutCode.GIVE_SCORE:
return <WiredActionGiveScoreView />;
case WiredActionLayoutCode.GIVE_SCORE_TO_PREDEFINED_TEAM:
return <WiredActionGiveScoreToPredefinedTeamView />;
case WiredActionLayoutCode.JOIN_TEAM:
return <WiredActionJoinTeamView />;
case WiredActionLayoutCode.KICK_FROM_ROOM:
return <WiredActionKickFromRoomView />;
case WiredActionLayoutCode.LEAVE_TEAM:
return <WiredActionLeaveTeamView />;
case WiredActionLayoutCode.MOVE_FURNI:
return <WiredActionMoveFurniView />;
case WiredActionLayoutCode.MOVE_AND_ROTATE_FURNI:
return <WiredActionMoveAndRotateFurniView />;
case WiredActionLayoutCode.MOVE_FURNI_TO:
return <WiredActionMoveFurniToView />;
case WiredActionLayoutCode.MUTE_USER:
return <WiredActionMuteUserView />;
case WiredActionLayoutCode.RESET:
return <WiredActionResetView />;
case WiredActionLayoutCode.SET_FURNI_STATE:
return <WiredActionSetFurniStateToView />;
case WiredActionLayoutCode.TELEPORT:
return <WiredActionTeleportView />;
case WiredActionLayoutCode.TOGGLE_FURNI_STATE:
return <WiredActionToggleFurniStateView />;
}
return null;
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionLeaveTeamView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ null } />;
};
@@ -0,0 +1,82 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
const directionOptions: { value: number, icon: string }[] = [
{
value: 0,
icon: 'ne'
},
{
value: 2,
icon: 'se'
},
{
value: 4,
icon: 'sw'
},
{
value: 6,
icon: 'nw'
}
];
const rotationOptions: number[] = [ 0, 1, 2, 3, 4, 5, 6 ];
export const WiredActionMoveAndRotateFurniView: FC<{}> = props =>
{
const [ movement, setMovement ] = useState(-1);
const [ rotation, setRotation ] = useState(-1);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ movement, rotation ]);
useEffect(() =>
{
if(trigger.intData.length >= 2)
{
setMovement(trigger.intData[0]);
setRotation(trigger.intData[1]);
}
else
{
setMovement(-1);
setRotation(-1);
}
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.startdir') }</Text>
<div className="flex gap-1">
{ directionOptions.map(option =>
{
return (
<div key={ option.value } className="flex items-center gap-1">
<input checked={ (movement === option.value) } className="form-check-input" id={ `movement${ option.value }` } name="movement" type="radio" onChange={ event => setMovement(option.value) } />
<Text>
<i className={ `icon icon-${ option.icon }` } />
</Text>
</div>
);
}) }
</div>
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.turn') }</Text>
{ rotationOptions.map(option =>
{
return (
<div key={ option } className="flex items-center gap-1">
<input checked={ (rotation === option) } className="form-check-input" id={ `rotation${ option }` } name="rotation" type="radio" onChange={ event => setRotation(option) } />
<Text>{ LocalizeText(`wiredfurni.params.turn.${ option }`) }</Text>
</div>
);
}) }
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,76 @@
import { FC, useEffect, useState } from 'react';
import ReactSlider from 'react-slider';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
const directionOptions: { value: number, icon: string }[] = [
{
value: 0,
icon: 'ne'
},
{
value: 2,
icon: 'se'
},
{
value: 4,
icon: 'sw'
},
{
value: 6,
icon: 'nw'
}
];
export const WiredActionMoveFurniToView: FC<{}> = props =>
{
const [ spacing, setSpacing ] = useState(-1);
const [ movement, setMovement ] = useState(-1);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ movement, spacing ]);
useEffect(() =>
{
if(trigger.intData.length >= 2)
{
setSpacing(trigger.intData[1]);
setMovement(trigger.intData[0]);
}
else
{
setSpacing(-1);
setMovement(-1);
}
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_OR_BY_TYPE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.emptytiles', [ 'tiles' ], [ spacing.toString() ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 5 }
min={ 1 }
value={ spacing }
onChange={ event => setSpacing(event) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.startdir') }</Text>
<div className="flex gap-1">
{ directionOptions.map(value =>
{
return (
<div key={ value.value } className="flex items-center gap-1">
<input checked={ (movement === value.value) } className="form-check-input" id={ `movement${ value.value }` } name="movement" type="radio" onChange={ event => setMovement(value.value) } />
<Text><i className={ `icon icon-${ value.icon }` } /></Text>
</div>
);
}) }
</div>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,100 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
const directionOptions: { value: number, icon: string }[] = [
{
value: 4,
icon: 'ne'
},
{
value: 5,
icon: 'se'
},
{
value: 6,
icon: 'sw'
},
{
value: 7,
icon: 'nw'
},
{
value: 2,
icon: 'mv-2'
},
{
value: 3,
icon: 'mv-3'
},
{
value: 1,
icon: 'mv-1'
}
];
const rotationOptions: number[] = [ 0, 1, 2, 3 ];
export const WiredActionMoveFurniView: FC<{}> = props =>
{
const [ movement, setMovement ] = useState(-1);
const [ rotation, setRotation ] = useState(-1);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ movement, rotation ]);
useEffect(() =>
{
if(trigger.intData.length >= 2)
{
setMovement(trigger.intData[0]);
setRotation(trigger.intData[1]);
}
else
{
setMovement(-1);
setRotation(-1);
}
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.movefurni') }</Text>
<div className="flex items-center gap-1">
<input checked={ (movement === 0) } className="form-check-input" id="movement0" name="selectedTeam" type="radio" onChange={ event => setMovement(0) } />
<Text>{ LocalizeText('wiredfurni.params.movefurni.0') }</Text>
</div>
<div className="flex gap-1">
{ directionOptions.map(option =>
{
return (
<div key={ option.value } className="flex items-center gap-1">
<input checked={ (movement === option.value) } className="form-check-input" id={ `movement${ option.value }` } name="movement" type="radio" onChange={ event => setMovement(option.value) } />
<i className={ `nitro.icon icon-${ option.icon }` } />
</div>
);
}) }
<div className="col" />
</div>
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.rotatefurni') }</Text>
{ rotationOptions.map(option =>
{
return (
<div key={ option } className="flex items-center gap-1">
<input checked={ (rotation === option) } className="form-check-input" id={ `rotation${ option }` } name="rotation" type="radio" onChange={ event => setRotation(option) } />
<Text>
{ [ 1, 2 ].includes(option) && <i className={ `nitro-icon icon-rot-${ option }` } /> }
{ LocalizeText(`wiredfurni.params.rotatefurni.${ option }`) }
</Text>
</div>
);
}) }
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,44 @@
import { FC, useEffect, useState } from 'react';
import ReactSlider from 'react-slider';
import { GetConfigurationValue, LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { NitroInput } from '../../../../layout';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionMuteUserView: FC<{}> = props =>
{
const [ time, setTime ] = useState(-1);
const [ message, setMessage ] = useState('');
const { trigger = null, setIntParams = null, setStringParam = null } = useWired();
const save = () =>
{
setIntParams([ time ]);
setStringParam(message);
};
useEffect(() =>
{
setTime((trigger.intData.length > 0) ? trigger.intData[0] : 0);
setMessage(trigger.stringData);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.length.minutes', [ 'minutes' ], [ time.toString() ]) }</Text>
<ReactSlider
className={ 'nitro-slider' }
max={ 10 }
min={ 1 }
value={ time }
onChange={ event => setTime(event) } />
</div>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.message') }</Text>
<NitroInput maxLength={ GetConfigurationValue<number>('wired.action.mute.user.max.length', 100) } type="text" value={ message } onChange={ event => setMessage(event.target.value) } />
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionResetView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_NONE } save={ null } />;
};
@@ -0,0 +1,42 @@
import { FC, useEffect, useState } from 'react';
import { LocalizeText, WiredFurniType } from '../../../../api';
import { Text } from '../../../../common';
import { useWired } from '../../../../hooks';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionSetFurniStateToView: FC<{}> = props =>
{
const [ stateFlag, setStateFlag ] = useState(0);
const [ directionFlag, setDirectionFlag ] = useState(0);
const [ positionFlag, setPositionFlag ] = useState(0);
const { trigger = null, setIntParams = null } = useWired();
const save = () => setIntParams([ stateFlag, directionFlag, positionFlag ]);
useEffect(() =>
{
setStateFlag(trigger.getBoolean(0) ? 1 : 0);
setDirectionFlag(trigger.getBoolean(1) ? 1 : 0);
setPositionFlag(trigger.getBoolean(2) ? 1 : 0);
}, [ trigger ]);
return (
<WiredActionBaseView hasSpecialInput={ true } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID } save={ save }>
<div className="flex flex-col gap-1">
<Text bold>{ LocalizeText('wiredfurni.params.conditions') }</Text>
<div className="flex items-center gap-1">
<input checked={ !!stateFlag } className="form-check-input" id="stateFlag" type="checkbox" onChange={ event => setStateFlag(event.target.checked ? 1 : 0) } />
<Text>{ LocalizeText('wiredfurni.params.condition.state') }</Text>
</div>
<div className="flex items-center gap-1">
<input checked={ !!directionFlag } className="form-check-input" id="directionFlag" type="checkbox" onChange={ event => setDirectionFlag(event.target.checked ? 1 : 0) } />
<Text>{ LocalizeText('wiredfurni.params.condition.direction') }</Text>
</div>
<div className="flex items-center gap-1">
<input checked={ !!positionFlag } className="form-check-input" id="positionFlag" type="checkbox" onChange={ event => setPositionFlag(event.target.checked ? 1 : 0) } />
<Text>{ LocalizeText('wiredfurni.params.condition.position') }</Text>
</div>
</div>
</WiredActionBaseView>
);
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionTeleportView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ null } />;
};
@@ -0,0 +1,8 @@
import { FC } from 'react';
import { WiredFurniType } from '../../../../api';
import { WiredActionBaseView } from './WiredActionBaseView';
export const WiredActionToggleFurniStateView: FC<{}> = props =>
{
return <WiredActionBaseView hasSpecialInput={ false } requiresFurni={ WiredFurniType.STUFF_SELECTION_OPTION_BY_ID_BY_TYPE_OR_FROM_CONTEXT } save={ null } />;
};