Skip to content

Commit 5318b8e

Browse files
authored
Codegen event arg methods (#173)
* Codegen event arg methods * Change files * update version * Produce typings for event args, fix bug with some events not being defined when thy exist in WUX and MUX simultaneously
1 parent 2f0f098 commit 5318b8e

26 files changed

+1774
-398
lines changed

USAGE.md

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -455,9 +455,26 @@ In order to enable Direct debugging for your app, make sure that your App.cpp/Ap
455455
InstanceSettings.UseWebDebugger = false;
456456
```
457457

458+
# Calling methods on XAML Event Args
459+
By default, only XAML properties of event arg objects are exposed back. Some event args support calling methods on them.
460+
See `eventArgMethods` in Windows.UI.Xaml.json.
461+
462+
Example:
463+
```jsx
464+
/// assume there is a MenuFlyout _menuRef defined.
465+
<TextBlock
466+
text="Hello"
467+
onContextRequested={e => {
468+
const tag = findNodeHandle(_tbRef.current);
469+
const { point, returnValue } = e.nativeEvent.args.TryGetPosition(tag);
470+
MenuFlyout.ShowAt(_menuRef, {point: point});
471+
}}
472+
/>
473+
```
474+
458475
# Calling methods on XAML objects ("commands")
459476
Some types support custom commands to expose some functionality of the underlying platform.
460-
For example, this allows calling the `MediaPlayerElement.Play()` method in response to some other action, or programatically showing a flyout menu:
477+
For example, this allows calling the programatically showing a flyout menu:
461478

462479
```jsx
463480
const _tbRef = React.useRef<TextBlock>(null);

examplenuget/App.js renamed to examplenuget/App.tsx

Lines changed: 49 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
*/
88

99
import React, {useRef} from 'react';
10-
import type {Node} from 'react';
10+
1111
import {
1212
findNodeHandle,
1313
SafeAreaView,
@@ -24,6 +24,13 @@ import {
2424
MenuFlyout,
2525
MenuFlyoutItem,
2626
TextBlock,
27+
WinUI,
28+
MediaPlayerElement,
29+
Button,
30+
ContentDialogState,
31+
ContentDialog,
32+
ContentDialogButton,
33+
ContentDialogResult,
2734
} from 'react-native-xaml';
2835
import {
2936
Colors,
@@ -33,7 +40,7 @@ import {
3340
ReloadInstructions,
3441
} from 'react-native/Libraries/NewAppScreen';
3542

36-
const Section = ({children, title}): Node => {
43+
const Section = ({children, title}) => {
3744
const isDarkMode = useColorScheme() === 'dark';
3845
return (
3946
<View style={styles.sectionContainer}>
@@ -59,7 +66,7 @@ const Section = ({children, title}): Node => {
5966
);
6067
};
6168

62-
const App: () => Node = () => {
69+
const App = () => {
6370
const isDarkMode = useColorScheme() === 'dark';
6471

6572
const backgroundStyle = {
@@ -68,8 +75,11 @@ const App: () => Node = () => {
6875

6976
const menu = useRef<MenuFlyout>(null);
7077
const _tbRef = React.useRef<TextBlock>(null);
78+
const _mpRef = React.useRef<MediaPlayerElement>(null);
79+
const [x, setX] = React.useState("100");
80+
81+
const [showState, setShowState] = React.useState(ContentDialogState.Hidden);
7182

72-
const [x, setX] = React.useState(100);
7383

7484
return (
7585
<SafeAreaView style={backgroundStyle}>
@@ -83,21 +93,50 @@ const App: () => Node = () => {
8393
backgroundColor: isDarkMode ? Colors.black : Colors.white,
8494
}}>
8595
<TextBox
86-
text={x}
96+
text={`x`}
8797
onBeforeTextChanging={e => {
88-
setX(e.nativeEvent.args.newText);
98+
if (e.nativeEvent.args) {
99+
setX(e.nativeEvent.args.newText);
100+
}
89101
}}
90102
/>
103+
104+
<Button
105+
onTapped={a => {setShowState(ContentDialogState.Popup);}}
106+
content="click to open a ContentDialog" />
107+
108+
<ContentDialog
109+
showState={showState}
110+
defaultButton={ContentDialogButton.Close}
111+
title="the title"
112+
content="this is the content"
113+
closeButtonText="close"
114+
primaryButtonText="primary"
115+
secondaryButtonText="secondary"
116+
onPrimaryButtonClick={e => {
117+
alert('primary');
118+
}}
119+
onSecondaryButtonClick={e => {
120+
alert('secondary');
121+
}}
122+
onClosed={e => {
123+
setShowState(ContentDialogState.Hidden)
124+
alert(JSON.stringify(e.nativeEvent.args));
125+
}}
126+
/>
127+
128+
91129
<TextBlock
92130
text="Hello"
93131
onTapped={e => {
94-
MenuFlyout.ShowAt(menu, {point: {x: x, y: 42}});
132+
MenuFlyout.ShowAt(menu, {point: {x: parseInt(x), y: 42}});
95133
}}
96134
ref={t => {
97135
_tbRef.current = t;
98136
}}
99137
onContextRequested={e => {
100138
const tag = findNodeHandle(_tbRef.current);
139+
101140
const { point, returnValue } = e.nativeEvent.args.TryGetPosition(tag);
102141
MenuFlyout.ShowAt(menu, { point: point });
103142
}}
@@ -110,6 +149,9 @@ const App: () => Node = () => {
110149
<MenuFlyoutItem text="menu option" />
111150
</MenuFlyout>
112151
</TextBlock>
152+
<WinUI.ColorPicker onColorChanged={e => {
153+
alert(JSON.stringify(e.nativeEvent.args.newColor));
154+
}} />
113155
</View>
114156
</ScrollView>
115157
</SafeAreaView>

package/CHANGELOG.json

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,21 @@
11
{
22
"name": "react-native-xaml",
33
"entries": [
4+
{
5+
"date": "Mon, 24 Jan 2022 21:16:18 GMT",
6+
"tag": "react-native-xaml_v0.0.57",
7+
"version": "0.0.57",
8+
"comments": {
9+
"patch": [
10+
{
11+
"author": "[email protected]",
12+
"package": "react-native-xaml",
13+
"comment": "Codegen event arg methods",
14+
"commit": "3db633ca67dedfb118647da17fca03d8eb5795c0"
15+
}
16+
]
17+
}
18+
},
419
{
520
"date": "Fri, 21 Jan 2022 17:41:16 GMT",
621
"tag": "react-native-xaml_v0.0.56",

package/CHANGELOG.md

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,17 @@
11
# Change Log - react-native-xaml
22

3-
This log was last generated on Fri, 21 Jan 2022 17:41:16 GMT and should not be manually modified.
3+
This log was last generated on Mon, 24 Jan 2022 21:16:18 GMT and should not be manually modified.
44

55
<!-- Start content -->
66

7+
## 0.0.57
8+
9+
Mon, 24 Jan 2022 21:16:18 GMT
10+
11+
### Patches
12+
13+
- Codegen event arg methods ([email protected])
14+
715
## 0.0.56
816

917
Fri, 21 Jan 2022 17:41:16 GMT

package/Codegen/EventArgsTypeProperties.cs

Lines changed: 88 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -161,7 +161,94 @@ struct EventArgsProperty {
161161

162162
#line default
163163
#line hidden
164-
this.Write("};");
164+
this.Write(@"};
165+
166+
struct EventArgsMethod {
167+
const char* const name;
168+
169+
using isType_t = bool (*) (const winrt::Windows::Foundation::IInspectable& ea);
170+
const isType_t isType;
171+
172+
using getter_t = facebook::jsi::Value(*) (facebook::jsi::Runtime& rt, std::shared_ptr<XamlObject> thisVal, const facebook::jsi::Value* args, size_t count);
173+
const getter_t getter;
174+
};
175+
176+
");
177+
178+
#line 49 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
179+
foreach (var t in Util.eventArgsMethods) {
180+
foreach (var m in t.Value) {
181+
182+
183+
#line default
184+
#line hidden
185+
this.Write("facebook::jsi::Value ");
186+
187+
#line 52 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
188+
this.Write(this.ToStringHelper.ToStringWithCulture(t.Key.Replace(".", "_")));
189+
190+
#line default
191+
#line hidden
192+
this.Write("_");
193+
194+
#line 52 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
195+
this.Write(this.ToStringHelper.ToStringWithCulture(m));
196+
197+
#line default
198+
#line hidden
199+
this.Write("(facebook::jsi::Runtime& rt, std::shared_ptr<XamlObject> thisVal, const facebook:" +
200+
":jsi::Value* args, size_t count);\r\n");
201+
202+
#line 53 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
203+
} }
204+
205+
#line default
206+
#line hidden
207+
this.Write("\r\nconst EventArgsMethod eventArgsMethods[] = {\r\n");
208+
209+
#line 56 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
210+
foreach (var t in Util.eventArgsMethods) {
211+
foreach (var m in t.Value) {
212+
213+
214+
#line default
215+
#line hidden
216+
this.Write(" { \"");
217+
218+
#line 59 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
219+
this.Write(this.ToStringHelper.ToStringWithCulture(m));
220+
221+
#line default
222+
#line hidden
223+
this.Write("\", IsType<");
224+
225+
#line 59 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
226+
this.Write(this.ToStringHelper.ToStringWithCulture(Util.GetCppWinRTType(t.Key)));
227+
228+
#line default
229+
#line hidden
230+
this.Write(">, ");
231+
232+
#line 59 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
233+
this.Write(this.ToStringHelper.ToStringWithCulture(t.Key.Replace(".", "_")));
234+
235+
#line default
236+
#line hidden
237+
this.Write("_");
238+
239+
#line 59 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
240+
this.Write(this.ToStringHelper.ToStringWithCulture(m));
241+
242+
#line default
243+
#line hidden
244+
this.Write(" },\r\n");
245+
246+
#line 60 "C:\Users\asklar\source\repos\react-native-xaml\package\Codegen\EventArgsTypeProperties.tt"
247+
} }
248+
249+
#line default
250+
#line hidden
251+
this.Write("};\r\n");
165252
return this.GenerationEnvironment.ToString();
166253
}
167254
}

package/Codegen/EventArgsTypeProperties.tt

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,4 +34,28 @@ if (prop.Property != null) { #>
3434
{ "<#= Util.ToJsName(prop.Name) #>", IsType<<#= Util.GetCppWinRTType(prop.DeclaringType) #>>, [](const winrt::Windows::Foundation::IInspectable& obj) { auto ea = obj.as<<#= Util.GetCppWinRTType(prop.DeclaringType) #>>(); return Get<#= prop.Name #>_<#= prop.DeclaringType.GetName() #>(); },
3535
<#} #>
3636
<# } #>
37-
};
37+
};
38+
39+
struct EventArgsMethod {
40+
const char* const name;
41+
42+
using isType_t = bool (*) (const winrt::Windows::Foundation::IInspectable& ea);
43+
const isType_t isType;
44+
45+
using getter_t = facebook::jsi::Value(*) (facebook::jsi::Runtime& rt, std::shared_ptr<XamlObject> thisVal, const facebook::jsi::Value* args, size_t count);
46+
const getter_t getter;
47+
};
48+
49+
<# foreach (var t in Util.eventArgsMethods) {
50+
foreach (var m in t.Value) {
51+
#>
52+
facebook::jsi::Value <#= t.Key.Replace(".", "_") #>_<#= m #>(facebook::jsi::Runtime& rt, std::shared_ptr<XamlObject> thisVal, const facebook::jsi::Value* args, size_t count);
53+
<# } } #>
54+
55+
const EventArgsMethod eventArgsMethods[] = {
56+
<# foreach (var t in Util.eventArgsMethods) {
57+
foreach (var m in t.Value) {
58+
#>
59+
{ "<#= m #>", IsType<<#= Util.GetCppWinRTType(t.Key) #>>, <#= t.Key.Replace(".", "_") #>_<#= m #> },
60+
<# } } #>
61+
};

package/Codegen/Model.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,9 @@ public bool Equals(MrTypeAndMemberBase that, MrTypeAndMemberBase other)
107107
}
108108

109109
return n1 == n2;
110+
} else if (that is MrType t1 && other is MrType t2)
111+
{
112+
return t1.GetFullName() == t2.GetFullName();
110113
}
111114
return that.GetName() == other.GetName();
112115
}

0 commit comments

Comments
 (0)