guesstimate/src/components/editable-text/index.tsx

56 lines
1.9 KiB
TypeScript
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { FunctionalComponent, h, Component, ComponentChild, Fragment } from "preact";
import * as style from "./style.module.css";
import { useState, useEffect } from "preact/hooks";
export interface EditableTextProps {
value: string
class?: string
editIconClass?: string
onChange?: (value: string) => void
render?: (value: string) => ComponentChild
}
const EditableText: FunctionalComponent<EditableTextProps> = ({ onChange, value, render, ...props }) => {
const [ internalValue, setInternalValue ] = useState(value);
const [ editMode, setEditMode ] = useState(false);
useEffect(() => {
if (onChange) onChange(internalValue);
}, [internalValue]);
const onEditIconClick = () => {
setEditMode(true);
};
const onValidateButtonClick = () => {
setEditMode(false);
}
const onValueChange = (evt: Event) => {
const currentTarget = evt.currentTarget as HTMLInputElement;
setInternalValue(currentTarget.value);
};
return (
<div class={`${style.editableText} ${props.class ? props.class : ''}`}>
{
editMode ?
<div class="field has-addons">
<div class="control">
<input class="input is-expanded" type="text" value={internalValue} onChange={onValueChange} />
</div>
<div class="control">
<a class="button" onClick={onValidateButtonClick}></a>
</div>
</div> :
<Fragment>
{ render ? render(internalValue) : <span>{internalValue}</span> }
<i class={`${style.editIcon} icon ${props.editIconClass ? props.editIconClass : ''}`} onClick={onEditIconClick}>🖋</i>
</Fragment>
}
</div>
);
};
export default EditableText;