@ainias42/react-bootstrap-mobile 0.1.15 → 0.1.17

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (81) hide show
  1. package/bin/updateCopies.js +9 -5
  2. package/bootstrapReactMobile.ts +13 -2
  3. package/dist/bootstrapReactMobile.d.ts +13 -2
  4. package/dist/bootstrapReactMobile.js +992 -395
  5. package/dist/bootstrapReactMobile.js.map +1 -1
  6. package/dist/src/Components/Clickable/Clickable.d.ts +7 -3
  7. package/dist/src/Components/Dialog/DialogBackground.d.ts +4 -5
  8. package/dist/src/Components/Dialog/DialogContainer.d.ts +7 -3
  9. package/dist/src/Components/DragAndDrop/DragItem.d.ts +1 -1
  10. package/dist/src/Components/Flavor.d.ts +4 -0
  11. package/dist/src/Components/FormElements/Button/Button.d.ts +8 -4
  12. package/dist/src/Components/FormElements/Button/ButtonType.d.ts +4 -0
  13. package/dist/src/Components/FormElements/Input/FileInput/FileInput.d.ts +12 -0
  14. package/dist/src/Components/FormElements/Input/FileInput/FileType.d.ts +7 -0
  15. package/dist/src/Components/FormElements/Input/FileInput/MultipleFileInput.d.ts +17 -0
  16. package/dist/src/Components/FormElements/Select/Select.d.ts +2 -1
  17. package/dist/src/Components/FormElements/Switch/Switch.d.ts +4 -4
  18. package/dist/src/Components/Hooks/useMousePosition.d.ts +5 -0
  19. package/dist/src/Components/Hooks/useWindowDimensions.d.ts +4 -0
  20. package/dist/src/Components/Icon/Icon.d.ts +2 -3
  21. package/dist/src/Components/Layout/Grid/Grid.d.ts +2 -1
  22. package/dist/src/Components/Layout/Grid/GridItem.d.ts +4 -1
  23. package/dist/src/Components/Menu/HoverMenu.d.ts +9 -0
  24. package/dist/src/Components/Menu/Menu.d.ts +16 -7
  25. package/dist/src/Components/Menu/MenuCloseContext.d.ts +3 -0
  26. package/dist/src/Components/Menu/MenuDivider.d.ts +2 -0
  27. package/dist/src/Components/Menu/MenuItem.d.ts +23 -0
  28. package/dist/src/Components/Menu/Submenu.d.ts +12 -0
  29. package/dist/src/Components/Menu/useMenu.d.ts +1 -1
  30. package/dist/src/Components/RbmComponentProps.d.ts +4 -0
  31. package/dist/src/Components/Text/Text.d.ts +1 -0
  32. package/dist/src/ListRow/ListRow.d.ts +1 -0
  33. package/package.json +8 -7
  34. package/src/Components/Clickable/Clickable.tsx +135 -19
  35. package/src/Components/Dialog/DialogBackground.tsx +5 -8
  36. package/src/Components/Dialog/DialogContainer.tsx +12 -8
  37. package/src/Components/Dialog/DialogContext.ts +1 -2
  38. package/src/Components/Dialog/dialogBackground.scss +5 -1
  39. package/src/Components/DragAndDrop/DragItem.tsx +7 -7
  40. package/src/Components/DragAndDrop/DropArea.tsx +2 -1
  41. package/src/Components/Flavor.ts +4 -0
  42. package/src/Components/FormElements/Button/Button.tsx +31 -13
  43. package/src/Components/FormElements/Button/ButtonType.ts +4 -0
  44. package/src/Components/FormElements/Button/button.scss +22 -5
  45. package/src/Components/FormElements/Input/FileInput/FileInput.tsx +55 -0
  46. package/src/Components/FormElements/Input/FileInput/FileType.ts +1 -0
  47. package/src/Components/FormElements/Input/FileInput/MultipleFileInput.tsx +281 -0
  48. package/src/Components/FormElements/{ImageInput/imageInput.scss → Input/FileInput/fileInput.scss} +37 -7
  49. package/src/Components/FormElements/Input/input.scss +1 -1
  50. package/src/Components/FormElements/SearchSelectInput/SearchSelectInput.tsx +2 -2
  51. package/src/Components/FormElements/SearchSelectInput/seachSelectInput.scss +1 -1
  52. package/src/Components/FormElements/Select/Select.tsx +3 -2
  53. package/src/Components/FormElements/Select/select.scss +5 -0
  54. package/src/Components/FormElements/Switch/Switch.tsx +9 -8
  55. package/src/Components/FormElements/Switch/switch.scss +1 -0
  56. package/src/Components/Hooks/useMousePosition.ts +13 -0
  57. package/src/Components/Hooks/useWindowDimensions.ts +17 -0
  58. package/src/Components/Icon/Icon.tsx +18 -14
  59. package/src/Components/Icon/icon.scss +9 -0
  60. package/src/Components/Layout/Grid/Grid.tsx +3 -2
  61. package/src/Components/Layout/Grid/GridItem.tsx +16 -1
  62. package/src/Components/Layout/Grid/grid.scss +113 -36
  63. package/src/Components/Menu/HoverMenu.tsx +82 -0
  64. package/src/Components/Menu/Menu.tsx +101 -47
  65. package/src/Components/Menu/MenuCloseContext.ts +10 -0
  66. package/src/Components/Menu/MenuDivider.tsx +22 -0
  67. package/src/Components/Menu/MenuItem.tsx +95 -0
  68. package/src/Components/Menu/Submenu.tsx +101 -0
  69. package/src/Components/Menu/menu.scss +99 -10
  70. package/src/Components/Menu/useMenu.ts +1 -1
  71. package/src/Components/RbmComponentProps.ts +6 -0
  72. package/src/Components/Text/Text.tsx +1 -0
  73. package/src/Components/Text/text.scss +13 -5
  74. package/src/ListRow/ListRow.tsx +20 -0
  75. package/src/WrongChildError.ts +0 -2
  76. package/src/scss/_colors.scss +1 -1
  77. package/src/scss/_flavorMixin.scss +10 -0
  78. package/dist/src/Components/FormElements/ImageInput/ImageInput.d.ts +0 -18
  79. package/dist/src/Components/FormElements/ImageInput/MultipleFileInput.d.ts +0 -21
  80. package/src/Components/FormElements/ImageInput/ImageInput.tsx +0 -98
  81. package/src/Components/FormElements/ImageInput/MultipleFileInput.tsx +0 -240
