[AAI-92 Amsterdam] Update license
[aai/sparky-fe.git] / src / generic-components / input / inputOptions / InputOptions.jsx
1 /*
2  * ============LICENSE_START=======================================================
3  * org.onap.aai
4  * ================================================================================
5  * Copyright © 2017 AT&T Intellectual Property. All rights reserved.
6  * Copyright © 2017 Amdocs
7  * ================================================================================
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *       http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  * ============LICENSE_END=========================================================
20  *
21  * ECOMP is a trademark and service mark of AT&T Intellectual Property.
22  */
23 import React from 'react';
24 import i18n from 'utils/i18n/i18n.js';
25 import classNames from 'classnames';
26 import Select from 'generic-components/input/SelectInput.jsx';
27
28 export const other = {OTHER: 'Other'};
29
30 class InputOptions extends React.Component {
31                 
32                 static propTypes = {
33                                 values: React.PropTypes.arrayOf(React.PropTypes.shape({
34                                                 enum: React.PropTypes.string,
35                                                 title: React.PropTypes.string
36                                 })),
37                                 isEnabledOther: React.PropTypes.bool,
38                                 title: React.PropTypes.string,
39                                 selectedValue: React.PropTypes.string,
40                                 multiSelectedEnum: React.PropTypes.array,
41                                 selectedEnum: React.PropTypes.string,
42                                 otherValue: React.PropTypes.string,
43                                 onEnumChange: React.PropTypes.func,
44                                 onOtherChange: React.PropTypes.func,
45                                 isRequired: React.PropTypes.bool,
46                                 isMultiSelect: React.PropTypes.bool
47                 };
48                 
49                 
50                 static contextTypes = {
51                                 isReadOnlyMode: React.PropTypes.bool
52                 };
53                 
54                 state = {
55                                 otherInputDisabled: !this.props.otherValue
56                 };
57                 
58                 oldProps = {
59                                 selectedEnum: '',
60                                 otherValue: '',
61                                 multiSelectedEnum: []
62                 };
63                 
64                 render() {
65                                 let {label, isRequired, values, otherValue, onOtherChange, isMultiSelect, onBlur, multiSelectedEnum, selectedEnum, hasError, validations, children} = this.props;
66                                 
67                                 let currentMultiSelectedEnum = [];
68                                 let currentSelectedEnum = '';
69                                 let {otherInputDisabled} = this.state;
70                                 if (isMultiSelect) {
71                                                 currentMultiSelectedEnum = multiSelectedEnum;
72                                                 if (!otherInputDisabled) {
73                                                                 currentSelectedEnum =
74                                                                                 multiSelectedEnum ? multiSelectedEnum.toString() : undefined;
75                                                 }
76                                 }
77                                 else {
78                                                 currentSelectedEnum = selectedEnum;
79                                 }
80                                 
81                                 let isReadOnlyMode = this.context.isReadOnlyMode;
82                                 
83                                 return (
84                                                 <div
85                                                                 className={classNames('form-group', {'required' : validations.required , 'has-error' : hasError})}>
86                                                                 <label className='control-label'>{label}</label>
87                                                                 {isMultiSelect && otherInputDisabled ?
88                                                                  <Select
89                                                                                  ref='_myInput'
90                                                                                  value={currentMultiSelectedEnum}
91                                                                                  className='options-input'
92                                                                                  clearable={false}
93                                                                                  required={isRequired}
94                                                                                  disabled={isReadOnlyMode || Boolean(this.props.disabled)}
95                                                                                  onBlur={() => onBlur()}
96                                                                                  onMultiSelectChanged={value => this.multiSelectEnumChanged(value)}
97                                                                                  options={this.renderMultiSelectOptions(values)}
98                                                                                  multi/> :
99                                                                  <div className={classNames('input-options',{'has-error' : hasError})}>
100                                                                                  <select
101                                                                                                  ref={'_myInput'}
102                                                                                                  label={label}
103                                                                                                  className='form-control input-options-select'
104                                                                                                  value={currentSelectedEnum}
105                                                                                                  style={{'width' : otherInputDisabled ? '100%' : '95px'}}
106                                                                                                  onBlur={() => onBlur()}
107                                                                                                  disabled={isReadOnlyMode || Boolean(this.props.disabled)}
108                                                                                                  onChange={ value => this.enumChanged(value)}
109                                                                                                  type='select'>
110                                                                                                  {values &&
111                                                                                                  values.length &&
112                                                                                                  values.map(val => this.renderOptions(val))}
113                                                                                                  {onOtherChange && <option key='other'
114                                                                                                                            value={other.OTHER}>{i18n(
115                                                                                                                  other.OTHER)}</option>}
116                                                                                                  {children}
117                                                                                  </select>
118                                                                                 
119                                                                                  {!otherInputDisabled && <div className='input-options-separator'/>}
120                                                                                  <input
121                                                                                                  className='form-control input-options-other'
122                                                                                                  placeholder={i18n('other')}
123                                                                                                  ref='_otherValue'
124                                                                                                  style={{'display' : otherInputDisabled ? 'none' : 'block'}}
125                                                                                                  disabled={isReadOnlyMode || Boolean(this.props.disabled)}
126                                                                                                  value={otherValue || ''}
127                                                                                                  onBlur={() => onBlur()}
128                                                                                                  onChange={() => this.changedOtherInput()}/>
129                                                                  </div>
130                                                                 }
131                                                 </div>
132                                 );
133                 }
134                 
135                 renderOptions(val) {
136                                 return (
137                                                 <option key={val.enum} value={val.enum}>{val.title}</option>
138                                 );
139                 }
140                 
141                 
142                 renderMultiSelectOptions(values) {
143                                 let {onOtherChange} = this.props;
144                                 let optionsList = [];
145                                 if (onOtherChange) {
146                                                 optionsList = values.map(option => {
147                                                                 return {
148                                                                                 label: option.title,
149                                                                                 value: option.enum,
150                                                                 };
151                                                 }).concat([{
152                                                                 label: i18n(other.OTHER),
153                                                                 value: i18n(other.OTHER),
154                                                 }]);
155                                 }
156                                 else {
157                                                 optionsList = values.map(option => {
158                                                                 return {
159                                                                                 label: option.title,
160                                                                                 value: option.enum,
161                                                                 };
162                                                 });
163                                 }
164                                 if (optionsList.length > 0 && optionsList[0].value === '') {
165                                                 optionsList.shift();
166                                 }
167                                 return optionsList;
168                 }
169                 
170                 getValue() {
171                                 let res = '';
172                                 let {isMultiSelect} = this.props;
173                                 let {otherInputDisabled} = this.state;
174                                 
175                                 if (otherInputDisabled) {
176                                                 res =
177                                                                 isMultiSelect
178                                                                                 ? this.refs._myInput.getValue()
179                                                                                 : this.refs._myInput.value;
180                                 } else {
181                                                 res = this.refs._otherValue.value;
182                                 }
183                                 return res;
184                 }
185                 
186                 enumChanged() {
187                                 let enumValue = this.refs._myInput.value;
188                                 let {onEnumChange, isMultiSelect, onChange} = this.props;
189                                 this.setState({
190                                                 otherInputDisabled: enumValue !== other.OTHER
191                                 });
192                                 if (onEnumChange) {
193                                                 onEnumChange(isMultiSelect ? [enumValue] : enumValue);
194                                 }
195                                 
196                                 if (onChange) {
197                                                 onChange(enumValue);
198                                 }
199                                 
200                 }
201                 
202                 multiSelectEnumChanged(enumValue) {
203                                 let {onEnumChange} = this.props;
204                                 let selectedValues = enumValue.map(enumVal => {
205                                                 return enumVal.value;
206                                 });
207                                 
208                                 if (this.state.otherInputDisabled === false) {
209                                                 selectedValues.shift();
210                                 }
211                                 else if (selectedValues.includes(i18n(other.OTHER))) {
212                                                 selectedValues = [i18n(other.OTHER)];
213                                 }
214                                 
215                                 this.setState({
216                                                 otherInputDisabled: !selectedValues.includes(i18n(other.OTHER))
217                                 });
218                                 onEnumChange(selectedValues);
219                 }
220                 
221                 changedOtherInput() {
222                                 let {onOtherChange} = this.props;
223                                 onOtherChange(this.refs._otherValue.value);
224                 }
225                 
226                 componentDidUpdate() {
227                                 let {otherValue, selectedEnum, onInputChange, multiSelectedEnum} = this.props;
228                                 if (this.oldProps.otherValue !== otherValue
229                                                 || this.oldProps.selectedEnum !== selectedEnum
230                                                 || this.oldProps.multiSelectedEnum !== multiSelectedEnum) {
231                                                 this.oldProps = {
232                                                                 otherValue,
233                                                                 selectedEnum,
234                                                                 multiSelectedEnum
235                                                 };
236                                                 onInputChange();
237                                 }
238                 }
239                 
240 }
241
242 export default InputOptions;