From f151f8e2f225a76077f56d10bd5df75c33f2d52c Mon Sep 17 00:00:00 2001
From: fsdavid <daviti1@mail.com>
Date: Wed, 4 May 2022 16:07:54 +0200
Subject: [PATCH] Update connectivity - change datasets by slider

---
 .../sapi/core/sapiParcellation.ts             |   4 +-
 .../connectivityBrowser.component.ts          | 435 ++++--------------
 .../connectivityBrowser.template.html         | 118 +++--
 .../connectivity/hasConnectivity.directive.ts |  39 +-
 src/sharedModules/angularMaterial.module.ts   |   7 +-
 .../layerCtrl.service/layerCtrl.service.ts    |   1 -
 6 files changed, 165 insertions(+), 439 deletions(-)

diff --git a/src/atlasComponents/sapi/core/sapiParcellation.ts b/src/atlasComponents/sapi/core/sapiParcellation.ts
index aa9fa59f2..611b6b0db 100644
--- a/src/atlasComponents/sapi/core/sapiParcellation.ts
+++ b/src/atlasComponents/sapi/core/sapiParcellation.ts
@@ -4,7 +4,7 @@ import { SAPI } from "../sapi.service"
 import { SapiParcellationFeatureModel, SapiParcellationModel, SapiQueryParam, SapiRegionModel } from "../type"
 
 type PaginationQuery = {
-  perPage: number
+  size: number
   page: number
 }
 