@@ -1,16 +1,19 @@
1
1
  import * as React from 'react';
2
- import { RbmComponentProps } from '../RbmComponentProps';
3
- import { OptionalListener, useListener } from '../Hooks/useListener';
2
+ import {RbmComponentProps} from '../RbmComponentProps';
3
+ import {OptionalListener, useListener} from '../Hooks/useListener';
4
4
 
5
5
  import styles from './clickable.scss';
6
6
  import classNames from 'classnames';
7
- import { useCallback, MouseEvent, ForwardedRef } from 'react';
8
- import { withForwardRef } from '../../helper/withForwardRef';
7
+ import {useCallback, MouseEvent as ReactMouseEvent, ForwardedRef, useEffect, MouseEvent} from 'react';
8
+ import {withForwardRef} from '../../helper/withForwardRef';
9
+ import {useComposedRef} from "../Hooks/useComposedRef";
9
10
 
10
11
  type OnClickListener<Data> = OptionalListener<'onClick', Data>;
11
12
  type OnMouseDownListener<Data> = OptionalListener<'onMouseDown', Data>;
12
13
  type OnMouseUpListener<Data> = OptionalListener<'onMouseUp', Data>;
13
14
  type OnMouseMoveListener<Data> = OptionalListener<'onMouseMove', Data>;
15
+ type OnDropListener<Data> = OptionalListener<'onDrop', Data>;
16
+ type OnDragOverListener<Data> = OptionalListener<'onDragOver', Data>;
14
17
 
15
18
  export type ClickableProps<
16
19
  OnClickData,
@@ -18,6 +21,11 @@ export type ClickableProps<
18
21
  OnMouseMoveData,
19
22
  OnMouseUpData,
20
23
  OnClickCaptureData,
