Skip to content

Commit 0445703

Browse files
authored
Merge branch 'master' into some-lint-fixes
2 parents d339a29 + 1ebd91a commit 0445703

File tree

5 files changed

+201
-24
lines changed

5 files changed

+201
-24
lines changed

projects/igniteui-angular/migrations/update-12_0_0/changes/inputs.json

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,22 @@
7272
"selector": "igx-tab-item",
7373
"type": "component"
7474
}
75+
},
76+
{
77+
"name": "class",
78+
"remove": true,
79+
"owner": {
80+
"selector": "igx-tab-item",
81+
"type": "component"
82+
}
83+
},
84+
{
85+
"name": "class",
86+
"remove": true,
87+
"owner": {
88+
"selector": "igx-bottom-nav-item",
89+
"type": "component"
90+
}
7591
}
7692
]
7793
}

projects/igniteui-angular/migrations/update-12_0_0/index.spec.ts

Lines changed: 98 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ $theme: igx-avatar-theme(
9494
appTree.create(
9595
'/testSrc/appPrefix/component/custom.component.html', `
9696
<igx-tabs type="contentFit" [selectedIndex]="0">
97-
<igx-tabs-group label="Tab1" icon="home">
97+
<igx-tabs-group label="Tab1" icon="home" class="tabgroup">
9898
<div>Some Content</div>
9999
</igx-tabs-group>
100100
</igx-tabs>`);
@@ -110,7 +110,7 @@ ${noteText}
110110
<igx-icon igxTabHeaderIcon>home</igx-icon>
111111
<span igxTabHeaderLabel>Tab1</span>
112112
</igx-tab-header>
113-
<igx-tab-content>
113+
<igx-tab-content class="tabgroup">
114114
<div>Some Content</div>
115115
</igx-tab-content>
116116
</igx-tab-item>
@@ -121,7 +121,7 @@ ${noteText}
121121
appTree.create(
122122
'/testSrc/appPrefix/component/custom.component.html', `
123123
<igx-tabs type="fixed">
124-
<igx-tab-item label="Tab1" icon="folder" routerLink="view1" [isSelected]="true">
124+
<igx-tab-item label="Tab1" icon="folder" routerLink="view1" [isSelected]="true" class="tabitem">
125125
</igx-tab-item>
126126
</igx-tabs>`);
127127
const tree = await schematicRunner.runSchematicAsync('migration-20', {}, appTree)
@@ -132,14 +132,70 @@ ${noteText}
132132
${noteText}
133133
<igx-tabs tabAlignment="justify">
134134
<igx-tab-item [selected]="true">
135-
<igx-tab-header routerLink="view1">
135+
<igx-tab-header routerLink="view1" class="tabitem">
136136
<igx-icon igxTabHeaderIcon>folder</igx-icon>
137137
<span igxTabHeaderLabel>Tab1</span>
138138
</igx-tab-header>
139139
</igx-tab-item>
140140
</igx-tabs>`);
141141
});
142142

143+
it('Should not create igx-[tab|botton-nav]-content if it\'s already present', async () => {
144+
appTree.create(
145+
'/testSrc/appPrefix/component/custom.component.html', `
146+
<igx-tabs #tabs1>
147+
<igx-tab-item>
148+
<igx-tab-header>
149+
<span igxTabHeaderLabel>Home</span>
150+
</igx-tab-header>
151+
<igx-tab-content>Home content.</igx-tab-content>
152+
</igx-tab-item>
153+
</igx-tabs>
154+
<!--BottomNav-->
155+
<igx-bottom-nav>
156+
<igx-bottom-nav-item>
157+
<igx-bottom-nav-header>
158+
<igx-icon igxBottomNavHeaderIcon>library_music</igx-icon>
159+
<span igxBottomNavHeaderLabel>Songs</span>
160+
</igx-bottom-nav-header>
161+
<igx-bottom-nav-content>
162+
<div class="item" *ngFor="let song of songsList">
163+
<span class="item-line1">{{song.title}}</span><br/>
164+
<span class="item-line2">{{song.artist}}</span>
165+
</div>
166+
</igx-bottom-nav-content>
167+
</igx-bottom-nav-item>
168+
</igx-bottom-nav>`);
169+
const tree = await schematicRunner.runSchematicAsync('migration-20', {}, appTree)
170+
.toPromise();
171+
172+
expect(tree.readContent('/testSrc/appPrefix/component/custom.component.html'))
173+
.toEqual(`
174+
<igx-tabs #tabs1>
175+
<igx-tab-item>
176+
<igx-tab-header>
177+
<span igxTabHeaderLabel>Home</span>
178+
</igx-tab-header>
179+
<igx-tab-content>Home content.</igx-tab-content>
180+
</igx-tab-item>
181+
</igx-tabs>
182+
<!--BottomNav-->
183+
<igx-bottom-nav>
184+
<igx-bottom-nav-item>
185+
<igx-bottom-nav-header>
186+
<igx-icon igxBottomNavHeaderIcon>library_music</igx-icon>
187+
<span igxBottomNavHeaderLabel>Songs</span>
188+
</igx-bottom-nav-header>
189+
<igx-bottom-nav-content>
190+
<div class="item" *ngFor="let song of songsList">
191+
<span class="item-line1">{{song.title}}</span><br/>
192+
<span class="item-line2">{{song.artist}}</span>
193+
</div>
194+
</igx-bottom-nav-content>
195+
</igx-bottom-nav-item>
196+
</igx-bottom-nav>`);
197+
});
198+
143199
it('Should insert ng-template content into igx-tab-header', async () => {
144200
appTree.create(
145201
'/testSrc/appPrefix/component/custom.component.html', `
@@ -174,7 +230,7 @@ ${noteText}
174230
appTree.create(
175231
'/testSrc/appPrefix/component/custom.component.html', `
176232
<igx-bottom-nav>
177-
<igx-tab-panel label="Tab1" icon="folder" [isSelected]="true">
233+
<igx-tab-panel label="Tab1" icon="folder" [isSelected]="true" class="tabpanel">
178234
Some Content
179235
</igx-tab-panel>
180236
</igx-bottom-nav>`);
@@ -190,7 +246,7 @@ ${noteText}
190246
<igx-icon igxBottomNavHeaderIcon>folder</igx-icon>
191247
<span igxBottomNavHeaderLabel>Tab1</span>
192248
</igx-bottom-nav-header>
193-
<igx-bottom-nav-content>
249+
<igx-bottom-nav-content class="tabpanel">
194250
Some Content
195251
</igx-bottom-nav-content>
196252
</igx-bottom-nav-item>
@@ -201,7 +257,7 @@ Some Content
201257
appTree.create(
202258
'/testSrc/appPrefix/component/custom.component.html', `
203259
<igx-bottom-nav>
204-
<igx-tab label="Tab1" icon="folder" routerLink="view1">
260+
<igx-tab label="Tab1" icon="folder" routerLink="view1" class="igxtab">
205261
</igx-tab>
206262
</igx-bottom-nav>`);
207263
const tree = await schematicRunner.runSchematicAsync('migration-20', {}, appTree)
@@ -212,7 +268,7 @@ Some Content
212268
${noteText}
213269
<igx-bottom-nav>
214270
<igx-bottom-nav-item>
215-
<igx-bottom-nav-header routerLink="view1">
271+
<igx-bottom-nav-header routerLink="view1" class="igxtab">
216272
<igx-icon igxBottomNavHeaderIcon>folder</igx-icon>
217273
<span igxBottomNavHeaderLabel>Tab1</span>
218274
</igx-bottom-nav-header>
@@ -248,4 +304,38 @@ ${noteText}
248304
</igx-bottom-nav-item>
249305
</igx-bottom-nav>`);
250306
});
307+
308+
it('Should update the css selectors', async () => {
309+
appTree.create('/testSrc/appPrefix/component/custom.component.scss', `
310+
igx-tabs-group {
311+
padding: 8px;
312+
}
313+
igx-tab-item {
314+
padding: 8px;
315+
}
316+
igx-tab-panel {
317+
padding: 8px;
318+
}
319+
igx-tab {
320+
padding: 8px;
321+
}`);
322+
323+
const tree = await schematicRunner.runSchematicAsync('migration-20', {}, appTree)
324+
.toPromise();
325+
326+
expect(tree.readContent('/testSrc/appPrefix/component/custom.component.scss'))
327+
.toEqual(`
328+
igx-tab-content {
329+
padding: 8px;
330+
}
331+
igx-tab-header {
332+
padding: 8px;
333+
}
334+
igx-bottom-nav-content {
335+
padding: 8px;
336+
}
337+
igx-bottom-nav-header {
338+
padding: 8px;
339+
}`);
340+
});
251341
});

projects/igniteui-angular/migrations/update-12_0_0/index.ts

Lines changed: 69 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
3333
const update = new UpdateChanges(__dirname, host, context);
3434
const changes = new Map<string, FileChange[]>();
3535
const htmlFiles = update.templateFiles;
36+
const sassFiles = update.sassFiles;
37+
let applyComment = false;
3638

3739
const applyChanges = () => {
3840
for (const [path, change] of changes.entries()) {
@@ -43,6 +45,7 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
4345
.forEach(c => buffer = c.apply(buffer));
4446

4547
host.overwrite(path, buffer);
48+
applyComment = true;
4649
}
4750
};
4851

@@ -54,7 +57,7 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
5457
}
5558
};
5659

57-
const isEmptyOrSpaces = (str) => str === null || str === '' || str === '\n' || str.match(/^ *$/) !== null;
60+
const isEmptyOrSpaces = (str) => str === null || str === '' || str === '\n' || str === '\r\n' || str.match(/^[\r\n\t]* *$/) !== null;
5861

5962
// Replace the tabsType input with tabsAligment
6063
for (const path of htmlFiles) {
@@ -92,7 +95,6 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
9295
addChange(file.url, new FileChange(startTag.start, tabPanel, textToReplace, 'replace'));
9396
});
9497

95-
9698
applyChanges();
9799
changes.clear();
98100

@@ -121,9 +123,15 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
121123
routerLinkText = ` ${routerLink.name}="${routerLink.value}"`;
122124
}
123125

126+
let classText = '';
127+
if ((node.name === 'igx-tab-item' || node.name === 'igx-tab') && hasAttribute(node, 'class')) {
128+
const classAttr = getAttribute(node, 'class')[0].value;
129+
classText = !isEmptyOrSpaces(classAttr) ? ` class="${classAttr}"` : '';
130+
}
131+
124132
if (iconText || labelText || routerLinkText) {
125133
// eslint-disable-next-line max-len
126-
const tabHeader = `\n<${comp.headerItem}${routerLinkText}>${iconText}${labelText}</${comp.headerItem}>`;
134+
const tabHeader = `\n<${comp.headerItem}${routerLinkText}${classText}>${iconText}${labelText}</${comp.headerItem}>`;
127135
addChange(file.url, new FileChange(startTag.end, tabHeader));
128136
}
129137
});
@@ -132,14 +140,26 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
132140
changes.clear();
133141

134142
// Grab the content between <igx-tabs-group> and create a <igx-tab-content>
143+
// Also migrate class from igx-tabs-group to igx-tab-content, if any
135144
findElementNodes(parseFile(host, path), comp.tags)
136145
.map(node => getSourceOffset(node as Element))
137146
.forEach(offset => {
138147
const tabHeader = offset.node.children.find(c => (c as Element).name === comp.headerItem);
148+
let classAttrText = '';
149+
if (offset.node.name === 'igx-tab-panel' || offset.node.name === 'igx-tabs-group') {
150+
const classAttr = hasAttribute(offset.node, 'class') ? getAttribute(offset.node, 'class')[0].value : '';
151+
classAttrText = !isEmptyOrSpaces(classAttr) ? ` class="${classAttr}"` : '';
152+
}
153+
139154
if (tabHeader) {
140155
const content = offset.file.content.substring(tabHeader.sourceSpan.end.offset, offset.endTag.start);
141-
if (!isEmptyOrSpaces(content)) {
142-
const tabPanel = `\n<${comp.panelItem}>${content}</${comp.panelItem}>\n`;
156+
// Since igx-tab-item tag is common for old and new igx-tabs
157+
// Check whether igx-tab-content is already present!
158+
const tabContentTag = new RegExp(String.raw`${comp.panelItem}`);
159+
const hasTabContent = content.match(tabContentTag);
160+
161+
if ((!hasTabContent || hasTabContent.length === 0) && !isEmptyOrSpaces(content)) {
162+
const tabPanel = `\n<${comp.panelItem}${classAttrText}>${content}</${comp.panelItem}>\n`;
143163
addChange(offset.file.url, new FileChange(tabHeader.sourceSpan.end.offset, tabPanel, content, 'replace'));
144164
}
145165
}
@@ -149,17 +169,51 @@ export default (): Rule => (host: Tree, context: SchematicContext) => {
149169
changes.clear();
150170

151171
// Insert a comment indicating the change/replacement
152-
findElementNodes(parseFile(host, path), comp.component).
153-
map(node => getSourceOffset(node as Element)).
154-
forEach(offset => {
155-
const { startTag, file } = offset;
156-
// eslint-disable-next-line max-len
157-
const commentText = `<!--NOTE: This component has been updated by Infragistics migration: v${version}\nPlease check your template whether all bindings/event handlers are correct.-->\n`;
158-
addChange(file.url, new FileChange(startTag.start, commentText));
159-
});
172+
if (applyComment) {
173+
findElementNodes(parseFile(host, path), comp.component).
174+
map(node => getSourceOffset(node as Element)).
175+
forEach(offset => {
176+
const { startTag, file } = offset;
177+
// eslint-disable-next-line max-len
178+
const commentText = `<!--NOTE: This component has been updated by Infragistics migration: v${version}\nPlease check your template whether all bindings/event handlers are correct.-->\n`;
179+
addChange(file.url, new FileChange(startTag.start, commentText));
180+
});
160181

161-
applyChanges();
162-
changes.clear();
182+
applyChanges();
183+
changes.clear();
184+
}
185+
}
186+
187+
for (const sassPath of sassFiles) {
188+
const origContent = host.read(sassPath).toString();
189+
let newContent = origContent;
190+
let changed = false;
191+
for (const item of comp.tags) {
192+
const searchText = new RegExp(String.raw`${item}(?=[\s])`);
193+
let replaceText = '';
194+
if (comp.component === 'igx-tabs') {
195+
if (item === 'igx-tab-item') {
196+
replaceText = comp.headerItem;
197+
} else if (item === 'igx-tabs-group') {
198+
replaceText = comp.panelItem;
199+
}
200+
}
201+
if (comp.component === 'igx-bottom-nav') {
202+
if (item === 'igx-tab') {
203+
replaceText = comp.headerItem;
204+
} else if (item === 'igx-tab-panel') {
205+
replaceText = comp.panelItem;
206+
}
207+
}
208+
209+
if (searchText.test(origContent)) {
210+
changed = true;
211+
newContent = newContent.replace(searchText, replaceText);
212+
}
213+
}
214+
if (changed) {
215+
host.overwrite(sassPath, newContent);
216+
}
163217
}
164218
}
165219

projects/igniteui-angular/src/lib/grids/grid/grid.component.ts

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -775,12 +775,26 @@ export class IgxGridComponent extends IgxGridBaseDirective implements GridType,
775775
return this.columnList.some((col) => col.groupable && !col.columnGroup);
776776
}
777777

778+
/**
779+
* Returns whether the `IgxGridComponent` has group area.
780+
*
781+
* @example
782+
* ```typescript
783+
* let isGroupAreaVisible = this.grid.showGroupArea;
784+
* ```
785+
*
786+
* @example
787+
* ```html
788+
* <igx-grid #grid [data]="Data" [showGroupArea]="false"></igx-grid>
789+
* ```
790+
*/
778791
@Input()
779792
public get showGroupArea(): boolean {
780793
return this._showGroupArea;
781794
}
782795
public set showGroupArea(value: boolean) {
783796
this._showGroupArea = value;
797+
this.notifyChanges(true);
784798
}
785799

786800
/**

projects/igniteui-angular/src/lib/grids/row.directive.ts

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -408,7 +408,10 @@ export class IgxRowDirective<T extends IgxGridBaseDirective & GridType> implemen
408408
this.selectionService.selectMultipleRows(this.rowID, this.rowData, event);
409409
return;
410410
}
411-
this.selectionService.selectRowById(this.rowID, !event.ctrlKey, event);
411+
412+
// eslint-disable-next-line no-bitwise
413+
const clearSelection = !(+event.ctrlKey ^ +event.metaKey);
414+
this.selectionService.selectRowById(this.rowID, clearSelection, event);
412415
}
413416

414417
/**

0 commit comments

Comments
 (0)