Skip to content

Commit 386ef14

Browse files
authored
Merge pull request #19 from carfup/anycompositefields
v1.3.0.0 : AnyCompositefields
2 parents a3b829f + 9028cf3 commit 386ef14

17 files changed

Lines changed: 6624 additions & 3 deletions

AnyCompositeFields/.gitignore

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
2+
3+
# dependencies
4+
/node_modules
5+
6+
# generated directory
7+
**/generated
8+
9+
# output directory
10+
/out
11+
12+
# msbuild output directories
13+
/bin
14+
/obj
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<manifest>
3+
<control namespace="Carfup" constructor="AnyCompositeFIelds" version="0.0.61" display-name-key="Carfup.AnyCompositeFIelds" description-key="AnyCompositeFIelds will allow you to display any stack of fields as composite rendering." control-type="standard" preview-image="img/preview.png">
4+
<!-- property node identifies a specific, configurable piece of data that the control expects from CDS -->
5+
<property name="FieldToAttachControl" display-name-key="FieldToAttachControl" description-key="Field to attach the control to" of-type-group="strings" usage="bound" required="true" />
6+
<property name="separator" display-name-key="Values separator" description-key="Separator to split the mapped values (for a space, put %20)" of-type="SingleLine.Text" usage="input" required="true" default-value="%20" />
7+
<property name="returnCompositeValue" display-name-key="Return the composite value ?" description-key="Do you want to retrieve the composite value ?" of-type="Enum" usage="input" required="true" default-value="true">
8+
<value name="true" display-name-key="True" description-key="true">true</value>
9+
<value name="false" display-name-key="False" description-key="false">false</value>
10+
</property>
11+
<property name="field1" display-name-key="Field 1" description-key="Field 1 to be used" of-type-group="strings" usage="bound" required="true" />
12+
<property name="field2" display-name-key="Field 2" description-key="Field 2 to be used" of-type-group="strings" usage="bound" required="true" />
13+
<property name="field3" display-name-key="Field 3" description-key="Field 3 to be used" of-type-group="strings" usage="bound" required="false" />
14+
<property name="field4" display-name-key="Field 4" description-key="Field 4 to be used" of-type-group="strings" usage="bound" required="false" />
15+
<property name="field5" display-name-key="Field 5" description-key="Field 5 to be used" of-type-group="strings" usage="bound" required="false" />
16+
<property name="field6" display-name-key="Field 6" description-key="Field 6 to be used" of-type-group="strings" usage="bound" required="false" />
17+
<property name="field7" display-name-key="Field 7" description-key="Field 7 to be used" of-type-group="strings" usage="bound" required="false" />
18+
<property name="field8" display-name-key="Field 8" description-key="Field 8 to be used" of-type-group="strings" usage="bound" required="false" />
19+
<type-group name="strings">
20+
<type>SingleLine.Email</type>
21+
<type>SingleLine.Text</type>
22+
<type>SingleLine.Phone</type>
23+
</type-group>
24+
<!--
25+
Property node's of-type attribute can be of-type-group attribute.
26+
Example:
27+
<type-group name="numbers">
28+
<type>Whole.None</type>
29+
<type>Currency</type>
30+
<type>FP</type>
31+
<type>Decimal</type>
32+
</type-group>
33+
<property name="sampleProperty" display-name-key="Property_Display_Key" description-key="Property_Desc_Key" of-type-group="numbers" usage="bound" required="true" />
34+
-->
35+
<resources>
36+
<code path="index.ts" order="1" />
37+
<resx path="strings/AnyCompositeFIelds.1033.resx" version="1.0.0" />
38+
<resx path="strings/AnyCompositeFIelds.1036.resx" version="1.0.0" />
39+
<!-- UNCOMMENT TO ADD MORE RESOURCES
40+
<css path="css/AnyCompositeFIelds.css" order="1" />
41+
<resx path="strings/AnyCompositeFIelds.1033.resx" version="1.0.0" />
42+
-->
43+
</resources>
44+
<feature-usage>
45+
<uses-feature name="WebAPI" required="true" />
46+
</feature-usage>
47+
<!-- UNCOMMENT TO ENABLE THE SPECIFIED API
48+
<feature-usage>
49+
<uses-feature name="Device.captureAudio" required="true" />
50+
<uses-feature name="Device.captureImage" required="true" />
51+
<uses-feature name="Device.captureVideo" required="true" />
52+
<uses-feature name="Device.getBarcodeValue" required="true" />
53+
<uses-feature name="Device.getCurrentPosition" required="true" />
54+
<uses-feature name="Device.pickFile" required="true" />
55+
<uses-feature name="Utility" required="true" />
56+
<uses-feature name="WebAPI" required="true" />
57+
</feature-usage>
58+
-->
59+
</control>
60+
</manifest>
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
export class CompositeValue{
2+
public separator : string;
3+
public returnCompositeValue : boolean;
4+
public fullValue : string;
5+
public fieldValue1? : any;
6+
public fieldValue2? : any;
7+
public fieldValue3? : any;
8+
public fieldValue4? : any;
9+
public fieldValue5? : any;
10+
public fieldValue6? : any;
11+
public fieldValue7? : any;
12+
public fieldValue8? : any;
13+
}
Lines changed: 160 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,160 @@
1+
import * as React from 'react';
2+
import { Callout, Stack, TextField, DefaultButton, BaseButton, Button, IStackStyles, ITextFieldStyles, ICalloutContentStyles, DirectionalHint } from 'office-ui-fabric-react';
3+
import { CompositeValue } from '../EntitiesDefinition';
4+
5+
export interface ICompositeControlProps {
6+
disabled : boolean;
7+
visible: boolean;
8+
compositeValue : CompositeValue;
9+
doneLabel : string;
10+
randNumber: number;
11+
onClickedDone : (compositeValue? : CompositeValue) => void;
12+
}
13+
14+
export interface IBCompositeControlState {
15+
showCallout: boolean,
16+
compositeValue : CompositeValue;
17+
}
18+
19+
const stackStyles: Partial<IStackStyles> = { root: { width: "100%" } };
20+
const textFieldStyles: Partial<ITextFieldStyles> = { root: { width: "100%" } };
21+
const calloutStyles: Partial<ICalloutContentStyles> = { root: { width: "300px" } };
22+
23+
export default class CompositeControl extends React.Component<ICompositeControlProps, IBCompositeControlState> {
24+
constructor(props: ICompositeControlProps) {
25+
super(props);
26+
this.state = {
27+
showCallout : false,
28+
compositeValue : this.props.compositeValue,
29+
};
30+
}
31+
32+
33+
34+
render(){
35+
return (
36+
<Stack horizontal id="acf_compositestack" styles={stackStyles}>
37+
<TextField
38+
value={this.state.compositeValue.fullValue}
39+
readOnly={true}
40+
onClick={() => this.setState({ showCallout : true }) }
41+
styles={textFieldStyles}
42+
id={"acf_compositeFullValue"+this.props.randNumber}
43+
/>
44+
{this.state.showCallout && (
45+
<Callout
46+
target={"#acf_compositeFullValue"+this.props.randNumber}
47+
onDismiss={() => this.setState({ showCallout : false }) }
48+
styles={calloutStyles}
49+
directionalHint={DirectionalHint.topCenter}
50+
>
51+
<Stack style={{margin : "10px"}}>
52+
53+
{this.state.compositeValue.fieldValue1.attributes.LogicalName != undefined && <TextField
54+
value={this.state.compositeValue.fieldValue1.raw!}
55+
label={this.state.compositeValue.fieldValue1.attributes.DisplayName}
56+
id={"acf_fieldValue1"}
57+
onChange={this.onChangeField}
58+
disabled={this.props.disabled || this.state.compositeValue.fieldValue1.disabled!}
59+
styles={textFieldStyles}
60+
/>}
61+
{this.state.compositeValue.fieldValue2.attributes.LogicalName != undefined && <TextField
62+
value={this.state.compositeValue.fieldValue2.raw!}
63+
label={this.state.compositeValue.fieldValue2.attributes.DisplayName}
64+
id={"acf_fieldValue2"}
65+
onChange={this.onChangeField}
66+
disabled={this.props.disabled || this.state.compositeValue.fieldValue2.disabled!}
67+
styles={textFieldStyles}
68+
/>}
69+
{this.state.compositeValue.fieldValue3.attributes.LogicalName != undefined && <TextField
70+
value={this.state.compositeValue.fieldValue3.raw!}
71+
label={this.state.compositeValue.fieldValue3.attributes.DisplayName}
72+
id={"acf_fieldValue3"}
73+
onChange={this.onChangeField}
74+
disabled={this.props.disabled || this.state.compositeValue.fieldValue3.disabled!}
75+
styles={textFieldStyles}
76+
/>}
77+
{this.state.compositeValue.fieldValue4.attributes.LogicalName != undefined && <TextField
78+
value={this.state.compositeValue.fieldValue4.raw!}
79+
label={this.state.compositeValue.fieldValue4.attributes.DisplayName}
80+
id={"acf_fieldValue4"}
81+
onChange={this.onChangeField}
82+
disabled={this.props.disabled || this.state.compositeValue.fieldValue4.disabled!}
83+
styles={textFieldStyles}
84+
/>}
85+
{this.state.compositeValue.fieldValue5.attributes.LogicalName != undefined && <TextField
86+
value={this.state.compositeValue.fieldValue5.raw!}
87+
label={this.state.compositeValue.fieldValue5.attributes.DisplayName}
88+
id={"acf_fieldValue5"}
89+
onChange={this.onChangeField}
90+
disabled={this.props.disabled || this.state.compositeValue.fieldValue5.disabled!}
91+
styles={textFieldStyles}
92+
/>}
93+
{this.state.compositeValue.fieldValue6.attributes.LogicalName != undefined && <TextField
94+
value={this.state.compositeValue.fieldValue6.raw!}
95+
label={this.state.compositeValue.fieldValue6.attributes.DisplayName}
96+
id={"acf_fieldValue6"}
97+
onChange={this.onChangeField}
98+
disabled={this.props.disabled || this.state.compositeValue.fieldValue6.disabled!}
99+
styles={textFieldStyles}
100+
/>}
101+
{this.state.compositeValue.fieldValue7.attributes.LogicalName != undefined && <TextField
102+
value={this.state.compositeValue.fieldValue7.raw!}
103+
label={this.state.compositeValue.fieldValue7.attributes.DisplayName}
104+
id={"acf_fieldValue7"}
105+
onChange={this.onChangeField}
106+
disabled={this.props.disabled || this.state.compositeValue.fieldValue7.disabled!}
107+
styles={textFieldStyles}
108+
/>}
109+
{this.state.compositeValue.fieldValue8.attributes.LogicalName != undefined && <TextField
110+
value={this.state.compositeValue.fieldValue8.raw!}
111+
label={this.state.compositeValue.fieldValue8.attributes.DisplayName}
112+
id={"acf_fieldValue8"}
113+
onChange={this.onChangeField}
114+
disabled={this.props.disabled || this.state.compositeValue.fieldValue8.disabled!}
115+
styles={textFieldStyles}
116+
/>}
117+
118+
<DefaultButton text={this.props.doneLabel} onClick={this.onClick} style={{marginTop:'10px',alignSelf: "flex-end"}}/>
119+
</Stack>
120+
121+
</Callout>
122+
)}
123+
</Stack>
124+
);
125+
}
126+
127+
private onChangeField = (event: React.FormEvent<HTMLInputElement | HTMLTextAreaElement>, newValue?: string | undefined) : void => {
128+
// @ts-ignore
129+
let target = event.target.id.replace('acf_', '');
130+
const compositeValue = {...this.state}.compositeValue;
131+
// @ts-ignore
132+
compositeValue[target].raw = newValue!;
133+
this.setState({compositeValue : compositeValue});
134+
}
135+
136+
private onClick = (event: React.MouseEvent<HTMLDivElement | HTMLAnchorElement | HTMLButtonElement | BaseButton | Button | HTMLSpanElement, MouseEvent>) : void => {
137+
const compositeValue = {...this.state}.compositeValue;
138+
this.buildFullValue(compositeValue);
139+
this.setState({showCallout : false});
140+
this.props.onClickedDone(this.state.compositeValue);
141+
}
142+
143+
private buildFullValue = (compositeValue : CompositeValue) : void => {
144+
let arrayValues = [];
145+
146+
let i = 1;
147+
for(i ; i<9; i++){
148+
// @ts-ignore
149+
if(compositeValue["fieldValue"+i]!.raw!){
150+
// @ts-ignore
151+
arrayValues.push(compositeValue["fieldValue"+i].raw);
152+
}
153+
}
154+
155+
compositeValue.fullValue = arrayValues.join(compositeValue.separator);
156+
157+
this.setState({compositeValue : compositeValue});
158+
}
159+
};
160+
5.49 KB
Loading

0 commit comments

Comments
 (0)