Skip to content

Commit 5887b98

Browse files
committed
add item data type for (list of items)
1 parent 4c256dd commit 5887b98

12 files changed

Lines changed: 64 additions & 35 deletions

File tree

CHANGELOG.md

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,11 @@
1+
## [0.0.25] - 2020-06-18
2+
- Add item data type for builder, itemBuilder, childBuilder and repeat.
3+
14
## [0.0.18] - 2020-06-18
25
New features:
36
- `<param>` now has anew `superParamName` attribute which will pass the parameter to super class constructor.
47
Breaking changes:
5-
- `<if>` and `:if` will now return a null (instead of Container(width: 0, height: 0)) is the else statement, if there is no `<else>` provided.
8+
- `<if>` will now return a null (instead of Container(width: 0, height: 0)) in the else statement, if there is no `<else>` provided.
69
Fixes:
710
- Fix goto definition bug in the new vscode release.
811

docs/parameters.md

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,20 +4,31 @@
44
Parameters are used to pass data from one widget to another, and since you can't modify the widget code (generated file), the XML structure enables you to declare the parameter(s) as follow:
55
```XML
66
<MyPage controller="MyController">
7+
<!-- basic -->
78
<param type="CategoryModel" name="category" />
89

10+
<!-- required -->
911
<param type="int" name="index" required="true" />
1012
<!--
1113
final int index;
1214
MyPage({@required this.index})
1315
-->
16+
17+
<!-- default value -->
18+
<param type="int" name="index" value="0" />
19+
<!--
20+
final int index;
21+
MyPage({this.index = 0})
22+
-->
1423

24+
<!-- passing parameters to super class -->
1525
<param type="UniqueKey" name="key" superParamName="key" />
1626
<!--
1727
final UniqueKey key;
1828
MyPage({this.key}) : super(key: key);
1929
-->
2030

31+
<!-- passing parameters to super class (without initializing field) -->
2132
<param type="UniqueKey" superParamName="key" />
2233
<!-- MyPage({UniqueKey key}) : super(key: key) -->
2334
...

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
"displayName": "XML Layout for Flutter",
44
"description": "XML Layout for Flutter. Brings Angular's style to Flutter!",
55
"publisher": "WaseemDev",
6-
"version": "0.0.22",
6+
"version": "0.0.25",
77
"icon": "images/logo.png",
88
"repository": {
99
"type": "github",

src/generators/class-generator.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -220,9 +220,9 @@ class ${widgetName} extends StatelessWidget${mixinsCode} {
220220
return `
221221
222222
class ${widgetName} extends StatefulWidget {
223-
${rootWidget.params.filter(a => !!a.name).map(a => `final ${a.type ? a.type + ' ' : ''}${a.name}${a.value !== undefined ? ' = ' + a.value : ''};`).join('\n ')}
223+
${rootWidget.params.filter(a => !!a.name).map(a => `final ${a.type ? a.type + ' ' : ''}${a.name};`).join('\n ')}
224224
${widgetName}(${rootWidget.params.length ? '{': ''}
225-
${rootWidget.params.map(a => `${a.required ? '@required ' : ''}${a.name ? `this.${a.name}` : `${(a.type ? a.type + ' ' : '')}${a.superParamName}`}`).join(',\n ')}
225+
${rootWidget.params.map(a => `${a.required ? '@required ' : ''}${a.name ? `this.${a.name}` : `${(a.type ? a.type + ' ' : '')}${a.superParamName}`}${a.value !== undefined ? ' = ' + a.value : ''}`).join(',\n ')}
226226
${rootWidget.params.length ? '}': ''})${superCtor};
227227
228228
@override
@@ -246,7 +246,7 @@ class _${widgetName}State extends State<${widgetName}>${mixinsCode} {
246246
}
247247
248248
@override
249-
void dispose() {${hasController ? `\nctrl.dispose();` : ''
249+
void dispose() {${hasController ? `\n ctrl.dispose();` : ''
250250
}${routeAware ? `\n _routeObserver.unsubscribe(this);` : ''
251251
}${(controllers.length > 0 ? '\n ' : '') + controllers.filter(a => a.isPrivate).map(a => `${a.name}.dispose();`).join('\n ')}
252252
super.dispose();

src/language-features/providers/dart_completion_item_provider.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,7 @@ export class DartCompletionItemProvider implements CompletionItemProvider {
210210
this.createCustomCompletionItem(document, position, 'type', vs.CompletionItemKind.Variable),
211211
this.createCustomCompletionItem(document, position, 'name', vs.CompletionItemKind.Variable),
212212
this.createCustomCompletionItem(document, position, 'required', vs.CompletionItemKind.Variable),
213+
this.createCustomCompletionItem(document, position, 'value', vs.CompletionItemKind.Variable),
213214
this.createCustomCompletionItem(document, position, 'superParamName', vs.CompletionItemKind.Variable),
214215
],
215216
};

src/property-handlers/builder.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -360,7 +360,7 @@ suite("Builder Tests", function () {
360360
test("ListView.separated (multiple builder) with streams for both builders", function() {
361361
const xml = `
362362
<ListView :use="separated" itemCount="component.items.length">
363-
<builder name="itemBuilder" params="context, index" data="index, item of component.items | stream">
363+
<builder name="itemBuilder" params="context, index" data="index, ItemModel item of component.items | stream">
364364
<Text text="item.title" />
365365
</builder>
366366
<builder name="separatorBuilder" params="context, index" data="index, item of component.items | stream">
@@ -381,7 +381,7 @@ suite("Builder Tests", function () {
381381
return ListView.separated(
382382
itemCount: component.items.length,
383383
itemBuilder: (context, index) {
384-
final item = componentItemsValue == null || componentItemsValue.length <= index || componentItemsValue.length == 0 ? null : componentItemsValue[index];
384+
final ItemModel item = componentItemsValue == null || componentItemsValue.length <= index || componentItemsValue.length == 0 ? null : componentItemsValue[index];
385385
return Text(
386386
item.title,
387387
);

src/property-handlers/builder.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { CustomPropertyHandler, PropertyResolveResult, WidgetResolveResult } from "../providers/property-handler-provider";
22
import * as parseXml from '../parser/types';
33
import { WidgetModel, ExtraDataModel, AttributeModel, PropertyModel, AttributeInfo } from '../models/models';
4-
import { extractForLoopParams, makeTabs, sortProperties } from "../utils";
4+
import { extractForLoopParams, makeTabs, sortProperties, spaceAfter } from "../utils";
55
import { PropertyResolver } from "../resolvers/property-resolver";
66

77
export class BuilderHandler extends CustomPropertyHandler {
@@ -109,9 +109,9 @@ export class BuilderHandler extends CustomPropertyHandler {
109109
const value = properties.filter(a => a.name === 'data').map(a => a.value)[0] || '';
110110
let params = properties.filter(a => a.name === 'params').map(a => a.value)[0];
111111

112-
const { listName, indexName, itemName } = extractForLoopParams(value);
112+
const { listName, indexName, itemName, typeName } = extractForLoopParams(value);
113113
const listNameWithPipes = value.substr(value.indexOf(listName));
114-
const tempData: any = { listName, indexName, itemName, builderName, params, childWidget: childWidget, arrayOfIfWidgets };
114+
const tempData: any = { listName, indexName, itemName, typeName, builderName, params, childWidget: childWidget, arrayOfIfWidgets };
115115
// contentWidget.properties[1].value = childWidget; // todo review
116116

117117

@@ -185,7 +185,7 @@ export class BuilderHandler extends CustomPropertyHandler {
185185
// if (hasItemList && (!data.params || data.indexName)) {
186186
if (hasItemList) {
187187
code += `
188-
${tabs} final ${data.itemName} = ${data.listValueVariableName} == null || ${data.listValueVariableName}.length <= ${indexName} || ${data.listValueVariableName}.length == 0 ? null : ${data.listValueVariableName}[${indexName}];`;
188+
${tabs} final ${spaceAfter(data.typeName)}${data.itemName} = ${data.listValueVariableName} == null || ${data.listValueVariableName}.length <= ${indexName} || ${data.listValueVariableName}.length == 0 ? null : ${data.listValueVariableName}[${indexName}];`;
189189
}
190190

191191
if (ifWidgets && ifWidgets.length) {

src/property-handlers/child-builder.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { CustomPropertyHandler, PropertyResolveResult } from "../providers/property-handler-provider";
22
import * as parseXml from '../parser/types';
33
import { WidgetModel, ExtraDataModel, AttributeModel, PropertyModel } from '../models/models';
4-
import { extractForLoopParams, makeTabs, sortProperties } from "../utils";
4+
import { extractForLoopParams, makeTabs, sortProperties, spaceAfter } from "../utils";
55
import { PropertyResolver } from "../resolvers/property-resolver";
66

77
export class ChildBuilderHandler extends CustomPropertyHandler {
@@ -21,8 +21,8 @@ export class ChildBuilderHandler extends CustomPropertyHandler {
2121
let wrapperWidget: WidgetModel | null = null;
2222
let extraData: ExtraDataModel | null = null;
2323

24-
const { listName, indexName, itemName } = extractForLoopParams(attr.value);
25-
const tempData: any = { listName, indexName, itemName };
24+
const { listName, indexName, itemName, typeName } = extractForLoopParams(attr.value);
25+
const tempData: any = { listName, indexName, itemName, typeName };
2626
const listNameWithPipes = attr.value.substr(attr.value.indexOf(listName));
2727
const contentWidget: WidgetModel = {
2828
controllers: [],
@@ -79,7 +79,7 @@ export class ChildBuilderHandler extends CustomPropertyHandler {
7979
}
8080

8181
code +=
82-
`${tabs}children: WidgetHelpers.mapToWidgetList(${data.listValueVariableName}, (${data.itemName || 'item'}, ${data.indexName || 'index'}) {
82+
`${tabs}children: WidgetHelpers.mapToWidgetList(${data.listValueVariableName}, (${spaceAfter(data.typeName)}${data.itemName || 'item'}, ${data.indexName || 'index'}) {
8383
${tabs} return ${generateChildWidgetCode(childWidget, tabsLevel + 1)};
8484
${tabs}})`;
8585

src/property-handlers/item-builder.test.ts

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -4,15 +4,15 @@ suite("ItemBuilder Tests", function () {
44

55
test("basic", function() {
66
const xml = `
7-
<ListView :use="builder" :itemBuilder="item of component.items">
7+
<ListView :use="builder" :itemBuilder="int item of component.items">
88
<Text text="item.title" />
99
</ListView>
1010
`;
1111

1212
const expected = `
1313
ListView.builder(
1414
itemBuilder: (BuildContext context, int index) {
15-
final item = component.items == null || component.items.length <= index || component.items.length == 0 ? null : component.items[index];
15+
final int item = component.items == null || component.items.length <= index || component.items.length == 0 ? null : component.items[index];
1616
return Text(
1717
item.title,
1818
);
@@ -27,15 +27,15 @@ suite("ItemBuilder Tests", function () {
2727

2828
test("with specified index", function() {
2929
const xml = `
30-
<ListView :use="builder" :itemBuilder="myIndex, item of component.items">
30+
<ListView :use="builder" :itemBuilder="myIndex, ItemModel item of component.items">
3131
<Text text="item.title" />
3232
</ListView>
3333
`;
3434

3535
const expected = `
3636
ListView.builder(
3737
itemBuilder: (BuildContext context, int myIndex) {
38-
final item = component.items == null || component.items.length <= myIndex || component.items.length == 0 ? null : component.items[myIndex];
38+
final ItemModel item = component.items == null || component.items.length <= myIndex || component.items.length == 0 ? null : component.items[myIndex];
3939
return Text(
4040
item.title,
4141
);
@@ -49,7 +49,7 @@ suite("ItemBuilder Tests", function () {
4949

5050
test("with stream", function() {
5151
const xml = `
52-
<ListView :use="builder" :itemBuilder="item of component.items | stream">
52+
<ListView :use="builder" :itemBuilder="ItemModel item of component.items | stream">
5353
<Text text="item.title" />
5454
</ListView>
5555
`;
@@ -65,7 +65,7 @@ suite("ItemBuilder Tests", function () {
6565
}
6666
return ListView.builder(
6767
itemBuilder: (BuildContext context, int index) {
68-
final item = componentItemsValue == null || componentItemsValue.length <= index || componentItemsValue.length == 0 ? null : componentItemsValue[index];
68+
final ItemModel item = componentItemsValue == null || componentItemsValue.length <= index || componentItemsValue.length == 0 ? null : componentItemsValue[index];
6969
return Text(
7070
item.title,
7171
);
@@ -188,7 +188,7 @@ suite("ItemBuilder Tests", function () {
188188
test("itemBuilder element", function() {
189189
const xml = `
190190
<ListView :use="builder">
191-
<itemBuilder data="item of component.items">
191+
<itemBuilder data="ItemModel item of component.items">
192192
<Text text="item.title" />
193193
</itemBuilder>
194194
</ListView>
@@ -197,7 +197,7 @@ suite("ItemBuilder Tests", function () {
197197
const expected = `
198198
ListView.builder(
199199
itemBuilder: (BuildContext context, int index) {
200-
final item = component.items == null || component.items.length <= index || component.items.length == 0 ? null : component.items[index];
200+
final ItemModel item = component.items == null || component.items.length <= index || component.items.length == 0 ? null : component.items[index];
201201
return Text(
202202
item.title,
203203
);

src/property-handlers/repeat.test.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -80,7 +80,7 @@ suite("Repeat Tests", function () {
8080
test("multiple inside column", function() {
8181
const xml = `
8282
<Column>
83-
<Text :repeat="item of items" />
83+
<Text :repeat="int item of items" />
8484
<Text :repeat="item of items" />
8585
<Text :repeat="item of items" />
8686
</Column>
@@ -89,7 +89,7 @@ suite("Repeat Tests", function () {
8989
const expected = `
9090
Column(
9191
children: [
92-
...WidgetHelpers.mapToWidgetList(items, (item, index) {
92+
...WidgetHelpers.mapToWidgetList(items, (int item, index) {
9393
return Text(
9494
9595
);
@@ -119,7 +119,7 @@ suite("Repeat Tests", function () {
119119
const xml = `
120120
<PopupMenuButton>
121121
<builder name="itemBuilder">
122-
<PopupMenuItem :repeat="menuItem of component.menuItems" value="menuItem">
122+
<PopupMenuItem :repeat="MenuItem menuItem of component.menuItems" value="menuItem">
123123
<Text text="menuItem.title" />
124124
</PopupMenuItem>
125125
</builder>
@@ -129,7 +129,7 @@ suite("Repeat Tests", function () {
129129
const expected = `
130130
PopupMenuButton(
131131
itemBuilder: (BuildContext context) {
132-
return WidgetHelpers.mapToWidgetList(component.menuItems, (menuItem, index) {
132+
return WidgetHelpers.mapToWidgetList(component.menuItems, (MenuItem menuItem, index) {
133133
return PopupMenuItem(
134134
value: menuItem,
135135
child: Text(

0 commit comments

Comments
 (0)