Skip to content

Commit f3c90eb

Browse files
authored
Merge pull request #7148 from IgniteUI/SKrastev/row-pinning-nav
feat(igxGrid): Update navigation to include ghost rows.
2 parents f451072 + 2db77fe commit f3c90eb

12 files changed

+322
-45
lines changed

projects/igniteui-angular/src/lib/grids/common/pipes.ts

+4-4
Original file line numberDiff line numberDiff line change
@@ -227,17 +227,17 @@ export class IgxGridRowPinningPipe implements PipeTransform {
227227
public transform(collection: any[] , id: string, isPinned = false, pipeTrigger: number) {
228228
const grid = this.gridAPI.grid;
229229

230-
if (!grid.hasPinnedRecords) {
231-
return isPinned ? [] : collection;
232-
}
233-
234230
if (grid.hasPinnedRecords && isPinned) {
235231
const result = collection.filter(rec => grid.isRecordPinned(rec));
236232
result.sort((rec1, rec2) => grid.pinRecordIndex(rec1) - grid.pinRecordIndex(rec2));
237233
return result;
238234
}
239235

240236
grid.unpinnedRecords = collection;
237+
if (!grid.hasPinnedRecords) {
238+
grid.pinnedRecords = [];
239+
return isPinned ? [] : collection;
240+
}
241241

242242
return collection.map((rec) => {
243243
return grid.isRecordPinned(rec) ? { recordRef: rec, ghostRecord: true} : rec;

projects/igniteui-angular/src/lib/grids/grid-base.directive.ts

+48-18
Original file line numberDiff line numberDiff line change
@@ -2444,6 +2444,11 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
24442444
*/
24452445
public columnWidthSetByUser = false;
24462446

2447+
/**
2448+
* @hidden @internal
2449+
*/
2450+
public pinnedRecords: any[];
2451+
24472452
/**
24482453
* @hidden @internal
24492454
*/
@@ -2665,12 +2670,13 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
26652670

26662671
/**
26672672
* @hidden
2673+
* Returns the row index of a row that takes into account the full view data like pinning.
26682674
*/
2669-
public getRowIndex(rowIndex, pinned) {
2675+
public getDataViewIndex(rowIndex, pinned) {
26702676
if (pinned && !this.isRowPinningToTop) {
2671-
rowIndex = rowIndex + this.dataView.length;
2677+
rowIndex = rowIndex + this.unpinnedDataView.length;
26722678
} else if (!pinned && this.isRowPinningToTop) {
2673-
rowIndex = rowIndex + this.pinnedRecordsCount;
2679+
rowIndex = rowIndex + this.pinnedDataView.length;
26742680
}
26752681
return rowIndex;
26762682
}
@@ -2727,6 +2733,15 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
27272733
return this._pinnedRecordIDs.indexOf(id) !== -1;
27282734
}
27292735

2736+
/**
2737+
* @hidden
2738+
* @internal
2739+
*/
2740+
public isRecordPinnedByIndex(rowIndex: number) {
2741+
return this.hasPinnedRecords && (this.isRowPinningToTop && rowIndex < this.pinnedDataView.length) ||
2742+
(!this.isRowPinningToTop && rowIndex >= this.unpinnedDataView.length);
2743+
}
2744+
27302745
/**
27312746
* @hidden
27322747
* @internal
@@ -2997,6 +3012,7 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
29973012
data = data.map(rec => rec.ghostRecord !== undefined ? rec.recordRef : rec);
29983013
if (this._pinnedRecordIDs.length > 0 && pinned) {
29993014
this._filteredSortedPinnedData = data;
3015+
this.pinnedRecords = data;
30003016
this.filteredSortedData = this.isRowPinningToTop ? [... this._filteredSortedPinnedData, ... this._filteredSortedUnpinnedData] :
30013017
[... this._filteredSortedUnpinnedData, ... this._filteredSortedPinnedData];
30023018
} else if (this._pinnedRecordIDs.length > 0 && !pinned) {
@@ -5172,25 +5188,38 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
51725188
}
51735189

51745190
/**
5175-
* Returns the currently transformed paged/filtered/sorted/grouped data, displayed in the grid.
5191+
* Returns the currently transformed paged/filtered/sorted/grouped pinned row data, displayed in the grid.
51765192
* @example
51775193
* ```typescript
5178-
* const dataView = this.grid.dataView;
5194+
* const pinnedDataView = this.grid.pinnedDataView;
51795195
* ```
51805196
*/
5181-
get dataView(): any[] {
5197+
get pinnedDataView(): any[] {
5198+
return this.pinnedRecords ? this.pinnedRecords : [];
5199+
}
5200+
5201+
/**
5202+
* Returns currently transformed paged/filtered/sorted/grouped unpinned row data, displayed in the grid.
5203+
* @example
5204+
* ```typescript
5205+
* const pinnedDataView = this.grid.pinnedDataView;
5206+
* ```
5207+
*/
5208+
get unpinnedDataView(): any[] {
51825209
return this.unpinnedRecords ? this.unpinnedRecords : this.verticalScrollContainer.igxForOf;
51835210
}
51845211

5185-
/**
5186-
* Returns the currently transformed paged/filtered/sorted/grouped pinned data, displayed in the grid.
5187-
* @example
5188-
* ```typescript
5189-
* const pinnedDataView = this.grid.pinnedDataView;
5190-
* ```
5191-
*/
5192-
get pinnedDataView(): any[] {
5193-
return this.pinnedRows.map(row => row.rowData);
5212+
/**
5213+
* Returns the currently transformed paged/filtered/sorted/grouped/pinned/unpinned row data, displayed in the grid.
5214+
* @example
5215+
* ```typescript
5216+
* const dataView = this.grid.dataView;
5217+
* ```
5218+
*/
5219+
get dataView(): any[] {
5220+
return this.isRowPinningToTop ?
5221+
[...this.pinnedDataView, ...this.unpinnedDataView] :
5222+
[...this.unpinnedDataView, ...this.pinnedDataView];
51945223
}
51955224

51965225
/**
@@ -5433,7 +5462,7 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
54335462
* If `headers` is enabled, it will use the column header (if any) instead of the column field.
54345463
*/
54355464
public getSelectedData(formatters = false, headers = false) {
5436-
const source = this.isRowPinningToTop ? [...this.pinnedDataView, ...this.dataView] : [...this.dataView, ...this.pinnedDataView];
5465+
const source = this.filteredSortedData;
54375466
return this.extractDataFromSelection(source, formatters, headers);
54385467
}
54395468

@@ -5637,6 +5666,7 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
56375666
if (this.dataView.slice(rowIndex, rowIndex + 1).find(rec => rec.expression || rec.childGridsData)) {
56385667
visibleColIndex = -1;
56395668
}
5669+
// If the target row is pinned no need to scroll as well.
56405670
const shouldScrollVertically = this.navigation.shouldPerformVerticalScroll(rowIndex, visibleColIndex);
56415671
const shouldScrollHorizontally = this.navigation.shouldPerformHorizontalScroll(visibleColIndex, rowIndex);
56425672
if (shouldScrollVertically) {
@@ -5923,11 +5953,11 @@ export class IgxGridBaseDirective extends DisplayDensityBase implements
59235953
if (delayScrolling) {
59245954
this.verticalScrollContainer.onDataChanged.pipe(first()).subscribe(() => {
59255955
this.scrollDirective(this.verticalScrollContainer,
5926-
typeof (row) === 'number' ? row : this.dataView.indexOf(row));
5956+
typeof (row) === 'number' ? row : this.unpinnedDataView.indexOf(row));
59275957
});
59285958
} else {
59295959
this.scrollDirective(this.verticalScrollContainer,
5930-
typeof (row) === 'number' ? row : this.dataView.indexOf(row));
5960+
typeof (row) === 'number' ? row : this.unpinnedDataView.indexOf(row));
59315961
}
59325962

59335963
this.scrollToHorizontally(column);

projects/igniteui-angular/src/lib/grids/grid-navigation.service.ts

+8-2
Original file line numberDiff line numberDiff line change
@@ -309,8 +309,11 @@ export class IgxGridNavigationService {
309309
}
310310

311311
public shouldPerformVerticalScroll(targetRowIndex: number, visibleColIndex: number): boolean {
312+
if (this.grid.isRecordPinnedByIndex(targetRowIndex)) { return false; }
313+
const scrollRowIndex = this.grid.hasPinnedRecords && this.grid.isRowPinningToTop ?
314+
targetRowIndex - this.grid.pinnedDataView.length : targetRowIndex;
312315
const targetRow = this.getRowElementByIndex(targetRowIndex);
313-
const rowHeight = this.grid.verticalScrollContainer.getSizeAt(targetRowIndex);
316+
const rowHeight = this.grid.verticalScrollContainer.getSizeAt(scrollRowIndex);
314317
const containerHeight = this.grid.calcHeight ? Math.ceil(this.grid.calcHeight) : 0;
315318
const endTopOffset = targetRow ? targetRow.offsetTop + rowHeight + this.containerTopOffset : containerHeight + rowHeight;
316319
return !targetRow || targetRow.offsetTop < Math.abs(this.containerTopOffset)
@@ -323,7 +326,10 @@ export class IgxGridNavigationService {
323326
}
324327

325328
public performVerticalScrollToCell(rowIndex: number, visibleColIndex = -1, cb?: () => void) {
326-
this.grid.verticalScrollContainer.scrollTo(rowIndex);
329+
// Only for top pinning we need to subtract pinned count because virtualization indexing doesn't count pinned rows.
330+
const scrollRowIndex = this.grid.hasPinnedRecords && this.grid.isRowPinningToTop ?
331+
rowIndex - this.grid.pinnedDataView.length : rowIndex;
332+
this.grid.verticalScrollContainer.scrollTo(scrollRowIndex);
327333
this.grid.verticalScrollContainer.onChunkLoad
328334
.pipe(first()).subscribe(() => {
329335
if (cb) { cb(); }

0 commit comments

Comments
 (0)