Skip to content

Commit

Permalink
update vector input fields
Browse files Browse the repository at this point in the history
  • Loading branch information
daoauth committed Jan 16, 2025
1 parent 6737a03 commit d5b9d52
Show file tree
Hide file tree
Showing 2 changed files with 174 additions and 68 deletions.
228 changes: 161 additions & 67 deletions src/webview/activitybar/src/components/VectorInputFields.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { useState } from 'react';
import { useEffect, useRef, useState } from 'react';
import {
VSCodeButton,
VSCodeTextArea,
VSCodeTextField,
} from '@vscode/webview-ui-toolkit/react';

Expand All @@ -23,7 +24,9 @@ export const VectorInputFields = ({
paramType: string;
update: (params: string[]) => void;
}) => {
const debounceTimeout = useRef<NodeJS.Timeout | null>(null);
const [vectorValues, setVectorValues] = useState<string[]>(['']);
const [hexInput, setHexInput] = useState('');

const handleAddField = () => {
setVectorValues([...vectorValues, '']);
Expand All @@ -41,77 +44,168 @@ export const VectorInputFields = ({
update(newVectorValues);
};

const getChunkSize = (): number => {
switch (paramType) {
case 'U8':
return 2;
case 'U16':
return 4;
case 'U32':
return 8;
case 'U64':
return 16;
case 'U128':
return 32;
case 'U256':
return 64;
default:
return 2;
}
};

const handleInput = (e: any) => {
const rawValue = e.target.value
.replace(/^0x/i, '')
.replace(/[^0-9A-F]/gi, '')
.toUpperCase();
setHexInput(rawValue);

if (debounceTimeout.current) {
clearTimeout(debounceTimeout.current);
}

debounceTimeout.current = setTimeout(() => {
const chunkSize = getChunkSize();
const formatted =
rawValue.match(new RegExp(`.{1,${chunkSize}}`, 'g'))?.join(' ') || '';
setHexInput(formatted);
setVectorValues(
rawValue.match(new RegExp(`.{1,${chunkSize}}`, 'g')) || [],
);
update(rawValue.match(new RegExp(`.{1,${chunkSize}}`, 'g')) || []);
}, 300);
};

useEffect(() => {
return () => {
if (debounceTimeout.current) {
clearTimeout(debounceTimeout.current);
}
};
}, []);

return (
<div style={cardStyles.card}>
<div style={{ flexDirection: 'column', padding: '8px' }}>
{vectorValues.map((value, index) => (
<div
key={index}
style={{
display: 'flex',
marginBottom: '8px',
width: '100%',
}}
>
<VSCodeTextField
style={{ width: '100%' }}
value={value}
placeholder={paramType.replace('vector<', '').slice(0, -1)}
onInput={(e) =>
handleChange(index, (e.target as HTMLInputElement).value)
}
/>
{vectorValues.length > 1 && (
<VSCodeButton
appearance="icon"
onClick={() => handleRemoveField(index)}
style={{ marginLeft: '8px' }}
>
<svg
width="16px"
height="16px"
viewBox="0 0 16 16"
xmlns="http://www.w3.org/2000/svg"
fill="currentColor"
>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M7.116 8l-4.558 4.558.884.884L8 8.884l4.558 4.558.884-.884L8.884 8l4.558-4.558-.884-.884L8 7.116 3.442 2.558l-.884.884L7.116 8z"
/>
</svg>
</VSCodeButton>
)}
</div>
))}
<div
style={{
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
marginTop: '8px',
width: '100%',
}}
>
{error ? (
<span
<>
{paramType === 'vector<u8>' ||
paramType === 'vector<u16>' ||
paramType === 'vector<u32>' ||
paramType === 'vector<u64>' ||
paramType === 'vector<u128>' ||
paramType === 'vector<u256>' ? (
<div style={{ flexDirection: 'column' }}>
<VSCodeTextArea
rows={3}
style={{ width: '100%' }}
placeholder={paramType}
value={hexInput}
onInput={handleInput}
/>
{error && (
<div
style={{
color: 'red',
fontSize: '11px',
wordWrap: 'break-word',
whiteSpace: 'pre-wrap',
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
marginTop: '8px',
width: '100%',
}}
>
{error}
</span>
) : (
<>&nbsp;</>
<span
style={{
color: 'red',
fontSize: '11px',
wordWrap: 'break-word',
whiteSpace: 'pre-wrap',
}}
>
{error}
</span>
</div>
)}
<VSCodeButton style={{ height: '16px' }} onClick={handleAddField}>
<div style={{ fontSize: '8px' }}>Add</div>
</VSCodeButton>
</div>
</div>
</div>
) : (
<div style={cardStyles.card}>
<div style={{ flexDirection: 'column', padding: '8px' }}>
{vectorValues.map((value, index) => (
<div
key={index}
style={{
display: 'flex',
marginBottom: '8px',
width: '100%',
}}
>
<VSCodeTextField
style={{ width: '100%' }}
value={value}
placeholder={paramType.replace('vector<', '').slice(0, -1)}
onInput={(e) =>
handleChange(index, (e.target as HTMLInputElement).value)
}
/>
{vectorValues.length > 1 && (
<VSCodeButton
appearance="icon"
onClick={() => handleRemoveField(index)}
style={{ marginLeft: '8px' }}
>
<svg
width="16px"
height="16px"
viewBox="0 0 16 16"
xmlns="http://www.w3.org/2000/svg"
fill="currentColor"
>
<path
fillRule="evenodd"
clipRule="evenodd"
d="M7.116 8l-4.558 4.558.884.884L8 8.884l4.558 4.558.884-.884L8.884 8l4.558-4.558-.884-.884L8 7.116 3.442 2.558l-.884.884L7.116 8z"
/>
</svg>
</VSCodeButton>
)}
</div>
))}
<div
style={{
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
marginTop: '8px',
width: '100%',
}}
>
{error ? (
<span
style={{
color: 'red',
fontSize: '11px',
wordWrap: 'break-word',
whiteSpace: 'pre-wrap',
}}
>
{error}
</span>
) : (
<>&nbsp;</>
)}
<VSCodeButton style={{ height: '16px' }} onClick={handleAddField}>
<div style={{ fontSize: '8px' }}>Add</div>
</VSCodeButton>
</div>
</div>
</div>
)}
</>
);
};
14 changes: 13 additions & 1 deletion src/webview/activitybar/src/utilities/helper.ts
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,19 @@ export const makeParams = (
const tempType = paramType.replace('vector<', '').slice(0, -1);
const temp = [];
for (const item of value) {
temp.push(makeParams(tempType, item));
switch (tempType) {
case 'u8':
case 'u16':
case 'u32':
case 'u64':
case 'u128':
case 'u256':
temp.push(parseInt(item, 16));
break;
default:
temp.push(makeParams(tempType, item));
break;
}
}
return temp;
}
Expand Down

0 comments on commit d5b9d52

Please sign in to comment.