24
+ OnDropData,
25
+ OnDragOverData,
26
+ OnMouseEnterData,
27
+ OnMouseLeaveData,
28
+ OnDoubleClickData,
21
29
  HrefType extends string | undefined
22
30
  > = RbmComponentProps<
23
31
  {
@@ -25,11 +33,17 @@ export type ClickableProps<
25
33
  href?: HrefType;
26
34
  preventDefault?: boolean;
27
35
  stopPropagation?: boolean;
36
+ useReactOnMouseLeave?: boolean;
28
37
  } & OnClickListener<OnClickData> &
29
- OnMouseDownListener<OnMouseDownData> &
30
- OnMouseMoveListener<OnMouseMoveData> &
31
- OnMouseUpListener<OnMouseUpData> &
32
- OptionalListener<'onClickCapture', OnClickCaptureData>
38
+ OnMouseDownListener<OnMouseDownData> &
39
+ OnMouseMoveListener<OnMouseMoveData> &
40
+ OnMouseUpListener<OnMouseUpData> &
41
+ OnDropListener<OnDropData> &
42
+ OnDragOverListener<OnDragOverData> &
43
+ OptionalListener<'onClickCapture', OnClickCaptureData> &
44
+ OptionalListener<'onMouseEnter', OnMouseEnterData> &
45
+ OptionalListener<'onMouseLeave', OnMouseLeaveData, MouseEvent|ReactMouseEvent> &
46
+ OptionalListener<'onDoubleClick', OnDoubleClickData>
33
47
  >;
34
48
 
35
49
  function Clickable<
@@ -38,6 +52,11 @@ function Clickable<
38
52
  OnMouseMoveData,
39
53
  OnMouseUpData,
40
54
  OnClickCaptureData,
55
+ OnDropData,
56
+ OnDragOverData,
57
+ OnMouseEnterData,
58
+ OnMouseLeaveData,
59
+ OnDoubleClickData,
41
60
  HrefType extends string | undefined
42
61
  >(
43
62
  {
@@ -48,8 +67,9 @@ function Clickable<
48
67
  interactable = true,
49
68
  preventDefault = false,
50
69
  stopPropagation = true,
70
+ useReactOnMouseLeave = false,
51
71
  ...clickData
52
- }: ClickableProps<OnClickData, OnMouseDownData, OnMouseMoveData, OnMouseUpData, OnClickCaptureData, HrefType>,
72
+ }: ClickableProps<OnClickData, OnMouseDownData, OnMouseMoveData, OnMouseUpData, OnClickCaptureData, OnDropData, OnDragOverData,OnMouseEnterData, OnMouseLeaveData, OnDoubleClickData, HrefType>,
53
73
  ref: ForwardedRef<HrefType extends string ? HTMLAnchorElement : HTMLSpanElement>
