plane/apps/app/components/ui/multi-input/index.tsx
sriram veeraghanta 9075f9441c
Refactoring Phase 1 (#199)
* style: added cta at the bottom of sidebar, added missing icons as well, showing dynamic workspace member count on workspace dropdown

* refractor: running parallel request,

made create/edit label function to async function

* fix: sidebar dropdown content going below kanban items

outside click detection in need help dropdown

* refractor: making parallel api calls

fix: create state input comes at bottom, create state input gets on focus automatically, form is getting submitted on enter click

* refactoring file structure and signin page

* style: changed text and added spinner for signing in loading

* refractor: removed unused type

* fix: my issue cta in profile page sending to 404 page

* fix: added new s3 bucket url in next.config.js file

increased image modal height

* packaging UI components

* eslint config

* eslint fixes

* refactoring changes

* build fixes

* minor fixes

* adding todo comments for reference

* refactor: cleared unused imports and re ordered imports

* refactor: removed unused imports

* fix: added workspace argument to useissues hook

* refactor: removed api-routes file, unnecessary constants

* refactor: created helpers folder, removed unnecessary constants

* refactor: new context for issue view

* refactoring issues page

* build fixes

* refactoring

* refactor: create issue modal

* refactor: module ui

* fix: sub-issues mutation

* fix: create more option in create issue modal

* description form debounce issue

* refactor: global component for assignees list

* fix: link module interface

* fix: priority icons and sub-issues count added

* fix: cycle mutation in issue details page

* fix: remove issue from cycle mutation

* fix: create issue modal in home page

* fix: removed unnecessary props

* fix: updated create issue form status

* fix: settings auth breaking

* refactor: issue details page

Co-authored-by: Dakshesh Jain <dakshesh.jain14@gmail.com>
Co-authored-by: Dakshesh Jain <65905942+dakshesh14@users.noreply.github.com>
Co-authored-by: venkatesh-soulpage <venkatesh.marreboyina@soulpageit.com>
Co-authored-by: Aaryan Khandelwal <aaryankhandu123@gmail.com>
Co-authored-by: Anmol Singh Bhatia <anmolsinghbhatia1001@gmail.com>
2023-01-26 23:42:20 +05:30

77 lines
2.3 KiB
TypeScript

// react
import React from "react";
const isEmailValid = (email: string) =>
String(email)
.toLowerCase()
.match(
/^(([^<>()[\]\\.,;:\s@"]+(\.[^<>()[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/
);
const MultiInput = ({ label, name, placeholder, setValue, watch }: any) => {
const handleKeyDown = (e: any) => {
if (e.key !== "Enter") return;
const value = e.target.value;
if (!value.trim()) return;
if (isEmailValid(value) && !watch(name)?.find((item: any) => item.email === value)) {
setValue(name, [...(watch(name) || []), { email: value }]);
e.target.value = "";
}
};
const handleBlur = (e: React.FocusEvent<HTMLInputElement, Element>) => {
const value = e.target.value;
if (!value.trim()) return;
if (isEmailValid(value) && !watch(name)?.find((item: any) => item.email === value)) {
setValue(name, [...(watch(name) || []), { email: value }]);
e.target.value = "";
} else {
e.target.value = "";
}
};
const handleChange = (e: any) => {
const value = e.target.value.trim();
if (!value) return;
if (value.includes(",")) {
const tags = value.split(",");
tags.forEach((tag: string) => {
if (isEmailValid(tag) && !watch(name)?.find((item: any) => item.email === tag)) {
setValue(name, [...(watch(name) || []), { email: tag }]);
}
});
e.target.value = "";
}
};
const removeTag = (index: Number) => {
setValue(
name,
watch(name).filter((_: string, i: any) => i !== index)
);
};
return (
<>
{label && <label className="mb-2 text-gray-500">{label}</label>}
<div className="rounded-md border p-2">
{watch(name)?.map((tag: any, index: number) => (
<button type="button" className="m-1.5 rounded-full bg-slate-300 p-1.5" key={index}>
{tag.email} <span onClick={() => removeTag(index)}>&times;</span>
</button>
))}
<input
onKeyDown={handleKeyDown}
onBlur={handleBlur}
onChange={handleChange}
type="text"
placeholder={placeholder}
className="block w-full rounded-md bg-transparent p-1.5 text-sm focus:outline-none"
/>
</div>
</>
);
};
export default MultiInput;