Skip to content

Commit 5190749

Browse files
authored
Merge pull request #81 from 1Byte-Software/develop
Update version 1.13.0
2 parents c15d321 + a259164 commit 5190749

14 files changed

Lines changed: 208 additions & 29 deletions

File tree

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,4 @@
11
node_modules
22
dist
3+
*.zip
4+
*.tgz

CHANGELOG.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,13 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
## [1.13.0]
9+
10+
### Added
11+
12+
- Support `requiredResolver` for `Form`, `Form.Item` and `Form.ItemControl` components.
13+
- Support `rdNotificationInstance` with `App` context component.
14+
815
## [1.12.4]
916

1017
### Added

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "1byte-react-design",
3-
"version": "1.12.4",
3+
"version": "1.13.0",
44
"description": "A simple React UI library",
55
"main": "dist/index.js",
66
"module": "dist/index.js",

src/molecules/Form/Form.tsx

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,20 @@ import { FormList } from './FormList';
66
import { FormProvider } from './FormProvider';
77
import { FormStyles } from './styles';
88
import { RdFormComponent, RdFormCompoundedComponent, RdFormProps } from './types';
9+
import { rdFormContext } from './context';
910

1011
export const FormInternal: RdFormComponent = (props: RdFormProps) => {
11-
return <FormStyles {...props} />;
12+
const { requiredResolver, ...formProps } = props;
13+
14+
return (
15+
<rdFormContext.Provider
16+
value={{
17+
requiredResolver,
18+
}}
19+
>
20+
<FormStyles {...formProps} />
21+
</rdFormContext.Provider>
22+
);
1223
};
1324

1425
export const Form = FormInternal as RdFormCompoundedComponent;

src/molecules/Form/FormItem.tsx

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,19 @@
1+
import { useContext } from 'react';
2+
import { rdFormContext } from './context';
13
import { FormItemStyles } from './styles';
24
import { RdFormItemProps } from './types';
35

46
export const FormItem = ({ errorMessage, ...antdProps }: RdFormItemProps) => {
7+
const ctx = useContext(rdFormContext);
8+
9+
const required =
10+
antdProps.required ??
11+
(ctx?.requiredResolver ? ctx.requiredResolver(antdProps.name) : undefined);
12+
513
if (errorMessage) {
614
antdProps.validateStatus = 'error';
715
antdProps.help = errorMessage;
816
}
917

10-
return <FormItemStyles {...antdProps} />;
18+
return <FormItemStyles {...antdProps} required={required} />;
1119
};

src/molecules/Form/FormItemControl.tsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,8 @@ export const FormItemControl = <
117117
return (
118118
<Form.Item
119119
{...props}
120+
name={name as string | undefined} // Required for Antd internal state management and validation
121+
initialValue={field.value} // Initial value for Antd (useful on first render)
120122
validateStatus={fieldState.invalid ? 'error' : undefined}
121123
help={fieldState.error?.message}
122124
>
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
// context.ts
2+
import { createContext } from 'react';
3+
import { RdFormContextValue } from './types';
4+
5+
export const rdFormContext = createContext<RdFormContextValue | null>(null);
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
export interface RdFormContextValue {
2+
requiredResolver?: (name: string) => boolean;
3+
}

src/molecules/Form/types.ts

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,39 @@ export type FormComponentToken = ComponentToken & {};
3131
//#endregion
3232

3333
//#region Define extended types
34-
type FormPropsExtend = {};
34+
type FormPropsExtend = {
35+
/**
36+
* Determines whether a `Form.Item` should be marked as required.
37+
*
38+
* This function receives the field name (the `name` prop of `Form.Item`)
39+
* and should return `true` if the field is required, or `false` otherwise.
40+
*
41+
* This allows consumers to define custom rules for determining required
42+
* status globally at the Form level instead of configuring each Form.Item.
43+
*
44+
* @example
45+
* ```tsx
46+
* <Form
47+
* requiredResolver={(name) => ["username", "password"].includes(name)}
48+
* >
49+
* <Form.Item name="username" label="Username">
50+
* <Input />
51+
* </Form.Item>
52+
*
53+
* <Form.Item name="email" label="Email">
54+
* <Input />
55+
* </Form.Item>
56+
* </Form>
57+
* ```
58+
*
59+
* In the example above, only "username" and "password" will be treated
60+
* as required fields automatically.
61+
*
62+
* @param name - The name of the field being evaluated.
63+
* @returns `true` if the field should be required, otherwise `false`.
64+
*/
65+
requiredResolver?: (name: string) => boolean;
66+
};
3567

3668
type FormItemPropsExtend = {
3769
/**

src/molecules/Notification/Notification.tsx

Lines changed: 30 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3,16 +3,23 @@ import { RdNotificationGlobalConfig, RdNotificationProps, RdNotificationStaticFn
33

44
let notification: RdNotificationProps = {} as RdNotificationProps;
55

6-
const rdNotificationStaticFunc: RdNotificationStaticFn = (rdNotificationArgsProps, type) => {
6+
/**
7+
* This is Internal Function. Do not use in your production.
8+
*/
9+
export const __rdNotificationStaticFunc: RdNotificationStaticFn = (
10+
rdNotificationArgsProps,
11+
notificationInstance
12+
) => {
713
let message = rdNotificationArgsProps.message;
14+
815
if (notification.globalConfigExtend.defaultMessage) {
916
typeof notification.globalConfigExtend.defaultMessage === 'string' &&
1017
(message = notification.globalConfigExtend.defaultMessage);
1118

1219
if (typeof notification.globalConfigExtend.defaultMessage === 'object') {
1320
const { success, info, warning, error } =
1421
notification.globalConfigExtend.defaultMessage;
15-
switch (type) {
22+
switch (rdNotificationArgsProps.type) {
1623
case 'success':
1724
message = success || message;
1825
break;
@@ -35,9 +42,11 @@ const rdNotificationStaticFunc: RdNotificationStaticFn = (rdNotificationArgsProp
3542
...rdNotificationArgsProps,
3643
};
3744

38-
antdNotification.open({
45+
const currentNotification = notificationInstance ?? antdNotification;
46+
47+
currentNotification.open({
3948
...notificationArgsProps,
40-
type,
49+
type: rdNotificationArgsProps.type,
4150
});
4251
};
4352

@@ -54,19 +63,31 @@ notification.destroy = config => {
5463
antdNotification.destroy(config);
5564
};
5665
notification.open = config => {
57-
rdNotificationStaticFunc(config);
66+
__rdNotificationStaticFunc(config);
5867
};
5968
notification.error = config => {
60-
rdNotificationStaticFunc(config, 'error');
69+
__rdNotificationStaticFunc({
70+
...config,
71+
type: 'error',
72+
});
6173
};
6274
notification.info = config => {
63-
rdNotificationStaticFunc(config, 'info');
75+
__rdNotificationStaticFunc({
76+
...config,
77+
type: 'info',
78+
});
6479
};
6580
notification.success = config => {
66-
rdNotificationStaticFunc(config, 'success');
81+
__rdNotificationStaticFunc({
82+
...config,
83+
type: 'success',
84+
});
6785
};
6886
notification.warning = config => {
69-
rdNotificationStaticFunc(config, 'warning');
87+
__rdNotificationStaticFunc({
88+
...config,
89+
type: 'warning',
90+
});
7091
};
7192
notification.useNotification = antdNotification.useNotification;
7293
notification._InternalPanelDoNotUseOrYouWillBeFired =

0 commit comments

Comments
 (0)