54
74
  ) {
55
75
  // Variables
@@ -57,11 +77,12 @@ function Clickable<
57
77
  // States
58
78
 
59
79
  // Refs
80
+ const clickableRef = useComposedRef(ref);
60
81
 
61
82
  // Callbacks
62
83
  const onClickInner = useListener<'onClick', OnClickData>('onClick', clickData);
63
84
  const realOnClick = useCallback(
64
- (e: MouseEvent) => {
85
+ (e: ReactMouseEvent) => {
65
86
  if (clickData.onClick) {
66
87
  if (stopPropagation) {
67
88
  e.stopPropagation();
@@ -77,7 +98,7 @@ function Clickable<
77
98
 
78
99
  const onMouseDownInner = useListener<'onMouseDown', OnMouseDownData>('onMouseDown', clickData);
79
100
  const realOnMouseDown = useCallback(
80
- (e: MouseEvent) => {
101
+ (e: ReactMouseEvent) => {
81
102
  if (clickData.onMouseDown) {
82
103
  if (stopPropagation) {
83
104
  e.stopPropagation();
@@ -93,7 +114,7 @@ function Clickable<
93
114
 
94
115
  const onMouseMoveInner = useListener<'onMouseMove', OnMouseMoveData>('onMouseMove', clickData);
95
116
  const realOnMouseMove = useCallback(
96
- (e: MouseEvent) => {
117
+ (e: ReactMouseEvent) => {
97
118
  if (clickData.onMouseMove) {
98
119
  if (stopPropagation) {
99
120
  e.stopPropagation();
@@ -109,7 +130,7 @@ function Clickable<
109
130
 
110
131
  const onMouseUpInner = useListener<'onMouseUp', OnMouseUpData>('onMouseUp', clickData);
111
132
  const realOnMouseUp = useCallback(
112
- (e: MouseEvent) => {
133
+ (e: ReactMouseEvent) => {
113
134
  if (clickData.onMouseUp) {
114
135
  if (stopPropagation) {
115
136
  e.stopPropagation();
@@ -124,8 +145,8 @@ function Clickable<
124
145
  );
125
146
 
126
147
  const onClickCaptureInner = useListener<'onClickCapture', OnClickCaptureData>('onClickCapture', clickData);
127
- const realOnClickCaptureInner = useCallback(
128
- (e: MouseEvent) => {
148
+ const realOnClickCapture = useCallback(
149
+ (e: ReactMouseEvent) => {
129
150
  if (clickData.onClickCapture) {
130
151
  if (stopPropagation) {
131
152
  e.stopPropagation();
@@ -139,7 +160,97 @@ function Clickable<
139
160
  [clickData.onClickCapture, onClickCaptureInner, preventDefault, stopPropagation]
140
161
  );
141
162
 
163
+ const onDropInner = useListener<'onDrop', OnDropData>('onDrop', clickData);
164
+ const realOnDrop = useCallback(
165
+ (e: ReactMouseEvent) => {
166
+ if (clickData.onDrop) {
167
+ if (stopPropagation) {
168
+ e.stopPropagation();
169
+ }
170
+ if (preventDefault) {
171
+ e.preventDefault();
172
+ }
173
+ onDropInner(e);
174
+ }
175
+ },
176
+ [clickData.onDrop, onDropInner, preventDefault, stopPropagation]
177
+ );
178
+
179
+ const onDragOver = useListener<'onDragOver', OnDragOverData>('onDragOver', clickData);
180
+ const realOnDragOver = useCallback(
181
+ (e: ReactMouseEvent) => {
182
+ if (clickData.onDragOver) {
183
+ if (stopPropagation) {
184
+ e.stopPropagation();
185
+ }
186
+ if (preventDefault) {
187
+ e.preventDefault();
188
+ }
189
+ onDragOver(e);
190
+ }
191
+ },
192
+ [clickData.onDragOver, onDragOver, preventDefault, stopPropagation]
193
+ );
194
+
195
+ const onMouseEnter = useListener<'onMouseEnter', OnMouseEnterData>('onMouseEnter', clickData);
196
+ const realOnMouseEnter = useCallback(
197
+ (e: ReactMouseEvent) => {
198
+ if (clickData.onMouseEnter) {
199
+ if (stopPropagation) {
200
+ e.stopPropagation();
201
+ }
202
+ if (preventDefault) {
203
+ e.preventDefault();
204
+ }
205
+ onMouseEnter(e);
206
+ }
207
+ },
208
+ [clickData.onMouseEnter, onMouseEnter, preventDefault, stopPropagation]
209
+ );
210
+
211
+ const onMouseLeave = useListener<'onMouseLeave', OnMouseLeaveData>('onMouseLeave', clickData);
212
+ const realOnMouseLeave = useCallback(
213
+ (e: Event|ReactMouseEvent) => {
214
+ if (clickData.onMouseLeave) {
215
+ if (stopPropagation) {
216
+ e.stopPropagation();
217
+ }
218
+ if (preventDefault) {
219
+ e.preventDefault();
220
+ }
221
+ onMouseLeave(e);
222
+ }
223
+ },
224
+ [clickData.onMouseLeave, onMouseLeave, preventDefault, stopPropagation]
225
+ );
226
+
227
+ const onDoubleClick = useListener<'onDoubleClick', OnDoubleClickData>('onDoubleClick', clickData);
228
+ const realOnDoubleClick = useCallback(
229
+ (e: Event|ReactMouseEvent) => {
230
+ if (clickData.onDoubleClick) {
231
+ if (stopPropagation) {
232
+ e.stopPropagation();
233
+ }
234
+ if (preventDefault) {
235
+ e.preventDefault();
236
+ }
237
+ onDoubleClick(e);
238
+ }
239
+ },
240
+ [clickData.onDoubleClick, onDoubleClick, preventDefault, stopPropagation]
241
+ );
242
+
142
243
  // Effects
244
+ useEffect(() => {
245
+ if (useReactOnMouseLeave) {
246
+ return undefined;
247
+ }
248
+ const elem = clickableRef.current;
249
+ elem?.addEventListener('mouseleave', realOnMouseLeave);
250
+ return () => {
251
+ elem?.removeEventListener('mouseleave', realOnMouseLeave);
252
+ };
253
+ }, [useReactOnMouseLeave, clickableRef, realOnMouseLeave]);
143
254
 
144
255
  // Other
145
256
 
@@ -153,22 +264,27 @@ function Clickable<
153
264
  onMouseDown: realOnMouseDown,
154
265
  onMouseMove: realOnMouseMove,
155
266
  onMouseUp: realOnMouseUp,
156
- onClickCapture: realOnClickCaptureInner,
267
+ onClickCapture: realOnClickCapture,
268
+ onDrop: realOnDrop,
269
+ onDragOver: realOnDragOver,
270
+ onMouseEnter: realOnMouseEnter,
271
+ onMouseLeave: useReactOnMouseLeave ? realOnMouseLeave : undefined,
272
+ onDoubleClick: realOnDoubleClick,
157
273
  tabIndex: interactable ? 0 : undefined,
158
274
  };
159
275
  if (typeof href === 'string') {
160
276
  return (
161
- <a {...props} href={href} ref={ref as ForwardedRef<HTMLAnchorElement>}>
277
+ <a {...props} href={href} ref={clickableRef as ForwardedRef<HTMLAnchorElement>}>
162
278
  {children}
163
279
  </a>
164
280
  );
165
281
  }
166
282
  return (
167
- <span {...props} ref={ref as ForwardedRef<HTMLSpanElement>}>
283
+ <span {...props} ref={clickableRef as ForwardedRef<HTMLSpanElement>}>
168
284
  {children}
169
285
  </span>
170
286
  );
171
287
  }
172
288
 
173
289
  const ClickableMemo = withForwardRef(Clickable, styles);
174
- export { ClickableMemo as Clickable };
290
+ export {ClickableMemo as Clickable};
@@ -2,14 +2,14 @@ import * as React from 'react';
2
2
  import { withMemo } from '../../helper/withMemo';
3
3
  import { RbmComponentProps } from '../RbmComponentProps';
4
4
  import { Block } from '../Layout/Block';
5
- import { EmptyProps } from '../../helper/EmptyProps';
6
5
 
7
6
  import styles from './dialogBackground.scss';
8
7
  import classNames from 'classnames';
8
+ import {Heading} from "../Text/Heading";
9
9
 
10
- export type DialogBackgroundProps = RbmComponentProps<EmptyProps>;
10
+ export type DialogBackgroundProps = RbmComponentProps<{title?: string}>;
11
11
 
12
- function DialogBackground({ children, className, style }: DialogBackgroundProps) {
12
+ export const DialogBackground = withMemo(function DialogBackground({ children, className, style, title }: DialogBackgroundProps) {
13
13
  // Variables
14
14
 
15
15
  // Refs
@@ -28,11 +28,8 @@ function DialogBackground({ children, className, style }: DialogBackgroundProps)
28
28
 
29
29
  return (
30
30
  <Block __allowChildren="all" className={classNames(styles.dialogBackground, className)} style={style}>
31
+ {!!title && <Heading className={styles.title}>{title}</Heading>}
31
32
  {children}
32
33
  </Block>
33
34
  );
34
- }
35
-
36
- // Need DialogBackgroundMemo for autocompletion of phpstorm
37
- const DialogBackgroundMemo = withMemo(DialogBackground, styles);
38
- export { DialogBackgroundMemo as DialogBackground };
35
+ }, styles);
@@ -1,10 +1,10 @@
1
1
  import * as React from 'react';
2
- import { withMemo } from '../../helper/withMemo';
3
- import { ComponentType, PropsWithChildren, useCallback, useState } from 'react';
2
+ import {ComponentType, ForwardedRef, PropsWithChildren, useCallback, useImperativeHandle, useState} from 'react';
4
3
  import { PromiseWithHandlers } from '@ainias42/js-helper';
5
4
  import { DialogProvider, ShowDialog } from './DialogContext';
6
5
  import { Dialog } from './Dialog';
7
6
  import { EmptyProps } from '../../helper/EmptyProps';
7
+ import {withForwardRef} from "../../helper/withForwardRef";
8
8
 
9
9
  export type DialogContainerProps = PropsWithChildren<EmptyProps>;
10
10
 
@@ -15,7 +15,11 @@ type DialogData = {
15
15
  resultPromise: PromiseWithHandlers<any>;
16
16
  };
17
17
 
18
- function DialogContainer({ children }: DialogContainerProps) {
18
+ export type DialogContainerRef = {
19
+ showDialog: ShowDialog;
20
+ }
21
+
22
+ export const DialogContainer = withForwardRef(function DialogContainer({ children }: DialogContainerProps, ref: ForwardedRef<DialogContainerRef>) {
19
23
  // Variables
20
24
  const [dialogs, setDialogs] = useState<DialogData[]>([]);
21
25
  const [, setLastId] = useState(0);
@@ -52,6 +56,10 @@ function DialogContainer({ children }: DialogContainerProps) {
52
56
  }, []);
53
57
 
54
58
  // Effects
59
+ useImperativeHandle(ref, () => ({
60
+ showDialog
61
+ }), [showDialog]);
62
+
55
63
 
56
64
  // Other
57
65
 
@@ -70,8 +78,4 @@ function DialogContainer({ children }: DialogContainerProps) {
70
78
  })}
71
79
  </DialogProvider>
72
80
  );
73
- }
74
-
75
- // Need DialogContainerMemo for autocompletion of phpstorm
76
- const DialogContainerMemo = withMemo(DialogContainer);
77
- export { DialogContainerMemo as DialogContainer };
81
+ });
@@ -16,6 +16,5 @@ const DialogContext = React.createContext<ShowDialog>(() => Promise.reject());
16
16
  export const DialogProvider = DialogContext.Provider;
17
17
 
18
18
  export function useDialog() {
19
- const showDialog = useContext(DialogContext);
20
- return showDialog as ShowDialog;
19
+ return useContext(DialogContext);
21
20
  }
@@ -1,4 +1,8 @@
1
1
  .dialogBackground {
2
2
  background-color: white;
3
- padding: 0.3rem;
3
+ padding: 0.5rem;
4
+
5
+ .title {
6
+ margin: 0 0 0.8rem;
7
+ }
4
8
  }
@@ -1,11 +1,11 @@
1
1
  import * as React from 'react';
2
- import { withMemo } from '../../helper/withMemo';
3
- import { RbmComponentProps, WithNoStringAndChildrenProps } from '../RbmComponentProps';
4
- import { Draggable, DraggableProps } from 'react-beautiful-dnd';
2
+ import {withMemo} from '../../helper/withMemo';
3
+ import {RbmComponentProps, WithNoStringAndChildrenProps} from '../RbmComponentProps';
4
+ import {Draggable, DraggableProps} from 'react-beautiful-dnd';
5
5
 
6
6
  export type DragItemProps = RbmComponentProps<Omit<DraggableProps, 'children'>, WithNoStringAndChildrenProps>;
7
7
 
8
- function DragItem({ children, ...dragProps }: DragItemProps) {
8
+ function DragItem({children, className, ...dragProps}: DragItemProps) {
9
9
  // Variables
10
10
 
11
11
  // Refs
@@ -24,8 +24,8 @@ function DragItem({ children, ...dragProps }: DragItemProps) {
24
24
 
25
25
  return (
26
26
  <Draggable {...dragProps}>
27
- {({ innerRef, dragHandleProps, draggableProps }) => (
28
- <div {...draggableProps} {...dragHandleProps} ref={innerRef}>
27
+ {({innerRef, dragHandleProps, draggableProps}) => (
28
+ <div className={className} {...draggableProps} {...dragHandleProps} ref={innerRef}>
29
29
  {children}
30
30
  </div>
31
31
  )}
@@ -35,4 +35,4 @@ function DragItem({ children, ...dragProps }: DragItemProps) {
35
35
 
36
36
  // Need DragItemMemo for autocompletion of phpstorm
37
37
  const DragItemMemo = withMemo(DragItem);
38
- export { DragItemMemo as DragItem };
38
+ export {DragItemMemo as DragItem};
@@ -29,9 +29,10 @@ function DropArea({ children, style, className, ...dropProps }: DropAreaProps) {
29
29
 
30
30
  return (
31
31
  <Droppable {...dropProps}>
32
- {({ innerRef, droppableProps }) => (
32
+ {({ innerRef, droppableProps, placeholder }) => (
33
33
  <div {...droppableProps} ref={innerRef} style={style} className={className}>
34
34
  {children}
35
+ {placeholder}
35
36
  </div>
36
37
  )}
37
38
  </Droppable>
@@ -0,0 +1,4 @@
1
+ export enum Flavor {
2
+ Accent = "flavor-accent",
3
+ Basic = "flavor-basic",
4
+ }
@@ -1,25 +1,43 @@
1
1
  import * as React from 'react';
2
- import { Override } from '@ainias42/js-helper';
3
- import { OptionalListener, useListener } from '../../Hooks/useListener';
2
+ import {Override} from '@ainias42/js-helper';
3
+ import {OptionalListener, useListener, useListenerWithExtractedProps} from '../../Hooks/useListener';
4
4
 
5
5
  import styles from './button.scss';
6
6
  import classNames from 'classnames';
7
- import { withMemo } from '../../../helper/withMemo';
8
- import { HTMLAttributes } from 'react';
9
- import { RbmComponentProps } from '../../RbmComponentProps';
7
+ import {withMemo} from '../../../helper/withMemo';
8
+ import {HTMLAttributes} from 'react';
9
+ import {RbmComponentProps} from '../../RbmComponentProps';
10
+ import {ButtonType} from "./ButtonType";
11
+ import {Flavor} from "../../Flavor";
10
12
 
11
13
  export type ButtonProps<ClickData> = RbmComponentProps<
12
- Override<HTMLAttributes<HTMLButtonElement>, OptionalListener<'onClick', ClickData>>
14
+ Override<HTMLAttributes<HTMLButtonElement>, {
15
+ type?: ButtonType,
16
+ disabled?: boolean;
17
+ flavor?: Flavor
18
+ } & OptionalListener<'onClick', ClickData>>
13
19
  >;
14
20
 
15
- function Button<ClickData>({ children, className, ...props }: ButtonProps<ClickData>) {
16
- const onClick = useListener<'onClick', ClickData>('onClick', props);
21
+ export const Button = withMemo(function Button<ClickData>({
22
+ children,
23
+ className,
24
+ disabled,
25
+ flavor = Flavor.Accent,
26
+ type = ButtonType.Primary,
27
+ ...props
28
+ }: ButtonProps<ClickData>) {
29
+ const [onClick, otherProps] = useListenerWithExtractedProps<'onClick', ClickData>('onClick', props);
30
+
31
+ const classes = {
32
+ [styles.primary]: type === ButtonType.Primary,
33
+ [styles.secondary]: type === ButtonType.Secondary,
34
+ [styles.disabled]: disabled,
35
+ };
36
+
17
37
  return (
18
- <button {...props} type="button" onClick={onClick} className={classNames(styles.button, className)}>
38
+ <button {...otherProps} disabled={disabled} type="button" onClick={onClick}
39
+ className={classNames(styles.button, classes, flavor, className)}>
19
40
  {children}
20
41
  </button>
21
42
  );
22
- }
23
-
24
- const ButtonMemo = withMemo(Button, styles);
25
- export { ButtonMemo as Button };
43
+ }, styles);
@@ -0,0 +1,4 @@
1
+ export enum ButtonType {
2
+ Primary = "primary",
3
+ Secondary = "secondary",
4
+ }
@@ -1,5 +1,6 @@
1
1
  @import "../../../scss/variables";
2
2
  @import "../../../scss/designMixin";
3
+ @import "../../../scss/flavorMixin";
3
4
 
4
5
  .button {
5
6
  cursor: pointer;
@@ -10,13 +11,11 @@
10
11
  overflow: hidden;
11
12
  text-decoration: none;
12
13
  letter-spacing: 0;
13
- color: white;
14
14
  vertical-align: middle;
15
- border: 0 solid currentColor;
16
15
  border-radius: 3px;
17
16
  transition: none;
18
17
 
19
- --text-primary-default-color: white;
18
+ @include flavorSelection(--button-color);
20
19
 
21
20
  @include design($material) {
22
21
  box-shadow: $boxShadowMaterial;
@@ -26,7 +25,6 @@
26
25
  text-align: center;
27
26
  font-size: 14px;
28
27
  text-transform: uppercase;
29
- background-color: var(--flavor-accent);
30
28
  font-weight: 500;
31
29
  }
32
30
 
@@ -34,6 +32,25 @@
34
32
  line-height: 32px;
35
33
  padding: 4px 18px;
36
34
  font-size: 17px;
37
- background-color: var(--flavor-accent);
35
+ }
36
+
37
+ &.primary {
38
+ background-color: var(--button-color);
39
+ border: 0 solid currentColor;
40
+ color: white;
41
+ --text-primary-default-color: white;
42
+ }
43
+
44
+ &.secondary {
45
+ background-color: transparent;
46
+ border: 1px solid var(--button-color);
47
+ color: var(--button-color);
48
+ --text-primary-default-color: var(--button-color);
49
+ }
50
+
51
+ &.disabled {
52
+ opacity: 0.3;
53
+ cursor: default;
54
+ pointer-events: none;
38
55
  }
39
56
  }
@@ -0,0 +1,55 @@
1
+ import * as React from 'react';
2
+ import {RbmComponentProps} from '../../../RbmComponentProps';
3
+ import {Override} from '../../../../TypeHelpers';
4
+ import {useCallback, useMemo} from 'react';
5
+ import {Listener, useListenerWithExtractedProps} from '../../../Hooks/useListener';
6
+
7
+ import styles from './fileInput.scss';
8
+ import {withMemo} from '../../../../helper/withMemo';
9
+ import {FileType} from "./FileType";
10
+ import {MultipleFileInput, MultipleFileInputProps} from "./MultipleFileInput";
11
+
12
+
13
+ export type FileInputProps<OnChangeFileData> = RbmComponentProps<
14
+ Override<
15
+ Omit<MultipleFileInputProps<unknown>, "onChangeFiles" | "maxFiles" | "onChangeFilesData" | "mimeTypes"|"showDeleteButton">, {
16
+ value?: FileType,
17
+ mimeType?: string,
18
+ required?: boolean,
19
+ } & Listener<'onChangeFile', OnChangeFileData, FileType | undefined>>
20
+ >;
21
+
22
+ // TODO use MultipleFileInput internal
23
+ export const FileInput = withMemo(function FileInput<OnChangeData>({
24
+ value,
25
+ mimeType,
26
+ required = false,
27
+ ...otherProps
28
+ }: FileInputProps<OnChangeData>) {
29
+ // Variables
30
+
31
+ // Refs
32
+
33
+ // States
34
+ const mimeTypes = useMemo(() => (mimeType ? [mimeType] : undefined), [mimeType]);
35
+ const innerValue = useMemo(() => value ? [value] : [], [value]);
36
+
37
+ // Selectors
38
+
39
+ // Callbacks
40
+ const [onChangeFile, multipleFileInputProps] = useListenerWithExtractedProps<"onChangeFile", OnChangeData>("onChangeFile", otherProps);
41
+ const onChangeFiles = useCallback((files: FileType[]) => {
42
+ if (!required || files[0]) {
43
+ onChangeFile(files[0]);
44
+ }
45
+ }, [onChangeFile, required]);
46
+
47
+ // Effects
48
+
49
+ // Other
50
+
51
+ // Render Functions
52
+ return <MultipleFileInput maxFiles={1} value={innerValue} onChangeFiles={onChangeFiles}
53
+ mimeTypes={mimeTypes} showDeleteButton={!required} {...multipleFileInputProps}/>;
54
+
55
+ }, styles);
@@ -0,0 +1 @@
1
+ export type FileType = { name: string; data: string; mimeType: string; uploaded?: boolean; blob?: Blob };