@@ -41,7 +41,7 @@ export class SAPIParcellation{
       `${this.sapi.bsEndpoint}/atlases/${encodeURIComponent(this.atlasId)}/parcellations/${encodeURIComponent(this.id)}/features`,
       {
         type: type,
-        per_page: param && param.perPage? param.perPage.toString() : '5',
+        size: param && param.size? param.size.toString() : '5',
         page: param && param.page? param.page.toString() : '0',
       },
       queryParam
diff --git a/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.component.ts b/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.component.ts
index ad48827ea..20fa01181 100644
--- a/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.component.ts
+++ b/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.component.ts
@@ -1,40 +1,19 @@
-import {
-  AfterViewInit, ChangeDetectorRef,
-  Component,
-  ElementRef,
-  OnDestroy,
-  ViewChild,
-  Input,
-  OnInit, Inject,
-} from "@angular/core";
+import {AfterViewInit, Component, ElementRef, OnDestroy, ViewChild, Input, ChangeDetectorRef} from "@angular/core";
 import {select, Store} from "@ngrx/store";
-import {fromEvent, Subscription, Subject, combineLatest, BehaviorSubject} from "rxjs";
-import {catchError, distinctUntilChanged, map, switchMap, take} from "rxjs/operators";
-import {HttpClient} from "@angular/common/http";
-import {BS_ENDPOINT} from "src/util/constants";
-import {OVERWRITE_SHOW_DATASET_DIALOG_TOKEN} from "src/util/interfaces";
+import {fromEvent, Subscription, BehaviorSubject} from "rxjs";
+import {catchError, take} from "rxjs/operators";
 import {SAPI, SapiAtlasModel, SapiParcellationModel, SAPIRegion, SapiRegionModel} from "src/atlasComponents/sapi";
-import {actions, selectors} from "src/state/atlasSelection";
 import { atlasAppearance, atlasSelection } from "src/state";
 import {PARSE_TYPEDARRAY} from "src/atlasComponents/sapi/sapi.service";
 import {SapiParcellationFeatureMatrixModel} from "src/atlasComponents/sapi/type";
 import { of } from "rxjs";
 import {CustomLayer} from "src/state/atlasAppearance";
 
-
-const CONNECTIVITY_NAME_PLATE = 'Connectivity'
-
 @Component({
   selector: 'sxplr-sapiviews-features-connectivity-browser',
   templateUrl: './connectivityBrowser.template.html',
-  providers: [
-    {
-      provide: OVERWRITE_SHOW_DATASET_DIALOG_TOKEN,
-      useValue: null
-    }
-  ]
 })
-export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDestroy {
+export class ConnectivityBrowserComponent implements AfterViewInit, OnDestroy {
 
     @Input('sxplr-sapiviews-features-connectivity-browser-atlas')
     atlas: SapiAtlasModel
@@ -42,8 +21,6 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
     @Input('sxplr-sapiviews-features-connectivity-browser-parcellation')
     parcellation: SapiParcellationModel
 
-    private setColorMap$: Subject<boolean> = new Subject()
-
     /**
      * accordion expansion should only toggle the clearviewqueue state
      * which should be the single source of truth
@@ -63,54 +40,17 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
         return
       }
       this.accordionIsExpanded = flag
-      // // this.store$.dispatch(
-      // //   ngViewerActionClearView({
-      // //     payload: {
-      // //       [CONNECTIVITY_NAME_PLATE]: flag && !this.noDataReceived
-      // //     }
-      // //   })
-      // // )
-      this.store$.dispatch({
-        type: 'SET_OVERWRITTEN_COLOR_MAP',
-        payload: flag? CONNECTIVITY_NAME_PLATE : false,
-      })
-
-      // if (flag) {
-      //   this.addNewColorMap()
-      // } else {
-      //   this.restoreDefaultColormap()
-      // } 
-        
-      // if (flag) {
-      //   this.setCustomLayer()
-      // } else {
-      //   this.removeCustomLayer()
-      // }
-                
-    }
 
-    public connectivityLayerId = 'connectivity-colormap-id'
-    
-    setCustomLayer() {
-      const map = new Map<SapiRegionModel, number[]>()
-      for (const region of this.allRegions) {
-        map.set(region, SAPIRegion.GetDisplayColor(region))
-      }
-        
-      const customLayer: CustomLayer = {
-        clType: 'customlayer/colormap',
-        id: this.connectivityLayerId,
-        colormap: map
+      if (flag) {
+        if (this.allRegions.length) {
+          this.setCustomLayer()
+        } else {
+          this.setCustomLayerOnLoad = true
+        }
+      } else {
+        this.removeCustomLayer()
       }
-      const layer = atlasAppearance.actions.addCustomLayer({customLayer})
-        
-      console.log(layer)
-    }
-    
-    removeCustomLayer() {
-      atlasAppearance.actions.removeCustomLayer({
-        id: this.connectivityLayerId
-      })
+
     }
 
     @Input() types: any[]
@@ -119,10 +59,10 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
     @Input() set defaultProfile(val: any) {
       this._defaultProfile = val
       this.selectedType = this.types.find(t => t.types.includes(val.type)).name
-      this.datasetList = val.datasets.map(d => this.formatDataset(d))
-      this.selectDataset(val.selectedDataset, false)
+      this.pageNumber = 1
+      this.selectedDataset = this.fixDatasetFormat(val.selectedDataset)
       this.setMatrixData(val.matrix)
-      this.fetchedPage = 0
+      this.numberOfDatasets = val.numberOfDatasets
     }
 
     get defaultProfile() {
@@ -136,18 +76,6 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
     set region(val) {
       const newRegionName = val && val.name
 
-      if (!val) {
-        this.store$.dispatch({
-          type: 'SET_OVERWRITTEN_COLOR_MAP',
-          payload: false,
-        })
-        return
-      }
-
-      if (newRegionName !== this.regionName && this.defaultColorMap) {
-        this.restoreDefaultColormap()
-      }
-
       if (val.status
           && !val.name.includes('left hemisphere')
           && !val.name.includes('right hemisphere')) {
@@ -155,149 +83,51 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
       }
 
       this.regionName = newRegionName
-
-      // if(this.selectedDataset) {
-      //   this.fetchConnectivity()
-      // }
-      // TODO may not be necessary
-      // this.changeDetectionRef.detectChanges()
     }
 
     public atlasId: any
     public regionName: string
     public regionHemisphere: string = null
-    public datasetList: any[] = []
     public selectedDataset: any
-    public selectedDatasetName: any
-    public selectedDatasetDescription: string = ''
-    public selectedDatasetKgId: string = ''
-    public selectedDatasetKgSchema: string = ''
     public connectionsString: string
     public connectedAreas: BehaviorSubject<any[]> = new BehaviorSubject([])
 
-    // TODO this may be incompatible
-    private selectedParcellationFlatRegions$ = this.store$.pipe(
-      switchMap(atlasSelection.fromRootStore.distinctATP()),
-      switchMap(({ atlas, template, parcellation }) => this.sapi.getParcRegions(atlas["@id"], parcellation["@id"], template["@id"]))
-    )
-
     private subscriptions: Subscription[] = []
-    public expandMenuIndex = -1
     public allRegions = []
     private regionIndexInMatrix = -1
     public defaultColorMap: Map<string, Map<number, { red: number, green: number, blue: number }>>
-    public fetching: boolean = false
     public matrixString: string
     public noDataReceived = false
-    public loadingDatasets: boolean
-    public fetchedPage = 0
-    public datasetPerPage = 20
-
+    public fetching: boolean
+    public numberOfDatasets: number
+    public connectivityLayerId = 'connectivity-colormap-id'
+    private setCustomLayerOnLoad = false
+    public pageNumber: number
+    private customLayerEnabled: boolean
 
     @ViewChild('connectivityComponent', {read: ElementRef}) public connectivityComponentElement: ElementRef<any>
     @ViewChild('fullConnectivityGrid') public fullConnectivityGridElement: ElementRef<any>
 
     constructor(
         private store$: Store<any>,
+        private sapi: SAPI,
         private changeDetectionRef: ChangeDetectorRef,
-        private httpClient: HttpClient,
-        @Inject(BS_ENDPOINT) private siibraApiUrl: string,
-        private sapi: SAPI
     ) {}
-    
-    ngOnInit(): void {
-      // this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"]).getFeatures()
-      //   .subscribe(res => {
-      //     this.datasetList = res
-      //       .filter(r => ['siibra/features/connectivity', 'siibra/connectivity'].includes(r.type))
-      //       .map((r: any) => ({
-      //         ...r,
-      //         connectionType: r.name.substring(0, r.name.indexOf('{') - 1),
-      //         dataset: JSON.parse(r.name.substring(r.name.indexOf('{')).replace(/'/g, '"'))
-      //       }))
-      //     this.selectDataset(this.datasetList[0]['@id'])
-      //   })
-    }
 
     public ngAfterViewInit(): void {
-      // // this.subscriptions.push(
-      // //   this.store$.pipe(
-      // //     select(atlasAppearance.selectors.getOverwrittenColormap),
-      // //   ).subscribe(value => {
-      // //     if (this.accordionIsExpanded) {
-      // //       this.setColorMap$.next(!!value)
-      // //     }
-      // //   })
-      // // )
-      //
-      // if (this.accordionIsExpanded) {
-      //   this.setColorMap$.next(true)
-      // }
-      //
       this.subscriptions.push(
-        // this.selectedParcellationFlatRegions$.subscribe(flattenedRegions => {
-        //   this.defaultColorMap = null
-        //   this.allRegions = flattenedRegions
-        //   console.log(this.allRegions)
-        // }),
 
         this.store$.pipe(
           select(atlasSelection.selectors.selectedParcAllRegions)
         ).subscribe(flattenedRegions => {
           this.defaultColorMap = null
           this.allRegions = flattenedRegions
-          this.setCustomLayer()
+          if (this.setCustomLayerOnLoad) {
+            this.setCustomLayer()
+            this.setCustomLayerOnLoad = false
+          }
         }),
-          
       )
-      //
-      // /**
-      //    * setting/restoring colormap
-      //    */
-      // this.subscriptions.push(
-      //   combineLatest([
-      //     this.setColorMap$.pipe(
-      //       distinctUntilChanged()
-      //     ),
-      //     // fromEvent(this.connectivityComponentElement?.nativeElement, 'connectivityDataReceived').pipe(
-      //     //   map((e: CustomEvent) => {
-      //     //     // if (e.detail !== 'No data') {
-      //     //     //   this.connectivityNumberReceived.emit(e.detail.length)
-      //     //     // }
-      //     //     return e.detail
-      //     //   })
-      //     // )
-      //     this.connectedAreas
-      //   ]).subscribe(([flag, connectedAreas]) => {
-      //
-      //     if (connectedAreas.length === 0) {
-      //       this.noDataReceived = true
-      //       return this.clearViewer()
-      //     } else {
-      //       // this.store$.dispatch(
-      //       //   ngViewerActionClearView({
-      //       //     payload: {
-      //       //       [CONNECTIVITY_NAME_PLATE]: true
-      //       //     }
-      //       //   })
-      //       // )
-      //       this.noDataReceived = false
-      //
-      //       if (flag) {
-      //         this.addNewColorMap()
-      //         this.store$.dispatch({
-      //           type: 'SET_OVERWRITTEN_COLOR_MAP',
-      //           payload: 'connectivity',
-      //         })
-      //       } else {
-      //         this.restoreDefaultColormap()
-      //
-      //         this.store$.dispatch({type: 'SET_OVERWRITTEN_COLOR_MAP', payload: null})
-      //
-      //       }
-      //     }
-      //   })
-      // )
 
       this.subscriptions.push(
         fromEvent(this.connectivityComponentElement?.nativeElement, 'customToolEvent', {capture: true})
@@ -315,66 +145,84 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
       )
     }
 
+    setCustomLayer() {
+      if (this.customLayerEnabled) {
+        this.removeCustomLayer()
+      }
+      const map = new Map<SapiRegionModel, number[]>()
+      const areas = this.connectedAreas.value
+      for (const region of this.allRegions) {
+        const area = areas.find(a => a.name === region.name)
+        if (area) {
+          map.set(region, Object.values(area.color))
+        } else {
+          map.set(region, [255,255,255,0.1])
+        }
+      }
+      this.customLayerEnabled = true
+      const customLayer: CustomLayer = {
+        clType: 'customlayer/colormap',
+        id: this.connectivityLayerId,
+        colormap: map
+      }
+
+      this.store$.dispatch(
+        atlasAppearance.actions.addCustomLayer({customLayer})
+      )
+    }
+
+    removeCustomLayer() {
+      this.store$.dispatch(
+        atlasAppearance.actions.removeCustomLayer({
+          id: this.connectivityLayerId
+        })
+      )
+    }
+
     selectType(typeName) {
       this.selectedType = typeName
-      this.fetchedPage=-1
-      this.loadMoreDatasets(0)
+      this.pageNumber = 1
+      this.loadDataset()
+    }
+
+    datasetSliderChanged(pageNumber) {
+      this.pageNumber = pageNumber
+      this.loadDataset()
     }
 
-    loadMoreDatasets(selectId = -1) {
-      this.loadingDatasets = true
-      this.fetchedPage += 1
+    loadDataset() {
+      this.fetching = true
       const type = this.types.find(t => t.name === this.selectedType).types[0]
       return this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"])
-        .getFeatures({page: this.fetchedPage, perPage: 20}, type)
+        .getFeatures({page: this.pageNumber, size: 1}, type)
         .pipe(
           take(1),
           catchError(() => {
+            this.fetching = false
             return of(null)
           })
-        ).subscribe((datasets: any[]) => {
-          if (datasets && datasets.length) {
-            datasets.forEach(d => this.datasetList.push(this.formatDataset(d)))
-
-            //  Select dataset if we have selectId
-            if (selectId >= 0 && selectId < datasets.length) {
-              this.selectDataset(datasets[selectId])
+        ).subscribe((res: any) => {
+          if (res && res.items) {
+            if (res.total !== this.numberOfDatasets) {
+              this.numberOfDatasets = res.total
             }
+            this.selectedDataset = this.fixDatasetFormat(res.items[0])
+            this.fetchConnectivity()
           }
-          this.loadingDatasets = false
         })
     }
 
-    selectDataset(datasetId, fetchConnectivity=true) {
-      const dataset = this.datasetList.find(d => d['@id'] === datasetId)
-      this.selectedDataset = dataset['@id']
-        console.log(dataset)
-      this.selectedDatasetName = dataset.data.name
-      this.selectedDatasetDescription = dataset.data.description
-      this.selectedDatasetKgId = dataset.data['dataset_id']
-
-      if (fetchConnectivity) {
-        this.fetchConnectivity()
-      }
-    }
-    
-    private formatDataset = (ds) => ({
+    // ToDo this is caused by the bug existing on siibra python
+    private fixDatasetFormat = (ds) => ({
       ...ds,
-      data: JSON.parse(ds.name.substring(ds.name.indexOf('{')).replace(/'/g, '"'))
+      ...JSON.parse(ds.name.substring(ds.name.indexOf('{')).replace(/'/g, '"'))
     })
-    
 
     fetchConnectivity() {
-      this.fetching = true
-      this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"]).getFeatureInstance(this.selectedDataset)
-        .pipe(catchError((err) => {
-          this.fetching = false
-          return of(null)
-        }))
+      this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"]).getFeatureInstance(this.selectedDataset['@id'])
         .subscribe(ds=> {
           this.setMatrixData(ds)  
           this.fetching = false
-          this.changeDetectionRef.detectChanges()
         })
     }
     
@@ -388,23 +236,13 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
             areas[matrixData.columns[i]] = value
           })
           this.connectionsString = JSON.stringify(areas)
-          this.connectedAreas.next(this.cleanConnectedAreas(areas))
+          this.connectedAreas.next(this.formatConnections(areas))
 
+          this.setCustomLayer()
           this.matrixString = JSON.stringify(matrixData.columns.map((mc, i) => ([mc, ...matrix.rawArray[i]])))
-        })
-    }
+          this.changeDetectionRef.detectChanges()
 
-    clearViewer() {
-      // this.store$.dispatch(
-      //   ngViewerActionClearView({
-      //     payload: {
-      //       [CONNECTIVITY_NAME_PLATE]: false
-      //     }
-      //   })
-      // )
-      this.connectedAreas.next([])
-
-      // return this.restoreDefaultColormap()
+        })
     }
 
     //ToDo navigateRegion action does not work any more
@@ -420,57 +258,6 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
       return this.allRegions.find(r => r.name === region)
     }
 
-    public restoreDefaultColormap() {
-      if (!this.defaultColorMap) return
-      getWindow().interactiveViewer.viewerHandle.applyLayersColourMap(this.defaultColorMap)
-    }
-
-    public addNewColorMap() {
-      if (!this.defaultColorMap) {
-        this.defaultColorMap = getWindow().interactiveViewer.viewerHandle.getLayersSegmentColourMap()
-      }
-
-      const existingMap: Map<string, Map<number, { red: number, green: number, blue: number }>> = (getWindow().interactiveViewer.viewerHandle.getLayersSegmentColourMap())
-      const colorMap = new Map(existingMap)
-
-      this.allRegions.forEach(r => {
-        if (r.ngId) {
-          colorMap.get(r.ngId).set(r.labelIndex, {red: 255, green: 255, blue: 255})
-        }
-      })
-
-      this.connectedAreas.value.forEach(area => {
-        const areaAsRegion = this.allRegions
-          .filter(r => {
-
-            if (this.regionHemisphere) {
-              let regionName = area.name
-              let regionStatus = null
-              if (regionName.includes('left hemisphere')) {
-                regionStatus = 'left hemisphere'
-                regionName = regionName.replace(' - left hemisphere', '');
-              } else if (regionName.includes('right hemisphere')) {
-                regionStatus = 'right hemisphere'
-                regionName = regionName.replace(' - right hemisphere', '');
-              }
-              return r.name === regionName && r.status === regionStatus
-            }
-
-            return r.name === area.name
-          })
-          .map(r => r)
-
-        if (areaAsRegion && areaAsRegion.length && areaAsRegion[0].ngId) {
-          colorMap.get(areaAsRegion[0].ngId).set(areaAsRegion[0].labelIndex, {
-            red: area.color.r,
-            green: area.color.g,
-            blue: area.color.b
-          })
-        }
-      })
-      getWindow().interactiveViewer.viewerHandle.applyLayersColourMap(colorMap)
-    }
-
     exportConnectivityProfile() {
       const a = document.querySelector('hbp-connectivity-matrix-row');
       (a as any).downloadCSV()
@@ -480,23 +267,13 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
       this.fullConnectivityGridElement?.nativeElement['downloadCSV']()
     }
 
-
     public ngOnDestroy(): void {
-      // this.store$.dispatch(
-      //   ngViewerActionClearView({
-      //     payload: {
-      //       [CONNECTIVITY_NAME_PLATE]: false
-      //     }
-      //   })
-      // )
-      this.restoreDefaultColormap()
+      this.removeCustomLayer()
       this.subscriptions.forEach(s => s.unsubscribe())
     }
 
-
     private floatConnectionNumbers
-
-    cleanConnectedAreas = (areas) => {
+    private formatConnections = (areas) => {
       const cleanedObj = Object.keys(areas)
         .map(key => ({name: key, numberOfConnections: areas[key]}))
         .filter(f => f.numberOfConnections > 0)
@@ -531,37 +308,9 @@ export class ConnectivityBrowserComponent implements OnInit, AfterViewInit, OnDe
       })
       return colorAreas
     }
+    private clamp = val => Math.round(Math.max(0, Math.min(1.0, val)) * 255)
+    private colormap_red = x => x < 0.7? this.clamp(4.0 * x - 1.5) : this.clamp(-4.0 * x + 4.5)
+    private colormap_green = x => x < 0.5? this.clamp(4.0 * x - 0.5) : this.clamp(-4.0 * x + 3.5)
+    private colormap_blue = x => x < 0.3? this.clamp(4.0 * x + 0.5) : this.clamp(-4.0 * x + 2.5)
 
-    clamp = val => Math.round(Math.max(0, Math.min(1.0, val)) * 255)
-
-    colormap_red = (x) => {
-      if (x < 0.7) {
-        return this.clamp(4.0 * x - 1.5);
-      } else {
-        return this.clamp(-4.0 * x + 4.5);
-      }
-    }
-
-    colormap_green = (x) => {
-      if (x < 0.5) {
-        return this.clamp(4.0 * x - 0.5);
-      } else {
-        return this.clamp(-4.0 * x + 3.5);
-      }
-    }
-
-    colormap_blue = (x) => {
-      if (x < 0.3) {
-        return this.clamp(4.0 * x + 0.5);
-      } else {
-        return this.clamp(-4.0 * x + 2.5);
-      }
-    }
-    
-    
-
-}
-
-function getWindow(): any {
-  return window
 }
diff --git a/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.template.html b/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.template.html
index c3d34c75d..543ead827 100644
--- a/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.template.html
+++ b/src/atlasComponents/sapiViews/features/connectivity/connectivityBrowser/connectivityBrowser.template.html
@@ -1,10 +1,61 @@
 <div class="w-100 h-100 d-block d-flex flex-column sxplr-pb-2">
+    <div>
+        <div *ngIf="types && types.length && selectedType" class="flex-grow-0 flex-shrink-0 d-flex flex-row flex-nowrap">
+            <mat-form-field class="flex-grow-1 flex-shrink-1 w-0">
+                <mat-label>
+                    Modality
+                </mat-label>
+
+                <mat-select
+                        [value]="selectedType"
+                        (selectionChange)="selectType($event.value)">
+                    <mat-option
+                            *ngFor="let type of types"
+                            [matTooltip]="type.name"
+                            [value]="type.name">
+                        {{ type.name }}
+                    </mat-option>
+                </mat-select>
+            </mat-form-field>
+        </div>
+
+        <div *ngIf="selectedDataset"  class="flex-grow-0 flex-shrink-0 d-flex flex-nowrap align-items-center">
+            <div class="flex-grow-1 flex-shrink-1 w-0">
+                <mat-label>
+                    Dataset
+                </mat-label>
+                <mat-slider [min]="1"
+                            [max]="numberOfDatasets"
+                            (change)="datasetSliderChanged($event.value)"
+                            [value]="pageNumber"
+                            thumbLabel
+                            step="1"
+                            class="w-100">
+                </mat-slider>
+            </div>
+
+            <ng-container *ngIf="selectedDataset.description || (selectedDataset.data && selectedDataset.data.description)" >
+                <!--                    TODO please reimplmenent button to explore KG dataset-->
+                <button class="flex-grow-0 flex-shrink-0"
+                        mat-icon-button
+                        (click)="exportFullConnectivity()"
+                        matTooltip="Export full connectivity profile">
+                    <i class="fas fa-download"></i>
+                </button>
+            </ng-container>
+        </div>
+
+    </div>
+
+    <div class="d-flex justify-content-center">
+      <mat-spinner *ngIf="fetching"></mat-spinner>
+    </div>
+
     <hbp-connectivity-matrix-row
             #connectivityComponent
-            *ngIf="regionName"
+            *ngIf="regionName && !fetching"
             [region]="regionName + (regionHemisphere? ' - ' + regionHemisphere : '')"
             [connections]="connectionsString"
-            [dataIsLoading]="fetching"
             theme="dark"
             show-export="true"
             show-source="false"
@@ -17,65 +68,6 @@
             [tools_custom]='[{"name": "exportslot", "type": "slot"}]'
             hide-export-view="true">
 
-        <div slot="dataset">
-            <div *ngIf="types && types.length && selectedType" class="flex-grow-0 flex-shrink-0 d-flex flex-row flex-nowrap">
-                <mat-form-field class="flex-grow-1 flex-shrink-1 w-0">
-                    <mat-label>
-                        Modality
-                    </mat-label>
-
-                    <mat-select
-                            [value]="selectedType"
-                            (selectionChange)="selectType($event.value)">
-                        <mat-option
-                                *ngFor="let type of types"
-                                [matTooltip]="type.name"
-                                [value]="type.name">
-                            {{ type.name }}
-                        </mat-option>
-                    </mat-select>
-                </mat-form-field>
-            </div>
-            <div *ngIf="datasetList.length && selectedDataset"  class="flex-grow-0 flex-shrink-0 d-flex flex-row flex-nowrap">
-                    <mat-form-field class="flex-grow-1 flex-shrink-1 w-0">
-                        <mat-label>
-                            Dataset
-                        </mat-label>
-
-                        <mat-select
-                                [value]="selectedDataset"
-                                (selectionChange)="selectDataset($event.value)">
-                            <mat-option
-                                   [matTooltip]="dataset.data.name"
-                                    *ngFor="let dataset of datasetList"
-                                    [value]="dataset['@id']">
-                                {{ dataset.data.name }}
-                            </mat-option>
-                            <mat-divider></mat-divider>
-
-                            <mat-progress-bar *ngIf="loadingDatasets" mode="indeterminate"></mat-progress-bar>
-
-                            <div class="d-flex justify-content-center" *ngIf="!loadingDatasets">
-                                <button mat-button color="primary" (click)="loadMoreDatasets()">Load more</button>
-                            </div>
-
-                        </mat-select>
-                    </mat-form-field>
-                <ng-container *ngIf="selectedDataset && (selectedDatasetDescription || selectedDatasetKgId)" >
-<!--                    TODO please reimplmenent button to explore KG dataset-->
-                    <button class="flex-grow-0 flex-shrink-0"
-                            mat-icon-button
-                            (click)="exportFullConnectivity()"
-                            matTooltip="Export full connectivity profile">
-                        <i class="fas fa-download"></i>
-                    </button>
-                </ng-container>
-            </div>
-            <div>
-                Connectivity Profile
-            </div>
-        </div>
-
         <div slot="exportslot">
             <button mat-icon-button
                     [disabled]="noDataReceived"
@@ -87,8 +79,8 @@
     </hbp-connectivity-matrix-row>
     <full-connectivity-grid #fullConnectivityGrid
                             [matrix]="matrixString"
-                            [datasetName]="selectedDatasetName"
-                            [datasetDescription]="selectedDatasetDescription"
+                            [datasetName]="selectedDataset?.name"
+                            [datasetDescription]="selectedDataset?.description || selectedDataset?.data?.description"
                             only-export="true">
     </full-connectivity-grid>
 </div>
diff --git a/src/atlasComponents/sapiViews/features/connectivity/hasConnectivity.directive.ts b/src/atlasComponents/sapiViews/features/connectivity/hasConnectivity.directive.ts
index 1bc30fff2..c0dff8fa9 100644
--- a/src/atlasComponents/sapiViews/features/connectivity/hasConnectivity.directive.ts
+++ b/src/atlasComponents/sapiViews/features/connectivity/hasConnectivity.directive.ts
@@ -43,7 +43,7 @@ export class HasConnectivity implements OnDestroy {
     private regionIndex: number
     public hasConnectivity = false
     public connectivityNumber = 0
-    
+
     private connectivityModalities: any[] = []
     private waitForModalities = false
     public defaultProfile: any
@@ -69,35 +69,31 @@ export class HasConnectivity implements OnDestroy {
           const type = m.types[0]
           
           this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"])
-            .getFeatures({page: 0, perPage: 20}, type)
+            .getFeatures({page: 1, size: 1}, type)
             .pipe(
-              take(1),  
-              switchMap((datasets: any[]) => {
-                if (datasets && datasets.length) {
+              take(1),
+              switchMap((res: any) => {
+                if (res && res.items) {
 
                   this.availableModalities.push(m)
+                  const firstDataset = res.items[0]
 
-                  if (datasets[0]) {
-
+                  if (firstDataset) {
                     this.hasConnectivity = true
                     if (!(this.defaultProfile && this.defaultProfile.length)) {
                       return this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"])
-                        .getFeatureInstance(datasets[0]['@id'])
+                        .getFeatureInstance(firstDataset['@id'])
                         .pipe(switchMap(inst => {
                           if (inst) {
-                            // if () {
                             this.defaultProfile = {
                               type,
-                              datasets,
-                              selectedDataset: datasets[0]['@id'],
-                              matrix: inst
+                              selectedDataset: firstDataset,
+                              matrix: inst,
+                              numberOfDatasets: res.total
                             }
-
-
                             const matrixData = inst as SapiParcellationFeatureMatrixModel
                             this.regionIndex = (matrixData.columns as Array<string>).findIndex(md => md === this.region.name)
                             return from(this.sapi.processNpArrayData<PARSE_TYPEDARRAY.RAW_ARRAY>(matrixData.matrix, PARSE_TYPEDARRAY.RAW_ARRAY))
-                            // }
                           }
                           return of(null)
                         }))
@@ -109,19 +105,6 @@ export class HasConnectivity implements OnDestroy {
                 }
                 return of(null)
               }), 
-              // switchMap(res => {
-              //   if (res) {
-              //     if (!(this.defaultProfile && this.defaultProfile.length)) {
-              //       this.defaultProfile = {type, matrix: res}
-              //     }
-              //
-              //     const matrixData = res as SapiParcellationFeatureMatrixModel
-              //     this.regionIndex = (matrixData.columns as Array<string>).findIndex(md => md === this.region.name)
-              //     // this.connectedAreas = matrixData.columns as Array<string>
-              //     return from(this.sapi.processNpArrayData<PARSE_TYPEDARRAY.RAW_ARRAY>(matrixData.matrix, PARSE_TYPEDARRAY.RAW_ARRAY))
-              //   }
-              //   return of(null)
-              // })
             ).subscribe(res => {
               if (res && res.rawArray && res.rawArray[this.regionIndex]) {
                 const connections = res.rawArray[this.regionIndex]
diff --git a/src/sharedModules/angularMaterial.module.ts b/src/sharedModules/angularMaterial.module.ts
index a294aca45..6f29b8913 100644
--- a/src/sharedModules/angularMaterial.module.ts
+++ b/src/sharedModules/angularMaterial.module.ts
@@ -30,6 +30,7 @@ import { MatToolbarModule } from '@angular/material/toolbar'
 import { ClipboardModule } from '@angular/cdk/clipboard'
 import { BrowserAnimationsModule } from "@angular/platform-browser/animations";
 import {MatProgressBarModule} from "@angular/material/progress-bar";
+import {MatProgressSpinnerModule} from "@angular/material/progress-spinner";
 
 const defaultDialogOption: MatDialogConfig = new MatDialogConfig()
 
@@ -64,7 +65,8 @@ const defaultDialogOption: MatDialogConfig = new MatDialogConfig()
     ScrollingModule,
     MatToolbarModule,
     ClipboardModule,
-    MatProgressBarModule
+    MatProgressBarModule,
+    MatProgressSpinnerModule,
   ],
   exports: [
     MatButtonModule,
@@ -94,7 +96,8 @@ const defaultDialogOption: MatDialogConfig = new MatDialogConfig()
     ScrollingModule,
     MatToolbarModule,
     ClipboardModule,
-    MatProgressBarModule
+    MatProgressBarModule,
+    MatProgressSpinnerModule,
   ],
   providers: [{
     provide: MAT_DIALOG_DEFAULT_OPTIONS,
diff --git a/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts b/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts
index 202bf6ecb..1ea2ae922 100644
--- a/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts
+++ b/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts
@@ -103,7 +103,6 @@ export class NehubaLayerControlService implements OnDestroy{
           }
           returnVal[ngId][labelIndex] = { red, green, blue }
         }
-        this.activeColorMap = returnVal
         return returnVal
       })
     ),
-- 
GitLab