2020-04-21 09:24:39 +02:00
|
|
|
|
import { FunctionalComponent, h, Component, ComponentChild, Fragment } from "preact";
|
2020-04-22 22:07:52 +02:00
|
|
|
|
import * as style from "./style.module.css";
|
2020-04-21 09:24:39 +02:00
|
|
|
|
import { useState, useEffect } from "preact/hooks";
|
|
|
|
|
|
|
|
|
|
export interface EditableTextProps {
|
|
|
|
|
value: string
|
|
|
|
|
class?: string
|
|
|
|
|
editIconClass?: string
|
|
|
|
|
onChange?: (value: string) => void
|
2020-04-21 20:45:47 +02:00
|
|
|
|
render?: (value: string) => ComponentChild
|
2020-04-21 09:24:39 +02:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const EditableText: FunctionalComponent<EditableTextProps> = ({ onChange, value, render, ...props }) => {
|
|
|
|
|
const [ internalValue, setInternalValue ] = useState(value);
|
|
|
|
|
const [ editMode, setEditMode ] = useState(false);
|
|
|
|
|
|
|
|
|
|
useEffect(() => {
|
2020-05-03 18:34:44 +02:00
|
|
|
|
if (internalValue === value) return;
|
|
|
|
|
if (onChange) onChange(internalValue);
|
2020-04-21 09:24:39 +02:00
|
|
|
|
}, [internalValue]);
|
2020-05-03 18:34:44 +02:00
|
|
|
|
|
|
|
|
|
useEffect(() => {
|
|
|
|
|
setInternalValue(value);
|
|
|
|
|
}, [value])
|
2020-04-21 09:24:39 +02:00
|
|
|
|
|
|
|
|
|
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>
|
2020-04-21 20:45:47 +02:00
|
|
|
|
{ render ? render(internalValue) : <span>{internalValue}</span> }
|
2020-04-21 09:24:39 +02:00
|
|
|
|
<i class={`${style.editIcon} icon ${props.editIconClass ? props.editIconClass : ''}`} onClick={onEditIconClick}>🖋️</i>
|
|
|
|
|
</Fragment>
|
|
|
|
|
}
|
|
|
|
|
</div>
|
|
|
|
|
);
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
export default EditableText;
|