react-bootstrap-front 3.7.3 → 3.7.7
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.
- package/CHANGELOG +22 -0
- package/dist/react-bootstrap-front.js +16 -26
- package/package.json +4 -12
- package/src/features/advanced/DefaultQuickSearch.js +17 -3
- package/src/features/advanced/DropdownWrapper.js +5 -8
- package/src/features/advanced/ResponsiveModalInner.js +38 -15
- package/src/features/advanced/ResponsiveModalInner.scss +7 -1
- package/src/features/basic/CalmButton.js +3 -3
- package/src/features/basic/InputJson.js +1 -0
- package/src/features/basic/ResponsiveButton.js +3 -3
- package/src/features/basic/index.js +1 -3
- package/src/features/basic/style.scss +0 -3
- package/src/features/draft/ColorPicker.js +50 -0
- package/src/features/draft/ColorPicker.scss +0 -0
- package/src/features/draft/FontSize.js +71 -0
- package/src/features/draft/FontSize.scss +0 -0
- package/src/features/draft/Inline.js +43 -0
- package/src/features/draft/Inline.scss +0 -0
- package/src/features/{basic/InputTextarea.js → draft/InputHtml.js} +25 -53
- package/src/features/draft/InputHtml.scss +8 -0
- package/src/features/draft/index.js +4 -0
- package/src/features/draft/style.scss +4 -0
- package/src/features/helpers/index.js +13 -3
- package/src/features/list/DefaultLine.jsx +17 -2
- package/src/features/list/DefaultList.jsx +1 -1
- package/src/features/list/MobileLine.jsx +45 -37
- package/src/index.js +7 -2
- package/src/styles/index.scss +1 -0
- package/src/styles/look2.scss +62 -13
- package/src/features/basic/InputTextarea.scss +0 -3
- package/src/features/basic/InputTextareaHtml.js +0 -175
- package/src/features/basic/InputTextareaHtml.scss +0 -6
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-bootstrap-front",
|
|
3
|
-
"version": "3.7.
|
|
3
|
+
"version": "3.7.7",
|
|
4
4
|
"description": "React Bootstrap Components",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"Bootstrap 4",
|
|
@@ -34,9 +34,6 @@
|
|
|
34
34
|
"react-router-dom": "^5.0.1"
|
|
35
35
|
},
|
|
36
36
|
"dependencies": {
|
|
37
|
-
"@aeaton/prosemirror-transformers": "^2.0.2",
|
|
38
|
-
"@aeaton/react-prosemirror": "^2.0.3",
|
|
39
|
-
"@aeaton/react-prosemirror-config-default": "^2.0.3",
|
|
40
37
|
"@ericblade/quagga2": "^1.4.1",
|
|
41
38
|
"@popperjs/core": "^2.5.4",
|
|
42
39
|
"autosize": "^4.0.2",
|
|
@@ -48,7 +45,7 @@
|
|
|
48
45
|
"date-fns": "^2.16.1",
|
|
49
46
|
"dom-helpers": "^5.1.0",
|
|
50
47
|
"draft-convert": "^2.1.8",
|
|
51
|
-
"draft-js": "^0.11.
|
|
48
|
+
"draft-js": "^0.11.2",
|
|
52
49
|
"html-entities": "^1.3.1",
|
|
53
50
|
"html-to-draftjs": "^1.5.0",
|
|
54
51
|
"imask": "^6.0.5",
|
|
@@ -63,20 +60,17 @@
|
|
|
63
60
|
"object-assign": "^4.1.1",
|
|
64
61
|
"object.omit": "^3.0.0",
|
|
65
62
|
"prop-types": "^15.7.2",
|
|
66
|
-
"prosemirror-model": "^1.13.3",
|
|
67
|
-
"prosemirror-state": "^1.3.4",
|
|
68
|
-
"prosemirror-view": "^1.18.2",
|
|
69
63
|
"react-app-polyfill": "^2.0.0",
|
|
64
|
+
"react-color": "^2.19.3",
|
|
70
65
|
"react-countdown-circle-timer": "^2.3.7",
|
|
71
66
|
"react-datepicker": "^2.11.0",
|
|
72
|
-
"react-draft-wysiwyg": "^1.14.
|
|
67
|
+
"react-draft-wysiwyg": "^1.14.7",
|
|
73
68
|
"react-imask": "^6.0.3",
|
|
74
69
|
"react-intersection-observer": "^8.32.2",
|
|
75
70
|
"react-json-view": "^1.21.3",
|
|
76
71
|
"react-observe-size": "^0.3.0",
|
|
77
72
|
"react-overlays": "^2.0.0-0",
|
|
78
73
|
"react-portal-tooltip": "^2.4.7",
|
|
79
|
-
"react-prosemirror": "^0.2.1",
|
|
80
74
|
"react-sortable-hoc": "^1.10.1",
|
|
81
75
|
"react-transition-group": "^4.3.0",
|
|
82
76
|
"react-world-flags": "^1.3.0",
|
|
@@ -84,8 +78,6 @@
|
|
|
84
78
|
"redux-actions": "^2.6.1",
|
|
85
79
|
"redux-logger": "^3.0.6",
|
|
86
80
|
"signature_pad": "^3.0.0-beta.4",
|
|
87
|
-
"slate": "^0.66.5",
|
|
88
|
-
"slate-react": "^0.69.0",
|
|
89
81
|
"trello-smooth-dnd": "1.0.0",
|
|
90
82
|
"uncontrollable": "^7.0.0"
|
|
91
83
|
},
|
|
@@ -8,10 +8,14 @@ export default class DefaultQuickSearch extends Component {
|
|
|
8
8
|
name: PropTypes.string.isRequired,
|
|
9
9
|
label: PropTypes.string,
|
|
10
10
|
icon: PropTypes.element.isRequired,
|
|
11
|
+
plus: PropTypes.element,
|
|
12
|
+
reset: PropTypes.element,
|
|
11
13
|
};
|
|
12
14
|
|
|
13
15
|
static defaultProps = {
|
|
14
16
|
label: '',
|
|
17
|
+
plus: null,
|
|
18
|
+
reset: null,
|
|
15
19
|
};
|
|
16
20
|
|
|
17
21
|
static getDerivedStateFromProps(props, state) {
|
|
@@ -38,11 +42,11 @@ export default class DefaultQuickSearch extends Component {
|
|
|
38
42
|
this.setState({ search: event.target.value });
|
|
39
43
|
}
|
|
40
44
|
|
|
41
|
-
onSubmit(event) {
|
|
45
|
+
onSubmit(event, mode) {
|
|
42
46
|
if (event) {
|
|
43
47
|
event.preventDefault();
|
|
44
48
|
}
|
|
45
|
-
this.props.onSubmit(this.state.search);
|
|
49
|
+
this.props.onSubmit(this.state.search, mode);
|
|
46
50
|
}
|
|
47
51
|
|
|
48
52
|
render() {
|
|
@@ -58,9 +62,19 @@ export default class DefaultQuickSearch extends Component {
|
|
|
58
62
|
onChange={this.onChange}
|
|
59
63
|
/>
|
|
60
64
|
<div className="input-group-append">
|
|
61
|
-
<button type="button" className="btn btn-outline-secondary bg-light" onClick={this.onSubmit}>
|
|
65
|
+
<button type="button" title="Recherche simple" className="btn btn-outline-secondary bg-light" onClick={(ev) => this.onSubmit(ev, "simple")}>
|
|
62
66
|
{this.props.icon}
|
|
63
67
|
</button>
|
|
68
|
+
{this.props.plus &&
|
|
69
|
+
<button type="button" title="Recherche mois stricte" className="btn btn-outline-secondary bg-light" onClick={(ev) => this.onSubmit(ev, "plus")}>
|
|
70
|
+
{this.props.plus}
|
|
71
|
+
</button>
|
|
72
|
+
}
|
|
73
|
+
{this.props.reset &&
|
|
74
|
+
<button type="button" title="Initialiser la recherche" className="btn btn-outline-secondary bg-light" onClick={(ev) => this.onSubmit(ev, "reset")}>
|
|
75
|
+
{this.props.reset}
|
|
76
|
+
</button>
|
|
77
|
+
}
|
|
64
78
|
</div>
|
|
65
79
|
</div>
|
|
66
80
|
</form>
|
|
@@ -39,16 +39,13 @@ export default class DropdownWrapper extends Component {
|
|
|
39
39
|
}
|
|
40
40
|
|
|
41
41
|
render() {
|
|
42
|
+
const clonedTrigger = React.cloneElement(
|
|
43
|
+
this.props.trigger,
|
|
44
|
+
{ref: this.state.ref, onClick: this.onClick, title: this.props.tooltip}
|
|
45
|
+
)
|
|
42
46
|
return (
|
|
43
47
|
<>
|
|
44
|
-
|
|
45
|
-
ref={this.state.ref}
|
|
46
|
-
className={classnames('advanced-dropdown-wrapper', this.props.className)}
|
|
47
|
-
onClick={this.onClick}
|
|
48
|
-
title={this.props.tooltip}
|
|
49
|
-
>
|
|
50
|
-
{this.props.trigger}
|
|
51
|
-
</div>
|
|
48
|
+
{clonedTrigger}
|
|
52
49
|
{this.state.open && (
|
|
53
50
|
<Dropdown align={this.props.align} myRef={this.state.ref} onClose={this.onClose}>
|
|
54
51
|
<div onClick={this.onClose}>{this.props.children}</div>
|
|
@@ -107,11 +107,32 @@ export default class ResponsiveModalInner extends Component {
|
|
|
107
107
|
}
|
|
108
108
|
|
|
109
109
|
componentDidMount() {
|
|
110
|
-
const
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
110
|
+
const backDrops = Array.from(document.getElementsByClassName('modal-opacity'));
|
|
111
|
+
const elems = backDrops.map(elem => {return {id: elem.id, zIndex: parseFloat(window.getComputedStyle(elem).zIndex)}});
|
|
112
|
+
elems.forEach(elem => {
|
|
113
|
+
const el = document.getElementById(elem.id);
|
|
114
|
+
if (el) {
|
|
115
|
+
el.style.opacity = 0;
|
|
116
|
+
}
|
|
117
|
+
});
|
|
118
|
+
this.setState({ opacity: '0.8', show: true });
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
componentWillUnmount() {
|
|
122
|
+
const backDrops = Array.from(document.getElementsByClassName('modal-opacity'));
|
|
123
|
+
if (Array.isArray(backDrops)) {
|
|
124
|
+
const elems = backDrops.map(elem => {return {id: elem.id, zIndex: parseFloat(window.getComputedStyle(elem).zIndex)}});
|
|
125
|
+
elems.pop(); // will be removed...
|
|
126
|
+
if (elems.length > 0) {
|
|
127
|
+
elems.sort((a, b) => { return a>b ? 1 : a<b ? -1 : 0 });
|
|
128
|
+
const last = elems.pop();
|
|
129
|
+
if (last) {
|
|
130
|
+
const el = document.getElementById(last.id);
|
|
131
|
+
if (el) {
|
|
132
|
+
el.style.opacity = 0.8;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
}
|
|
115
136
|
}
|
|
116
137
|
}
|
|
117
138
|
|
|
@@ -122,7 +143,6 @@ export default class ResponsiveModalInner extends Component {
|
|
|
122
143
|
render() {
|
|
123
144
|
const bStyles = { ...backStyle, opacity: this.state.opacity };
|
|
124
145
|
let iStyles = { overflowX: 'hidden', overflowY: 'auto' };
|
|
125
|
-
let scrollStyles = { ...inlineStyle };
|
|
126
146
|
if (this.props.height && this.props.height !== '') {
|
|
127
147
|
iStyles.height = this.props.height;
|
|
128
148
|
iStyles.minHeight = this.props.height;
|
|
@@ -132,28 +152,24 @@ export default class ResponsiveModalInner extends Component {
|
|
|
132
152
|
case 'xl':
|
|
133
153
|
iStyles.height = '510px';
|
|
134
154
|
iStyles.minHeight = '510px';
|
|
135
|
-
scrollStyles.maxHeight = '510px';
|
|
136
155
|
break;
|
|
137
156
|
case 'lg':
|
|
138
157
|
iStyles.height = '480px';
|
|
139
158
|
iStyles.minHeight = '480px';
|
|
140
|
-
scrollStyles.maxHeight = '480px';
|
|
141
159
|
break;
|
|
142
160
|
case 'md':
|
|
143
161
|
iStyles.height = '450px';
|
|
144
162
|
iStyles.minHeight = '450px';
|
|
145
|
-
scrollStyles.maxHeight = '450px';
|
|
146
163
|
break;
|
|
147
164
|
default:
|
|
148
165
|
iStyles.height = '350px';
|
|
149
166
|
iStyles.minHeight = '350px';
|
|
150
|
-
scrollStyles.maxHeight = '350px';
|
|
151
167
|
break;
|
|
152
168
|
}
|
|
153
169
|
}
|
|
154
170
|
return (
|
|
155
171
|
<Portal className="backdrop-style" zIndex={zIndex++}>
|
|
156
|
-
<div className="modal-style modal-opacity bg-light" style={{ ...bStyles, zIndex: zIndex++ }} />
|
|
172
|
+
<div id={`mdap-opacity-${zIndex}`} className="modal-style modal-opacity bg-light" style={{ ...bStyles, zIndex: zIndex++ }} />
|
|
157
173
|
<div style={{ ...modalStyle, zIndex: zIndex++ }}>
|
|
158
174
|
<Transition in={this.state.show} timeout={100}>
|
|
159
175
|
{state => (
|
|
@@ -163,7 +179,7 @@ export default class ResponsiveModalInner extends Component {
|
|
|
163
179
|
<div
|
|
164
180
|
className={classnames(
|
|
165
181
|
'modal-dialog',
|
|
166
|
-
sizeGreater(this.props.size, mediaSize) ? 'modal-fullscreen' : `modal-${this.props.size}`,
|
|
182
|
+
sizeGreater(this.props.size, mediaSize) ? 'modal-fullscreen' : `modal-w-${this.props.size}`,
|
|
167
183
|
state
|
|
168
184
|
)}
|
|
169
185
|
>
|
|
@@ -284,14 +300,21 @@ export default class ResponsiveModalInner extends Component {
|
|
|
284
300
|
</div>
|
|
285
301
|
{this.props.buttons && (
|
|
286
302
|
<div className={classnames('modal-footer', this.props.modalClassName)}>
|
|
287
|
-
{this.props.help &&
|
|
303
|
+
{(this.props.help || this.props.saving ) &&
|
|
288
304
|
<div className="modal-left-buttons">
|
|
289
|
-
|
|
305
|
+
{this.props.help &&
|
|
306
|
+
<button className="btn btn-secondary" onClick={this.onToggleHelp}>?</button>
|
|
307
|
+
}
|
|
308
|
+
{this.props.saving &&
|
|
309
|
+
<div className="calm-button-loader pr-1 text-light">
|
|
310
|
+
<SmLoading9x9 width={20} height={20} />
|
|
311
|
+
</div>
|
|
312
|
+
}
|
|
290
313
|
</div>
|
|
291
314
|
}
|
|
292
315
|
{this.props.buttons.map((button, idx) => {
|
|
293
316
|
if (!button.hidden && button.name !== '') {
|
|
294
|
-
return <ResponsiveButton key={`btn-resp${idx}`} button={button} />;
|
|
317
|
+
return <ResponsiveButton key={`btn-resp${idx}`} button={button} disabled={this.props.saving}/>;
|
|
295
318
|
}
|
|
296
319
|
return null;
|
|
297
320
|
})}
|
|
@@ -33,7 +33,6 @@
|
|
|
33
33
|
margin-left: 20px;
|
|
34
34
|
margin-right: 10px;
|
|
35
35
|
padding: 2px;
|
|
36
|
-
background-color: theme-color('secondary');
|
|
37
36
|
}
|
|
38
37
|
.nav-link-inner-btn:hover {
|
|
39
38
|
background-color: theme-color('secondary-light');
|
|
@@ -53,6 +52,13 @@
|
|
|
53
52
|
min-height: 36px;
|
|
54
53
|
min-width: 36px;
|
|
55
54
|
}
|
|
55
|
+
|
|
56
|
+
.calm-button-loader {
|
|
57
|
+
line-height: 36px;
|
|
58
|
+
margin: auto;
|
|
59
|
+
vertical-align: middle;
|
|
60
|
+
position: relative;
|
|
61
|
+
}
|
|
56
62
|
}
|
|
57
63
|
}
|
|
58
64
|
|
|
@@ -52,7 +52,7 @@ export default class CalmButton extends Component {
|
|
|
52
52
|
} else {
|
|
53
53
|
this.timer = setTimeout(() => {
|
|
54
54
|
this.setState({ executing: false });
|
|
55
|
-
},
|
|
55
|
+
}, 500);
|
|
56
56
|
this.setState({ executing: true });
|
|
57
57
|
this.props.onClick(event);
|
|
58
58
|
}
|
|
@@ -99,13 +99,13 @@ export default class CalmButton extends Component {
|
|
|
99
99
|
{this.props.options.map(option => {
|
|
100
100
|
return (
|
|
101
101
|
<DropdownMenuOption
|
|
102
|
-
key={`text-${option.
|
|
102
|
+
key={`text-${option.value}`}
|
|
103
103
|
label={option.label}
|
|
104
104
|
onClick={ev => {
|
|
105
105
|
if (ev) {
|
|
106
106
|
ev.preventDefault();
|
|
107
107
|
}
|
|
108
|
-
|
|
108
|
+
this.props.onClick(option.value);
|
|
109
109
|
this.onOptionsMenuClose();
|
|
110
110
|
}}
|
|
111
111
|
/>
|
|
@@ -8,6 +8,7 @@ import { getFieldId } from '../helpers';
|
|
|
8
8
|
export const InputJson = props => {
|
|
9
9
|
let myId = getFieldId(props.name, props.id);
|
|
10
10
|
const data = JSON.parse(props.value) || {};
|
|
11
|
+
console.log(data, props.value);
|
|
11
12
|
return (
|
|
12
13
|
<InputGroup {...props} id={myId}>
|
|
13
14
|
{props.prepend && props.prepend !== '' && (
|
|
@@ -10,12 +10,12 @@ export const ResponsiveButton = props => (
|
|
|
10
10
|
<CalmButton
|
|
11
11
|
type="button"
|
|
12
12
|
className={classnames('btn', `btn-${props.button.theme}`)}
|
|
13
|
-
disabled={props.button.disabled || false}
|
|
14
13
|
onClick={props.button.function}
|
|
15
14
|
options={props.button.options}
|
|
16
15
|
optionsAlign={props.button.optionsAlign}
|
|
17
16
|
optionsOpenMulti={props.button.optionsOpenMulti}
|
|
18
|
-
loader={
|
|
17
|
+
loader={false}
|
|
18
|
+
disabled={props.button.disabled || props.disabled || false}
|
|
19
19
|
>
|
|
20
20
|
{props.button.name ? <span className="no-selector" color="white">{props.button.name}</span> : props.button.icon}
|
|
21
21
|
</CalmButton>
|
|
@@ -24,12 +24,12 @@ export const ResponsiveButton = props => (
|
|
|
24
24
|
<CalmButton
|
|
25
25
|
type="button"
|
|
26
26
|
className={classnames('btn btn-mobile', `btn-${props.button.theme}`)}
|
|
27
|
-
disabled={props.button.disabled || false}
|
|
28
27
|
onClick={props.button.function}
|
|
29
28
|
options={props.button.options}
|
|
30
29
|
optionsAlign={props.button.optionsAlign}
|
|
31
30
|
optionsOpenMulti={props.button.optionsOpenMulti}
|
|
32
31
|
loader={false}
|
|
32
|
+
disabled={props.button.disabled || props.disabled || false}
|
|
33
33
|
>
|
|
34
34
|
{props.button.icon ? props.button.icon : <span className="no-selector" color="white">{props.button.name}</span>}
|
|
35
35
|
</CalmButton>
|
|
@@ -21,8 +21,6 @@ export { default as InputSelect } from "./InputSelect";
|
|
|
21
21
|
export { default as InputSpin } from "./InputSpin";
|
|
22
22
|
export { default as InputStringarray } from "./InputStringarray";
|
|
23
23
|
export * from "./InputText";
|
|
24
|
-
export { default as InputTextarea } from "./InputTextarea";
|
|
25
|
-
export { default as InputTextareaHtml } from "./InputTextareaHtml";
|
|
26
24
|
export * from "./ResponsiveButton";
|
|
27
25
|
export { default as InputCheckList } from "./InputCheckList";
|
|
28
26
|
export { default as CalmButton } from "./CalmButton";
|
|
@@ -47,4 +45,4 @@ export { default as InputBarCode } from "./InputBarCode";
|
|
|
47
45
|
export { default as Scanner } from "./Scanner";
|
|
48
46
|
export { default as InputSignature } from "./InputSignature";
|
|
49
47
|
export * from "./InputTextMultiline";
|
|
50
|
-
export * from "./InputChildren";
|
|
48
|
+
export * from "./InputChildren";
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
@import '~react-datepicker/dist/react-datepicker.css';
|
|
2
|
-
@import '~react-draft-wysiwyg/dist/react-draft-wysiwyg.css';
|
|
3
2
|
@import './CalmButton';
|
|
4
3
|
@import './Dropdown';
|
|
5
4
|
@import './InlineInputCheckbox';
|
|
@@ -24,8 +23,6 @@
|
|
|
24
23
|
@import './InputSpin';
|
|
25
24
|
@import './InputStringarray';
|
|
26
25
|
@import './InputText';
|
|
27
|
-
@import './InputTextarea';
|
|
28
|
-
@import './InputTextareaHtml';
|
|
29
26
|
@import './ResponsiveButton';
|
|
30
27
|
@import './InputGroup';
|
|
31
28
|
@import './InputGroupAppend';
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import React, { Component } from 'react';
|
|
2
|
+
import classnames from 'classnames';
|
|
3
|
+
import PropTypes from 'prop-types';
|
|
4
|
+
import { ChromePicker } from 'react-color';
|
|
5
|
+
import { DropdownWrapper } from '../advanced'
|
|
6
|
+
import { DropdownMenu } from '../basic';
|
|
7
|
+
|
|
8
|
+
export default class ColorPicker extends Component {
|
|
9
|
+
static propTypes = {
|
|
10
|
+
expanded: PropTypes.bool,
|
|
11
|
+
onExpandEvent: PropTypes.func,
|
|
12
|
+
onChange: PropTypes.func,
|
|
13
|
+
currentState: PropTypes.object,
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
constructor(props) {
|
|
17
|
+
super(props);
|
|
18
|
+
this.state = {
|
|
19
|
+
myRef: React.createRef()
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
stopPropagation = (event) => {
|
|
24
|
+
event.stopPropagation();
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
onChange = (color) => {
|
|
28
|
+
const { onChange } = this.props;
|
|
29
|
+
onChange('color', color.hex);
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
render() {
|
|
33
|
+
const trigger = (
|
|
34
|
+
<button
|
|
35
|
+
type="button"
|
|
36
|
+
className={classnames(this.props.className, 'btn btn-light')}
|
|
37
|
+
>
|
|
38
|
+
Color
|
|
39
|
+
</button>
|
|
40
|
+
);
|
|
41
|
+
const { color } = this.props.currentState;
|
|
42
|
+
return (
|
|
43
|
+
<DropdownWrapper trigger={trigger} className="rbf-inline-wrapper btn-group pl-2" align="bottom-right" myRef={this.state.myRef}>
|
|
44
|
+
<DropdownMenu>
|
|
45
|
+
<ChromePicker color={color} onChangeComplete={this.onChange} />
|
|
46
|
+
</DropdownMenu>
|
|
47
|
+
</DropdownWrapper>
|
|
48
|
+
);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
File without changes
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import React, { Component } from 'react';
|
|
2
|
+
import classnames from 'classnames';
|
|
3
|
+
import PropTypes from 'prop-types';
|
|
4
|
+
import { DropdownWrapper } from '../advanced'
|
|
5
|
+
import { DropdownMenu, DropdownMenuOption } from '../basic';
|
|
6
|
+
|
|
7
|
+
export default class FontSize extends Component {
|
|
8
|
+
static propTypes = {
|
|
9
|
+
expanded: PropTypes.bool,
|
|
10
|
+
onExpandEvent: PropTypes.func,
|
|
11
|
+
onChange: PropTypes.func,
|
|
12
|
+
currentState: PropTypes.object,
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
constructor(props) {
|
|
16
|
+
super(props);
|
|
17
|
+
this.state = {
|
|
18
|
+
myRef: React.createRef()
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
stopPropagation = (event) => {
|
|
23
|
+
event.stopPropagation();
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
onChange = (color) => {
|
|
27
|
+
const { onChange } = this.props;
|
|
28
|
+
onChange('color', color.hex);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
render() {
|
|
32
|
+
const trigger = (
|
|
33
|
+
<button
|
|
34
|
+
type="button"
|
|
35
|
+
className={classnames(this.props.className, 'btn btn-light')}
|
|
36
|
+
>
|
|
37
|
+
Size
|
|
38
|
+
</button>
|
|
39
|
+
);
|
|
40
|
+
const {
|
|
41
|
+
config: { icon, className, dropdownClassName, options, title },
|
|
42
|
+
onChange,
|
|
43
|
+
expanded,
|
|
44
|
+
doCollapse,
|
|
45
|
+
onExpandEvent,
|
|
46
|
+
doExpand,
|
|
47
|
+
translations,
|
|
48
|
+
} = this.props;
|
|
49
|
+
let { currentState: { fontSize: currentFontSize } } = this.props;
|
|
50
|
+
let { defaultFontSize } = this.state;
|
|
51
|
+
defaultFontSize = Number(defaultFontSize);
|
|
52
|
+
currentFontSize = currentFontSize ||
|
|
53
|
+
(options && options.indexOf(defaultFontSize) >= 0 && defaultFontSize);
|
|
54
|
+
return (
|
|
55
|
+
<DropdownWrapper trigger={trigger} className="rbf-inline-wrapper btn-group pl-2" align="bottom-right" myRef={this.state.myRef}>
|
|
56
|
+
<DropdownMenu>
|
|
57
|
+
{options.map((size, index) =>
|
|
58
|
+
(<DropdownMenuOption
|
|
59
|
+
className="rdw-fontsize-option"
|
|
60
|
+
active={currentFontSize === size}
|
|
61
|
+
onClick={() => onChange(size)}
|
|
62
|
+
key={index}
|
|
63
|
+
>
|
|
64
|
+
{size}
|
|
65
|
+
</DropdownMenuOption>),
|
|
66
|
+
)}
|
|
67
|
+
</DropdownMenu>
|
|
68
|
+
</DropdownWrapper>
|
|
69
|
+
);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
File without changes
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import React, { Component } from 'react';
|
|
2
|
+
import classnames from 'classnames';
|
|
3
|
+
import PropTypes from 'prop-types';
|
|
4
|
+
|
|
5
|
+
export default class Inline extends Component {
|
|
6
|
+
static propTypes = {
|
|
7
|
+
expanded: PropTypes.bool,
|
|
8
|
+
onExpandEvent: PropTypes.func,
|
|
9
|
+
onChange: PropTypes.func,
|
|
10
|
+
currentState: PropTypes.object,
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
constructor(props) {
|
|
14
|
+
super(props);
|
|
15
|
+
this.state = {
|
|
16
|
+
myRef: React.createRef()
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
render() {
|
|
20
|
+
const { config, currentState, onChange, translations } = this.props;
|
|
21
|
+
return (
|
|
22
|
+
<div className={classnames('rbf-inline-wrapper btn-group pl-2', config.className)} aria-label="rdw-inline-control">
|
|
23
|
+
{
|
|
24
|
+
config.options
|
|
25
|
+
.map((style, index) =>
|
|
26
|
+
(<button
|
|
27
|
+
key={index}
|
|
28
|
+
onClick={() => onChange(style)}
|
|
29
|
+
className={classnames("btn btn-light", config[style].className, (currentState[style] === true ||
|
|
30
|
+
(style === 'MONOSPACE' && currentState.CODE)) && "active")}
|
|
31
|
+
title={config[style].title || translations[`components.controls.inline.${style}`]}
|
|
32
|
+
>
|
|
33
|
+
<img
|
|
34
|
+
alt=""
|
|
35
|
+
src={config[style].icon}
|
|
36
|
+
/>
|
|
37
|
+
</button>),
|
|
38
|
+
)
|
|
39
|
+
}
|
|
40
|
+
</div>
|
|
41
|
+
);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
File without changes
|
|
@@ -4,16 +4,18 @@ import classnames from 'classnames';
|
|
|
4
4
|
import { EditorState, Modifier } from 'draft-js';
|
|
5
5
|
import { Editor } from 'react-draft-wysiwyg';
|
|
6
6
|
import { convertToHTML, convertFromHTML } from 'draft-convert';
|
|
7
|
-
import { DropdownWrapper, ResponsiveConfirm } from '../advanced';
|
|
8
|
-
import { DropdownMenu, DropdownMenuOption, Dropdown } from '../basic';
|
|
9
7
|
import { htmlToString } from '../helpers';
|
|
8
|
+
import { ColorPicker, Inline, FontSize } from './';
|
|
9
|
+
import '../../../node_modules/react-draft-wysiwyg/dist/react-draft-wysiwyg.css';
|
|
10
10
|
|
|
11
11
|
const myStyle = {
|
|
12
12
|
height: 'auto',
|
|
13
13
|
};
|
|
14
|
+
|
|
14
15
|
const appenStyle = {
|
|
15
16
|
maxHeight: '40px',
|
|
16
17
|
};
|
|
18
|
+
|
|
17
19
|
const toHtml = {
|
|
18
20
|
styleToHTML: style => {
|
|
19
21
|
const parts = style.split('-');
|
|
@@ -171,10 +173,9 @@ export default class InputTextarea extends Component {
|
|
|
171
173
|
this.state = {
|
|
172
174
|
editorState: EditorState.createWithContent(value),
|
|
173
175
|
toolbar: false,
|
|
174
|
-
myRef: React.createRef(),
|
|
175
|
-
presetText: false,
|
|
176
176
|
};
|
|
177
177
|
this.onEditorStateChange = this.onEditorStateChange.bind(this);
|
|
178
|
+
this.onChange = this.onChange.bind(this);
|
|
178
179
|
this.onToolbar = this.onToolbar.bind(this);
|
|
179
180
|
this.onClear = this.onClear.bind(this);
|
|
180
181
|
this.onPresetText = this.onPresetText.bind(this);
|
|
@@ -186,6 +187,9 @@ export default class InputTextarea extends Component {
|
|
|
186
187
|
this.setState({
|
|
187
188
|
editorState,
|
|
188
189
|
});
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
onChange(ev, editorState) {
|
|
189
193
|
const content = editorState.getCurrentContent();
|
|
190
194
|
const event = {
|
|
191
195
|
target: {
|
|
@@ -221,16 +225,7 @@ export default class InputTextarea extends Component {
|
|
|
221
225
|
const editorState = this.state.editorState;
|
|
222
226
|
let content = editorState.getCurrentContent();
|
|
223
227
|
const selection = editorState.getSelection();
|
|
224
|
-
//const contentStateWithEntity = content.createEntity('MY_ENTITY_TYPE','IMMUTABLE');
|
|
225
|
-
//const entityKey = contentStateWithEntity.getLastCreatedEntityKey();
|
|
226
228
|
content = Modifier.insertText(content, selection, htmlToString(contentMore));
|
|
227
|
-
/**content = Modifier.insertText(
|
|
228
|
-
content,
|
|
229
|
-
selection,
|
|
230
|
-
contentMore,
|
|
231
|
-
null,
|
|
232
|
-
entityKey,
|
|
233
|
-
);*/
|
|
234
229
|
let newState = EditorState.push(editorState, content);
|
|
235
230
|
this.setState({ editorState: newState });
|
|
236
231
|
const newContent = newState.getCurrentContent();
|
|
@@ -250,6 +245,21 @@ export default class InputTextarea extends Component {
|
|
|
250
245
|
render() {
|
|
251
246
|
//<div className={classnames('input-group', (props.error || props.warning) && 'is-invalid')}>
|
|
252
247
|
const { editorState, toolbar } = this.state;
|
|
248
|
+
const editorToolbar = {
|
|
249
|
+
options: ['inline','fontSize','colorPicker'],
|
|
250
|
+
inline: {
|
|
251
|
+
inDropdown: false,
|
|
252
|
+
component: Inline,
|
|
253
|
+
options: ['bold', 'italic', 'underline', 'superscript', 'subscript'],
|
|
254
|
+
},
|
|
255
|
+
fontSize: {
|
|
256
|
+
component: FontSize,
|
|
257
|
+
options: [7, 8, 9, 10, 11, 12, 14, 16, 18, 24, 30, 36, 48, 60, 72, 96],
|
|
258
|
+
},
|
|
259
|
+
colorPicker: {
|
|
260
|
+
component: ColorPicker
|
|
261
|
+
}
|
|
262
|
+
};
|
|
253
263
|
return (
|
|
254
264
|
<div className={classnames('form-group', !this.props.labelTop && 'row')}>
|
|
255
265
|
{this.props.label !== '' && (
|
|
@@ -265,51 +275,13 @@ export default class InputTextarea extends Component {
|
|
|
265
275
|
>
|
|
266
276
|
<Editor
|
|
267
277
|
toolbarHidden={!toolbar}
|
|
278
|
+
toolbar={editorToolbar}
|
|
268
279
|
editorState={editorState}
|
|
269
|
-
toolbarClassName="toolbarClassName"
|
|
270
280
|
wrapperClassName="form-control border-rbf h-auto"
|
|
271
|
-
editorClassName="editorClassName overflow-hidden"
|
|
272
281
|
onEditorStateChange={this.onEditorStateChange}
|
|
282
|
+
onBlur={this.onChange}
|
|
273
283
|
/>
|
|
274
284
|
<div className="input-group-append" style={appenStyle}>
|
|
275
|
-
{this.props.presetTextIcon && (
|
|
276
|
-
<>
|
|
277
|
-
<button
|
|
278
|
-
type="button"
|
|
279
|
-
className={classnames(
|
|
280
|
-
'btn btn-input btn-outline-rbf bg-light',
|
|
281
|
-
this.props.size === 'sm' && `btn-${this.props.size}`
|
|
282
|
-
)}
|
|
283
|
-
onClick={this.onPresetText}
|
|
284
|
-
ref={this.state.myRef}
|
|
285
|
-
>
|
|
286
|
-
{this.props.presetTextIcon}
|
|
287
|
-
</button>
|
|
288
|
-
{this.props.presetTexts && this.props.presetTexts.length > 0 && this.state.presetText && (
|
|
289
|
-
<Dropdown
|
|
290
|
-
align="bottom-right"
|
|
291
|
-
myRef={this.state.myRef}
|
|
292
|
-
maxHeight="250px"
|
|
293
|
-
onClose={this.onPresetTextClose}
|
|
294
|
-
>
|
|
295
|
-
<DropdownMenu>
|
|
296
|
-
{Array.isArray(this.props.presetTexts) &&
|
|
297
|
-
this.props.presetTexts.map(text => {
|
|
298
|
-
return (
|
|
299
|
-
<DropdownMenuOption
|
|
300
|
-
key={`text-${text.id}`}
|
|
301
|
-
label={text.text_code}
|
|
302
|
-
onClick={() => {
|
|
303
|
-
this.onAddPresetText(text.text_content);
|
|
304
|
-
}}
|
|
305
|
-
/>
|
|
306
|
-
);
|
|
307
|
-
})}
|
|
308
|
-
</DropdownMenu>
|
|
309
|
-
</Dropdown>
|
|
310
|
-
)}
|
|
311
|
-
</>
|
|
312
|
-
)}
|
|
313
285
|
<button
|
|
314
286
|
type="button"
|
|
315
287
|
className={classnames(
|