[WEB-394]: Added a description to project network options (#3717)

* chore: project access specifier description added

* chore: project access specifier description added to the project settings form

* chore: remove fullstop

* fix: dropdown width
This commit is contained in:
Aaryan Khandelwal 2024-02-21 18:26:41 +05:30 committed by GitHub
parent 71901efcdf
commit 487e961df1
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
6 changed files with 65 additions and 37 deletions

View File

@ -122,7 +122,7 @@ const Option = (props: ICustomSelectItemProps) => {
value={value} value={value}
className={({ active }) => className={({ active }) =>
cn( cn(
"cursor-pointer select-none truncate rounded px-1 py-1.5 text-custom-text-200", "cursor-pointer select-none truncate rounded px-1 py-1.5 text-custom-text-200 flex items-center justify-between gap-2",
{ {
"bg-custom-background-80": active, "bg-custom-background-80": active,
}, },
@ -131,10 +131,10 @@ const Option = (props: ICustomSelectItemProps) => {
} }
> >
{({ selected }) => ( {({ selected }) => (
<div className="flex items-center justify-between gap-2"> <>
<div className="flex items-center gap-2">{children}</div> {children}
{selected && <Check className="h-3.5 w-3.5 flex-shrink-0" />} {selected && <Check className="h-3.5 w-3.5 flex-shrink-0" />}
</div> </>
)} )}
</Listbox.Option> </Listbox.Option>
); );

View File

@ -51,10 +51,10 @@ export const DateFilterSelect: React.FC<Props> = ({ title, value, onChange }) =>
> >
{dueDateRange.map((option, index) => ( {dueDateRange.map((option, index) => (
<CustomSelect.Option key={index} value={option.value}> <CustomSelect.Option key={index} value={option.value}>
<> <div className="flex items-center gap-2">
<span>{option.icon}</span> <span>{option.icon}</span>
{title} {option.name} {title} {option.name}
</> </div>
</CustomSelect.Option> </CustomSelect.Option>
))} ))}
</CustomSelect> </CustomSelect>

View File

@ -46,10 +46,10 @@ export const SidebarStatusSelect: React.FC<Props> = ({ control, submitChanges, w
> >
{MODULE_STATUS.map((option) => ( {MODULE_STATUS.map((option) => (
<CustomSelect.Option key={option.value} value={option.value}> <CustomSelect.Option key={option.value} value={option.value}>
<> <div className="flex items-center gap-2">
<span className="h-2 w-2 flex-shrink-0 rounded-full" style={{ backgroundColor: option.color }} /> <span className="h-2 w-2 flex-shrink-0 rounded-full" style={{ backgroundColor: option.color }} />
{option.label} {option.label}
</> </div>
</CustomSelect.Option> </CustomSelect.Option>
))} ))}
</CustomSelect> </CustomSelect>

View File

@ -4,7 +4,7 @@ import { Dialog, Transition } from "@headlessui/react";
import { observer } from "mobx-react-lite"; import { observer } from "mobx-react-lite";
import { X } from "lucide-react"; import { X } from "lucide-react";
// hooks // hooks
import { useEventTracker, useProject, useUser, useWorkspace } from "hooks/store"; import { useEventTracker, useProject, useUser } from "hooks/store";
import useToast from "hooks/use-toast"; import useToast from "hooks/use-toast";
// ui // ui
import { Button, CustomSelect, Input, TextArea } from "@plane/ui"; import { Button, CustomSelect, Input, TextArea } from "@plane/ui";
@ -66,7 +66,6 @@ export const CreateProjectModal: FC<Props> = observer((props) => {
const { const {
membership: { currentWorkspaceRole }, membership: { currentWorkspaceRole },
} = useUser(); } = useUser();
const { currentWorkspace } = useWorkspace();
const { addProjectToFavorites, createProject } = useProject(); const { addProjectToFavorites, createProject } = useProject();
// states // states
const [isChangeInIdentifierRequired, setIsChangeInIdentifierRequired] = useState(true); const [isChangeInIdentifierRequired, setIsChangeInIdentifierRequired] = useState(true);
@ -160,7 +159,7 @@ export const CreateProjectModal: FC<Props> = observer((props) => {
payload: { payload: {
...payload, ...payload,
state: "FAILED", state: "FAILED",
} },
}); });
}); });
}); });
@ -365,13 +364,14 @@ export const CreateProjectModal: FC<Props> = observer((props) => {
tabIndex={4} tabIndex={4}
> >
{NETWORK_CHOICES.map((network) => ( {NETWORK_CHOICES.map((network) => (
<CustomSelect.Option <CustomSelect.Option key={network.key} value={network.key}>
key={network.key} <div className="flex items-start gap-2">
value={network.key} <network.icon className="h-3.5 w-3.5" />
className="flex items-center gap-1" <div className="-mt-1">
> <p>{network.label}</p>
<network.icon className="h-4 w-4" /> <p className="text-xs text-custom-text-400">{network.description}</p>
{network.label} </div>
</div>
</CustomSelect.Option> </CustomSelect.Option>
))} ))}
</CustomSelect> </CustomSelect>

View File

@ -132,7 +132,7 @@ export const ProjectDetailsForm: FC<IProjectDetailsForm> = (props) => {
}, 300); }, 300);
}; };
const currentNetwork = NETWORK_CHOICES.find((n) => n.key === project?.network); const currentNetwork = NETWORK_CHOICES.find((n) => n.key === project?.network);
const selectedNetwork = NETWORK_CHOICES.find((n) => n.key === watch("network"));
return ( return (
<form onSubmit={handleSubmit(onSubmit)}> <form onSubmit={handleSubmit(onSubmit)}>
<div className="relative mt-6 h-44 w-full"> <div className="relative mt-6 h-44 w-full">
@ -269,23 +269,44 @@ export const ProjectDetailsForm: FC<IProjectDetailsForm> = (props) => {
<Controller <Controller
name="network" name="network"
control={control} control={control}
render={({ field: { value, onChange } }) => ( render={({ field: { value, onChange } }) => {
<CustomSelect const selectedNetwork = NETWORK_CHOICES.find((n) => n.key === value);
value={value}
onChange={onChange} return (
label={selectedNetwork?.label ?? "Select network"} <CustomSelect
buttonClassName="!border-custom-border-200 !shadow-none font-medium rounded-md" value={value}
input onChange={onChange}
disabled={!isAdmin} label={
optionsClassName="w-full" <div className="flex items-center gap-1">
> {selectedNetwork ? (
{NETWORK_CHOICES.map((network) => ( <>
<CustomSelect.Option key={network.key} value={network.key}> <selectedNetwork.icon className="h-3.5 w-3.5" />
{network.label} {selectedNetwork.label}
</CustomSelect.Option> </>
))} ) : (
</CustomSelect> <span className="text-custom-text-400">Select network</span>
)} )}
</div>
}
buttonClassName="!border-custom-border-200 !shadow-none font-medium rounded-md"
input
disabled={!isAdmin}
// optionsClassName="w-full"
>
{NETWORK_CHOICES.map((network) => (
<CustomSelect.Option key={network.key} value={network.key}>
<div className="flex items-start gap-2">
<network.icon className="h-3.5 w-3.5" />
<div className="-mt-1">
<p>{network.label}</p>
<p className="text-xs text-custom-text-400">{network.description}</p>
</div>
</div>
</CustomSelect.Option>
))}
</CustomSelect>
);
}}
/> />
</div> </div>
</div> </div>

View File

@ -11,15 +11,22 @@ export enum EUserProjectRoles {
ADMIN = 20, ADMIN = 20,
} }
export const NETWORK_CHOICES: { key: 0 | 2; label: string; icon: LucideIcon }[] = [ export const NETWORK_CHOICES: {
key: 0 | 2;
label: string;
description: string;
icon: LucideIcon;
}[] = [
{ {
key: 0, key: 0,
label: "Private", label: "Private",
description: "Accessible only by invite",
icon: Lock, icon: Lock,
}, },
{ {
key: 2, key: 2,
label: "Public", label: "Public",
description: "Anyone in the workspace can join",
icon: Globe2, icon: Globe2,
}, },
]; ];