@@ -7,10 +7,11 @@ import { GenericModal } from '@rocket.chat/ui-client';
77import { useToastMessageDispatch , useSetting , useEndpoint , useUser , useTranslation } from '@rocket.chat/ui-contexts' ;
88import type { ChangeEvent , ComponentProps } from 'react' ;
99import { useEffect , useMemo } from 'react' ;
10- import { Controller , useForm , useWatch } from 'react-hook-form' ;
10+ import { Controller , useForm } from 'react-hook-form' ;
1111
1212import UserStatusMenu from '../../../components/UserStatusMenu' ;
1313import { USER_STATUS_TEXT_MAX_LENGTH } from '../../../lib/constants' ;
14+ import { getUserStatusInitialValues } from '../../../lib/getUserInitialStatus' ;
1415import { STATUS_DURATION_OPTIONS } from '../../../lib/statusDurations' ;
1516
1617type EditStatusModalProps = {
@@ -20,9 +21,9 @@ type EditStatusModalProps = {
2021type StatusFormValues = {
2122 statusText : string ;
2223 statusType : UserStatusType ;
23- duration : string ;
24- customDate : string ;
25- customTime : string ;
24+ statusDuration : string ;
25+ statusCustomDate : string ;
26+ statusCustomTime : string ;
2627} ;
2728
2829const EditStatusModal = ( { onClose } : EditStatusModalProps ) => {
@@ -31,54 +32,43 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
3132 const allowUserStatusMessageChange = useSetting ( 'Accounts_AllowUserStatusMessageChange' ) ;
3233 const dispatchToastMessage = useToastMessageDispatch ( ) ;
3334 const [ customStatus , setCustomStatus ] = useLocalStorage < string > ( 'Local_Custom_Status' , '' ) ;
34- const initialStatusText = user ?. statusText ?? customStatus ?? '' ;
35-
36- const initialExpiration = user ?. statusExpiresAt && new Date ( user . statusExpiresAt ) > new Date ( ) ? new Date ( user . statusExpiresAt ) : null ;
37- const initialDate = initialExpiration ?? new Date ( ) ;
3835
3936 const {
4037 control,
4138 handleSubmit,
4239 setValue,
43- formState : { errors } ,
40+ watch,
41+ formState : { errors, isDirty } ,
4442 } = useForm < StatusFormValues > ( {
45- defaultValues : {
46- statusText : initialStatusText ,
47- statusType :
48- user ?. status === UserStatusType . AWAY && user ?. statusDefault === UserStatusType . AWAY
49- ? UserStatusType . AWAY
50- : ( user ?. statusDefault ?? UserStatusType . ONLINE ) ,
51- duration : initialExpiration ? 'custom' : '' ,
52- customDate : initialDate . toLocaleDateString ( 'en-CA' ) ,
53- customTime : initialDate . toTimeString ( ) . slice ( 0 , 5 ) ,
54- } ,
43+ defaultValues : getUserStatusInitialValues ( user , customStatus ) ,
5544 } ) ;
5645
57- const duration = useWatch ( { control, name : 'duration' } ) ;
58- const statusType = useWatch ( { control, name : 'statusType' } ) ;
59- const statusText = useWatch ( { control, name : 'statusText' } ) ;
60-
46+ const { statusDuration, statusType, statusText } = watch ( ) ;
6147 const isExpirationDisabled = statusType === UserStatusType . ONLINE && ! statusText . trim ( ) ;
6248
6349 useEffect ( ( ) => {
6450 if ( isExpirationDisabled ) {
65- setValue ( 'duration ' , '' , { shouldValidate : true } ) ;
51+ setValue ( 'statusDuration ' , '' , { shouldValidate : true } ) ;
6652 }
6753 } , [ isExpirationDisabled , setValue ] ) ;
6854
6955 const isStatusFromCall = user ?. statusSource === 'internal' || user ?. statusSource === 'external' ;
7056
7157 const setUserStatus = useEndpoint ( 'POST' , '/v1/users.setStatus' ) ;
7258
73- const defaultStatusLabel = `${ t ( statusType ) } (${ t ( 'Default' ) } )` ;
74-
7559 const durationOptions : SelectOption [ ] = useMemo ( ( ) => STATUS_DURATION_OPTIONS . map ( ( { value, labelKey } ) => [ value , t ( labelKey ) ] ) , [ t ] ) ;
7660
77- const handleSaveStatus = async ( { statusText, statusType, duration, customDate, customTime } : StatusFormValues ) : Promise < void > => {
78- const expiresAt = STATUS_DURATION_OPTIONS . find ( ( o ) => o . value === duration ) ?. getExpiresAt ?.( {
61+ const handleSaveStatus = async ( {
62+ statusText,
63+ statusType,
64+ statusDuration,
65+ statusCustomDate,
66+ statusCustomTime,
67+ } : StatusFormValues ) : Promise < void > => {
68+ const expiresAt = STATUS_DURATION_OPTIONS . find ( ( o ) => o . value === statusDuration ) ?. getExpiresAt ?.( {
7969 now : new Date ( ) ,
80- customDate,
81- customTime,
70+ customDate : statusCustomDate ,
71+ customTime : statusCustomTime ,
8272 } ) ;
8373 try {
8474 await setUserStatus ( {
@@ -101,7 +91,7 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
10191 title = { t ( 'Status_set_your_status' ) }
10292 onCancel = { onClose }
10393 confirmText = { t ( 'Save' ) }
104- confirmDisabled = { ! ! errors . statusText }
94+ confirmDisabled = { ! isDirty }
10595 wrapperFunction = { ( props : ComponentProps < typeof Box > ) => < Box is = 'form' onSubmit = { handleSubmit ( handleSaveStatus ) } { ...props } /> }
10696 >
10797 < FieldGroup >
@@ -123,7 +113,7 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
123113 error = { errors . statusText ?. message }
124114 disabled = { ! allowUserStatusMessageChange }
125115 flexGrow = { 1 }
126- placeholder = { defaultStatusLabel }
116+ placeholder = { t ( statusType ) }
127117 startAddon = {
128118 < Controller
129119 control = { control }
@@ -143,17 +133,17 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
143133 < FieldRow >
144134 < Controller
145135 control = { control }
146- name = 'duration '
136+ name = 'statusDuration '
147137 rules = { {
148- deps : [ 'customDate ' , 'customTime ' ] ,
149- validate : ( value , { customDate , customTime } ) => {
138+ deps : [ 'statusCustomDate ' , 'statusCustomTime ' ] ,
139+ validate : ( value , { statusCustomDate , statusCustomTime } ) => {
150140 if ( value !== 'custom' ) {
151141 return true ;
152142 }
153143 const expiresAt = STATUS_DURATION_OPTIONS . find ( ( o ) => o . value === value ) ?. getExpiresAt ?.( {
154144 now : new Date ( ) ,
155- customDate,
156- customTime,
145+ customDate : statusCustomDate ,
146+ customTime : statusCustomTime ,
157147 } ) ;
158148 if ( ! expiresAt ) {
159149 return t ( 'Status_choose_date_and_time' ) ;
@@ -174,12 +164,12 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
174164 ) }
175165 />
176166 </ FieldRow >
177- { duration === 'custom' && (
167+ { statusDuration === 'custom' && (
178168 < Box display = 'flex' mi = 'neg-x4' mbs = { 8 } >
179169 < Margins inline = { 4 } >
180170 < Controller
181171 control = { control }
182- name = 'customDate '
172+ name = 'statusCustomDate '
183173 render = { ( { field : { value, onChange } } ) => (
184174 < InputBox
185175 aria-label = { t ( 'Status_expiration_date' ) }
@@ -193,7 +183,7 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
193183 />
194184 < Controller
195185 control = { control }
196- name = 'customTime '
186+ name = 'statusCustomTime '
197187 render = { ( { field : { value, onChange } } ) => (
198188 < InputBox
199189 aria-label = { t ( 'Status_expiration_time' ) }
@@ -207,7 +197,7 @@ const EditStatusModal = ({ onClose }: EditStatusModalProps) => {
207197 </ Margins >
208198 </ Box >
209199 ) }
210- { errors . duration && < FieldError > { errors . duration . message } </ FieldError > }
200+ { errors . statusDuration && < FieldError > { errors . statusDuration . message } </ FieldError > }
211201 < FieldHint > { t ( isStatusFromCall ? 'Status_new_status_warning_after_call' : 'Status_new_status_warning' ) } </ FieldHint >
212202 </ Field >
213203 </ FieldGroup >
0 commit comments