diff --git a/package.json b/package.json
index d4b47cfb3001a96f0e61c254a7c174ee31cb965a..b05fd47fcb2775a0304ecef3bf84318a0891656c 100644
--- a/package.json
+++ b/package.json
@@ -15,7 +15,7 @@
     "watch": "ng build --watch --configuration development",
     "test": "ng test",
     "test-ci": "ng test --progress false --watch false --browsers=ChromeHeadless",
-    "sapi-schema": "npx openapi-typescript@5.1.1 http://localhost:5000/v1_0/openapi.json --output ./src/atlasComponents/sapi/schema.ts",
+    "sapi-schema": "npx openapi-typescript@5.1.1 http://localhost:5000/v1_0/openapi.json --output ./src/atlasComponents/sapi/schema.ts && eslint ./src/atlasComponents/sapi/schema.ts --no-ignore --fix",
     "docs:json": "compodoc -p ./tsconfig.json -e json -d .",
     "storybook": "npm run docs:json && start-storybook -p 6006",
     "build-storybook": "npm run docs:json && build-storybook"
diff --git a/src/atlasComponents/annotations/annotation.service.ts b/src/atlasComponents/annotations/annotation.service.ts
new file mode 100644
index 0000000000000000000000000000000000000000..471e628bbff4e137d91d4bd5c3fb2633d25a6dd9
--- /dev/null
+++ b/src/atlasComponents/annotations/annotation.service.ts
@@ -0,0 +1,120 @@
+import { getUuid } from "src/util/fn";
+
+export type TNgAnnotationLine = {
+  type: 'line'
+  pointA: [number, number, number]
+  pointB: [number, number, number]
+  id: string
+  description?: string
+}
+
+export type TNgAnnotationPoint = {
+  type: 'point'
+  point: [number, number, number]
+  id: string
+  description?: string
+}
+
+export type AnnotationSpec = TNgAnnotationLine | TNgAnnotationPoint
+type _AnnotationSpec = Omit<AnnotationSpec, 'type'> & { type: number }
+type AnnotationRef = {}
+
+interface NgAnnotationLayer {
+  layer: {
+    localAnnotations: {
+      references: {
+        get(id: string): AnnotationRef
+        delete(id: string): void
+      }
+      update(ref: AnnotationRef, spec: _AnnotationSpec): void
+      add(spec: _AnnotationSpec): void
+      delete(spec: AnnotationRef):void
+      annotationMap: Map<string, _AnnotationSpec>
+    }
+    registerDisposer(fn: () => void): void
+  }
+  setVisible(flag: boolean): void
+}
+
+export class AnnotationLayer {
+  private nglayer: NgAnnotationLayer
+  constructor(
+    private name: string = getUuid(),
+    private color="#ffffff"
+  ){
+    const layerSpec = this.viewer.layerSpecification.getLayer(
+      this.name,
+      {
+        type: "annotation",
+        "annotationColor": this.color,
+        "annotations": [],
+        name: this.name,
+        transform: [
+          [1, 0, 0, 0],
+          [0, 1, 0, 0],
+          [0, 0, 1, 0],
+          [0, 0, 0, 1],
+        ]
+      }
+    )
+    this.nglayer = this.viewer.layerManager.addManagedLayer(layerSpec)
+    this.nglayer.layer.registerDisposer(() => {
+      this.nglayer = null
+    })
+  }
+  setVisible(flag: boolean){
+    this.nglayer.setVisible(flag)
+  }
+  dispose() {
+    try {
+      this.viewer.layerManager.removeManagedLayer(this.nglayer)
+    } catch (e) {
+
+    }
+  }
+
+  addAnnotation(spec: AnnotationSpec){
+    const localAnnotations = this.nglayer.layer.localAnnotations
+    const annSpec = this.parseNgSpecType(spec)
+    localAnnotations.add(
+      annSpec
+    )
+  }
+  removeAnnotation(spec: { id: string }) {
+    const { localAnnotations } = this.nglayer.layer
+    const ref = localAnnotations.references.get(spec.id)
+    if (ref) {
+      localAnnotations.delete(ref)
+      localAnnotations.references.delete(spec.id)
+    }
+  }
+  updateAnnotation(spec: AnnotationSpec) {
+    const localAnnotations = this.nglayer.layer.localAnnotations
+    const ref = localAnnotations.references.get(spec.id)
+    const _spec = this.parseNgSpecType(spec)
+    if (ref) {
+      localAnnotations.update(
+        ref,
+        _spec
+      )
+    } else {
+      localAnnotations.add(_spec)
+    }
+  }
+
+  private get viewer() {
+    if ((window as any).viewer) return (window as any).viewer
+    throw new Error(`window.viewer not defined`)
+  }
+
+  private parseNgSpecType(spec: AnnotationSpec): _AnnotationSpec{
+    let overwritingType = null
+    if (spec.type === 'point') overwritingType = 0
+    if (spec.type === 'line') overwritingType = 1
+    if (overwritingType === null) throw new Error(`overwrite type lookup failed for ${spec.type}`)
+    return {
+      ...spec,
+      type: overwritingType
+    }
+  }
+}
diff --git a/src/atlasComponents/annotations/index.ts b/src/atlasComponents/annotations/index.ts
new file mode 100644
index 0000000000000000000000000000000000000000..651584158e28cbeb2ea72a5f3cbb954e4e402310
--- /dev/null
+++ b/src/atlasComponents/annotations/index.ts
@@ -0,0 +1 @@
+export { AnnotationLayer, TNgAnnotationPoint } from "./annotation.service"
\ No newline at end of file
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.style.css b/src/atlasComponents/annotations/module.ts
similarity index 100%
rename from src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.style.css
rename to src/atlasComponents/annotations/module.ts
diff --git a/src/atlasComponents/sapi/core/sapiParcellation.ts b/src/atlasComponents/sapi/core/sapiParcellation.ts
index e33e20de39edda831adc161e5e2d2acf1b3219d9..5f956620942b6f2edb19a0046eeea8d59a958b20 100644
--- a/src/atlasComponents/sapi/core/sapiParcellation.ts
+++ b/src/atlasComponents/sapi/core/sapiParcellation.ts
@@ -44,9 +44,9 @@ export class SAPIParcellation{
     )
   }
 
-  getFeatureInstance(instanceId: string): Promise<SapiParcellationFeatureModel> {
+  getFeatureInstance(instanceId: string): Observable<SapiParcellationFeatureModel> {
     return this.sapi.http.get<SapiParcellationFeatureModel>(
       `${this.sapi.bsEndpoint}/atlases/${encodeURIComponent(this.atlasId)}/parcellations/${encodeURIComponent(this.id)}/features/${encodeURIComponent(instanceId)}`,
-    ).toPromise()
+    )
   }
 }
diff --git a/src/atlasComponents/sapi/core/sapiRegion.ts b/src/atlasComponents/sapi/core/sapiRegion.ts
index 0b2c4fb68c1646edbc4a01abf2ec34bd39ccd9ba..afadc4929dc48394affa9daa5a246b301b914b1f 100644
--- a/src/atlasComponents/sapi/core/sapiRegion.ts
+++ b/src/atlasComponents/sapi/core/sapiRegion.ts
@@ -1,7 +1,8 @@
 import { SAPI } from "..";
-import { SapiRegionalFeatureModel, SapiRegionMapInfoModel, SapiRegionModel } from "../type";
+import { SapiRegionalFeatureModel, SapiRegionMapInfoModel, SapiRegionModel, cleanIeegSessionDatasets, SapiIeegSessionModel, CleanedIeegDataset } from "../type";
 import { strToRgb, hexToRgb } from 'common/util'
-import { Observable } from "rxjs";
+import { forkJoin, Observable, of } from "rxjs";
+import { catchError, map } from "rxjs/operators";
 
 export class SAPIRegion{
 
@@ -26,29 +27,45 @@ export class SAPIRegion{
     this.prefix = `${this.sapi.bsEndpoint}/atlases/${encodeURIComponent(this.atlasId)}/parcellations/${encodeURIComponent(this.parcId)}/regions/${encodeURIComponent(this.id)}`
   }
 
-  getFeatures(spaceId: string): Promise<SapiRegionalFeatureModel[]> {
-    return this.sapi.http.get<SapiRegionalFeatureModel[]>(
-      `${this.prefix}/features`,
-      {
-        params: {
+  getFeatures(spaceId: string): Observable<(SapiRegionalFeatureModel | CleanedIeegDataset)[]> {
+    return forkJoin({
+      regionalFeatures: this.sapi.httpGet<SapiRegionalFeatureModel[]>(
+        `${this.prefix}/features`,
+        {
           space_id: spaceId
         }
-      }
-    ).toPromise()
+      ).pipe(
+        catchError((err, obs) => of([]))
+      ),
+      spatialFeatures: spaceId
+        ? this.sapi.getSpace(this.atlasId, spaceId).getFeatures({ parcellationId: this.parcId, region: this.id }).pipe(
+          catchError((err, obs) => {
+            console.log('error caught')
+            return of([])
+          }),
+          map(feats => {
+            const ieegSessions: SapiIeegSessionModel[] = feats.filter(feat => feat["@type"] === "siibra/features/ieegSession")
+            return cleanIeegSessionDatasets(ieegSessions)
+          }),
+        )
+        : of([] as CleanedIeegDataset[])
+    }).pipe(
+      map(({ regionalFeatures, spatialFeatures }) => {
+        return [...spatialFeatures, ...regionalFeatures]
+      })
+    )
   }
 
-  getFeatureInstance(instanceId: string, spaceId: string = null): Promise<SapiRegionalFeatureModel> {
-    return this.sapi.http.get<SapiRegionalFeatureModel>(
+  getFeatureInstance(instanceId: string, spaceId: string = null): Observable<SapiRegionalFeatureModel> {
+    return this.sapi.httpGet<SapiRegionalFeatureModel>(
       `${this.prefix}/features/${encodeURIComponent(instanceId)}`,
       {
-        params: {
-          space_id: spaceId
-        }
+        space_id: spaceId
       }
-    ).toPromise()
+    )
   }
 
-  getMapInfo(spaceId: string): Promise<SapiRegionMapInfoModel> {
+  getMapInfo(spaceId: string): Observable<SapiRegionMapInfoModel> {
     return this.sapi.http.get<SapiRegionMapInfoModel>(
       `${this.prefix}/regional_map/info`,
       {
@@ -56,7 +73,7 @@ export class SAPIRegion{
           space_id: spaceId
         }
       }
-    ).toPromise()
+    )
   }
 
   getMapUrl(spaceId: string): string {
diff --git a/src/atlasComponents/sapi/core/sapiSpace.ts b/src/atlasComponents/sapi/core/sapiSpace.ts
index bd33b4239601550338b500a49aa77292952e0045..3ed79e8a7c06be812fc56de29d83cd4d543f8fa4 100644
--- a/src/atlasComponents/sapi/core/sapiSpace.ts
+++ b/src/atlasComponents/sapi/core/sapiSpace.ts
@@ -32,13 +32,24 @@ export class SAPISpace{
     )
   }
 
-  getFeatures(modalityId: string, opts: SpatialFeatureOpts): Observable<SapiSpatialFeatureModel[]> {
+  getFeatures(opts: SpatialFeatureOpts): Observable<SapiSpatialFeatureModel[]> {
     const query: Record<string, string> = {}
     for (const [key, value] of Object.entries(opts)) {
       query[camelToSnake(key)] = value
     }
     return this.sapi.httpGet<SapiSpatialFeatureModel[]>(
-      `${this.sapi.bsEndpoint}/atlases/${encodeURIComponent(this.atlasId)}/spaces/${encodeURIComponent(this.id)}/features/${encodeURIComponent(modalityId)}`,
+      `${this.sapi.bsEndpoint}/atlases/${encodeURIComponent(this.atlasId)}/spaces/${encodeURIComponent(this.id)}/features`,
+      query
+    )
+  }
+
+  getFeatureInstance(instanceId: string, opts: SpatialFeatureOpts): Observable<SapiSpatialFeatureModel> {
+    const query: Record<string, string> = {}
+    for (const [key, value] of Object.entries(opts)) {
+      query[camelToSnake(key)] = value
+    }
+    return this.sapi.httpGet<SapiSpatialFeatureModel>(
+      `${this.sapi.bsEndpoint}/atlases/${encodeURIComponent(this.atlasId)}/spaces/${encodeURIComponent(this.id)}/features/${encodeURIComponent(instanceId)}`,
       query
     )
   }
diff --git a/src/atlasComponents/sapi/index.ts b/src/atlasComponents/sapi/index.ts
index b1bbb7c2313d3c88f505f59b4a4947bbb620c99d..7e00877e930cd38bd040751ccd4b5dadd5ee723b 100644
--- a/src/atlasComponents/sapi/index.ts
+++ b/src/atlasComponents/sapi/index.ts
@@ -12,6 +12,9 @@ export {
   SapiSpatialFeatureModel,
   SapiFeatureModel,
   SapiParcellationFeatureModel,
+  CleanedIeegDataset,
+  SxplrCleanedFeatureModel,
+  CLEANED_IEEG_DATASET_TYPE,
 } from "./type"
 
 export { SAPI } from "./sapi.service"
diff --git a/src/atlasComponents/sapi/module.ts b/src/atlasComponents/sapi/module.ts
index 452d71f70804eedce57e4c5b051e3c3abdff4be4..32701a9c5e86af9becbcbcbf23261d796f754f4a 100644
--- a/src/atlasComponents/sapi/module.ts
+++ b/src/atlasComponents/sapi/module.ts
@@ -2,17 +2,15 @@ import { NgModule } from "@angular/core";
 import { SAPI } from "./sapi.service";
 import { SpatialFeatureBBox } from "./directives/spatialFeatureBBox.directive"
 import { CommonModule } from "@angular/common";
-import { EffectsModule } from "@ngrx/effects";
-import { SapiEffects } from "./sapi.effects";
-import { HTTP_INTERCEPTORS } from "@angular/common/http";
+import { HttpClientModule, HTTP_INTERCEPTORS } from "@angular/common/http";
 import { PriorityHttpInterceptor } from "src/util/priority";
+import { MatSnackBarModule } from "@angular/material/snack-bar";
 
 @NgModule({
   imports: [
     CommonModule,
-    EffectsModule.forFeature([
-      SapiEffects
-    ])
+    HttpClientModule,
+    MatSnackBarModule,
   ],
   declarations: [
     SpatialFeatureBBox,
diff --git a/src/atlasComponents/sapi/sapi.effects.ts b/src/atlasComponents/sapi/sapi.effects.ts
deleted file mode 100644
index c1cb06fb33676d803368afaac8f39bbd0c7887ef..0000000000000000000000000000000000000000
--- a/src/atlasComponents/sapi/sapi.effects.ts
+++ /dev/null
@@ -1,12 +0,0 @@
-import { Injectable } from "@angular/core";
-import { SAPI } from "./sapi.service"
-
-@Injectable()
-export class SapiEffects{
-
-  constructor(
-    private sapiSvc: SAPI
-  ){
-
-  }
-}
diff --git a/src/atlasComponents/sapi/sapi.service.ts b/src/atlasComponents/sapi/sapi.service.ts
index 86c05ee11654f9041900de8dba83be00dd26b0cf..de44e86da06479ad232478e98d05b52491303c7c 100644
--- a/src/atlasComponents/sapi/sapi.service.ts
+++ b/src/atlasComponents/sapi/sapi.service.ts
@@ -1,10 +1,9 @@
-import { Inject, Injectable } from "@angular/core";
+import { Injectable } from "@angular/core";
 import { HttpClient } from '@angular/common/http';
-import { BS_ENDPOINT } from 'src/util/constants';
-import { map, shareReplay, take, tap } from "rxjs/operators";
+import { map, shareReplay, tap } from "rxjs/operators";
 import { SAPIAtlas, SAPISpace } from './core'
-import { SapiAtlasModel, SapiParcellationModel, SapiQueryParam, SapiRegionalFeatureModel, SapiRegionModel, SapiSpaceModel, SpyNpArrayDataModel } from "./type";
-import { CachedFunction, getExportNehuba } from "src/util/fn";
+import { SapiAtlasModel, SapiParcellationModel, SapiQueryParam, SapiRegionalFeatureModel, SapiRegionModel, SapiSpaceModel, SpyNpArrayDataModel, SxplrCleanedFeatureModel } from "./type";
+import { getExportNehuba } from "src/util/fn";
 import { SAPIParcellation } from "./core/sapiParcellation";
 import { SAPIRegion } from "./core/sapiRegion"
 import { MatSnackBar } from "@angular/material/snack-bar";
@@ -71,10 +70,7 @@ export class SAPI{
     return parc.getRegions(spaceId, queryParam)
   }
 
-  @CachedFunction({
-    serialization: (atlasId, parcId, spaceId, regionId, ...args) => `sapi::getRegions::${atlasId}::${parcId}::${spaceId}::${regionId}`
-  })
-  getRegionFeatures(atlasId: string, parcId: string, spaceId: string, regionId: string, priority = 0): Promise<SapiRegionalFeatureModel[]>{
+  getRegionFeatures(atlasId: string, parcId: string, spaceId: string, regionId: string, priority = 0): Observable<(SapiRegionalFeatureModel | SxplrCleanedFeatureModel)[]>{
 
     const reg = this.getRegion(atlasId, parcId, regionId)
     return reg.getFeatures(spaceId)
diff --git a/src/atlasComponents/sapi/schema.ts b/src/atlasComponents/sapi/schema.ts
index c6b5bbca49d58c286aa0381ce8752ce59b4071ac..483b4d62789e416bb058b676c31a728a52715b71 100644
--- a/src/atlasComponents/sapi/schema.ts
+++ b/src/atlasComponents/sapi/schema.ts
@@ -10,11 +10,11 @@ export interface paths {
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}/regions/{region_id}/features": {
     /** Returns all regional features for a region. */
-    get: operations["get_all_features_for_region_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features_get"]
+    get: operations["get_all_regional_features_for_region_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features_get"]
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}/regions/{region_id}/features/{feature_id}": {
     /** Returns a feature for a region, as defined by by the modality and feature ID */
-    get: operations["get_regional_modality_by_id_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features__feature_id__get"]
+    get: operations["get_single_detailed_regional_feature_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features__feature_id__get"]
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}/regions/{region_id}/regional_map/info": {
     /** Returns information about a regional map for given region name. */
@@ -33,19 +33,19 @@ export interface paths {
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}/features/{feature_id}": {
     /** Returns a global feature for a specific modality id. */
-    get: operations["get_single_global_feature_detail_atlases__atlas_id__parcellations__parcellation_id__features__feature_id__get"]
+    get: operations["get_single_detailed_global_feature_atlases__atlas_id__parcellations__parcellation_id__features__feature_id__get"]
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}/features": {
     /** Returns all global features for a parcellation. */
-    get: operations["get_global_features_names_atlases__atlas_id__parcellations__parcellation_id__features_get"]
+    get: operations["get_all_global_features_for_parcellation_atlases__atlas_id__parcellations__parcellation_id__features_get"]
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}/volumes": {
     /** Returns one parcellation for given id. */
-    get: operations["get_volumes_by_id_atlases__atlas_id__parcellations__parcellation_id__volumes_get"]
+    get: operations["get_volumes_for_parcellation_atlases__atlas_id__parcellations__parcellation_id__volumes_get"]
   }
   "/atlases/{atlas_id}/parcellations/{parcellation_id}": {
     /** Returns one parcellation for given id. */
-    get: operations["get_parcellation_by_id_atlases__atlas_id__parcellations__parcellation_id__get"]
+    get: operations["get_single_parcellation_detail_atlases__atlas_id__parcellations__parcellation_id__get"]
   }
   "/atlases/{atlas_id}/spaces": {
     /** Returns all spaces that are defined in the siibra client. */
@@ -64,18 +64,18 @@ export interface paths {
      * Get a detailed view on a single spatial feature.
      * A parcellation id and region id can be provided optional to get more details.
      */
-    get: operations["get_single_spatial_feature_detail_atlases__atlas_id__spaces__space_id__features__feature_id__get"]
+    get: operations["get_single_detailed_spatial_feature_atlases__atlas_id__spaces__space_id__features__feature_id__get"]
   }
   "/atlases/{atlas_id}/spaces/{space_id}/features": {
     /** Return all possible feature names and links to get more details */
-    get: operations["get_spatial_features_from_space_atlases__atlas_id__spaces__space_id__features_get"]
+    get: operations["get_all_spatial_features_for_space_atlases__atlas_id__spaces__space_id__features_get"]
   }
   "/atlases/{atlas_id}/spaces/{space_id}/volumes": {
-    get: operations["get_one_space_volumes_atlases__atlas_id__spaces__space_id__volumes_get"]
+    get: operations["get_volumes_for_space_atlases__atlas_id__spaces__space_id__volumes_get"]
   }
   "/atlases/{atlas_id}/spaces/{space_id}": {
     /** Returns one space for given id, with links to further resources */
-    get: operations["get_one_space_by_id_atlases__atlas_id__spaces__space_id__get"]
+    get: operations["get_single_space_detail_atlases__atlas_id__spaces__space_id__get"]
   }
   "/atlases": {
     /** Get all atlases known by siibra. */
@@ -153,10 +153,10 @@ export interface components {
       /** @Id */
       "@id": string
       /**
-       * Type
+       * @Type
        * @constant
        */
-      type?: "siibra/core/dataset"
+      "@type"?: "siibra/core/dataset"
       metadata: components["schemas"]["siibra__openminds__core__v4__products__datasetVersion__Model"]
       /** Urls */
       urls: components["schemas"]["Url"][]
@@ -181,6 +181,8 @@ export interface components {
     }
     /** BoundingBoxModel */
     BoundingBoxModel: {
+      /** @Type */
+      "@type": string
       /** Space */
       space: { [key: string]: string }
       center: components["schemas"]["siibra__openminds__SANDS__v3__miscellaneous__coordinatePoint__Model"]
@@ -195,11 +197,8 @@ export interface components {
     ConnectivityMatrixDataModel: {
       /** @Id */
       "@id": string
-      /**
-       * Type
-       * @constant
-       */
-      type?: "siibra/features/connectivity"
+      /** @Type */
+      "@type": string
       /** Name */
       name: string
       /** Parcellations */
@@ -213,10 +212,10 @@ export interface components {
       /** @Id */
       "@id": string
       /**
-       * Type
+       * @Type
        * @constant
        */
-      type?: "siibra/core/dataset"
+      "@type"?: "siibra/core/dataset"
       metadata: components["schemas"]["siibra__openminds__core__v4__products__datasetVersion__Model"]
       /** Urls */
       urls: components["schemas"]["Url"][]
@@ -310,12 +309,16 @@ export interface components {
     }
     /** IEEGContactPointModel */
     IEEGContactPointModel: {
+      /** Inroi */
+      inRoi?: boolean
       /** Id */
       id: string
       point: components["schemas"]["siibra__openminds__SANDS__v3__miscellaneous__coordinatePoint__Model"]
     }
     /** IEEGElectrodeModel */
     IEEGElectrodeModel: {
+      /** Inroi */
+      inRoi?: boolean
       /** Electrode Id */
       electrode_id: string
       /** Contact Points */
@@ -325,13 +328,15 @@ export interface components {
     }
     /** IEEGSessionModel */
     IEEGSessionModel: {
+      /** Inroi */
+      inRoi?: boolean
       /** @Id */
       "@id": string
       /**
-       * Type
+       * @Type
        * @constant
        */
-      type?: "siibra/features/ieegSession"
+      "@type"?: "siibra/features/ieegSession"
       dataset: components["schemas"]["DatasetJsonModel"]
       /** Sub Id */
       sub_id: string
@@ -459,10 +464,10 @@ export interface components {
       /** @Id */
       "@id": string
       /**
-       * Type
+       * @Type
        * @constant
        */
-      type?: "siibra/features/receptor"
+      "@type"?: "siibra/features/receptor"
       metadata: components["schemas"]["siibra__openminds__core__v4__products__datasetVersion__Model"]
       /** Urls */
       urls: components["schemas"]["Url"][]
@@ -734,10 +739,10 @@ export interface components {
       /** @Id */
       "@id": string
       /**
-       * Type
+       * @Type
        * @constant
        */
-      type?: "siibra/features/voi"
+      "@type"?: "siibra/features/voi"
       metadata: components["schemas"]["siibra__openminds__core__v4__products__datasetVersion__Model"]
       /** Urls */
       urls: components["schemas"]["Url"][]
@@ -784,10 +789,10 @@ export interface components {
       /** @Id */
       "@id": string
       /**
-       * Type
+       * @Type
        * @constant
        */
-      type?: "siibra/core/dataset"
+      "@type"?: "siibra/core/dataset"
       metadata: components["schemas"]["siibra__openminds__core__v4__products__datasetVersion__Model"]
       /** Urls */
       urls: components["schemas"]["Url"][]
@@ -1333,7 +1338,7 @@ export interface operations {
     }
   }
   /** Returns all regional features for a region. */
-  get_all_features_for_region_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features_get: {
+  get_all_regional_features_for_region_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features_get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1363,7 +1368,7 @@ export interface operations {
     }
   }
   /** Returns a feature for a region, as defined by by the modality and feature ID */
-  get_regional_modality_by_id_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features__feature_id__get: {
+  get_single_detailed_regional_feature_atlases__atlas_id__parcellations__parcellation_id__regions__region_id__features__feature_id__get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1498,7 +1503,7 @@ export interface operations {
     }
   }
   /** Returns a global feature for a specific modality id. */
-  get_single_global_feature_detail_atlases__atlas_id__parcellations__parcellation_id__features__feature_id__get: {
+  get_single_detailed_global_feature_atlases__atlas_id__parcellations__parcellation_id__features__feature_id__get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1525,7 +1530,7 @@ export interface operations {
     }
   }
   /** Returns all global features for a parcellation. */
-  get_global_features_names_atlases__atlas_id__parcellations__parcellation_id__features_get: {
+  get_all_global_features_for_parcellation_atlases__atlas_id__parcellations__parcellation_id__features_get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1555,7 +1560,7 @@ export interface operations {
     }
   }
   /** Returns one parcellation for given id. */
-  get_volumes_by_id_atlases__atlas_id__parcellations__parcellation_id__volumes_get: {
+  get_volumes_for_parcellation_atlases__atlas_id__parcellations__parcellation_id__volumes_get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1578,7 +1583,7 @@ export interface operations {
     }
   }
   /** Returns one parcellation for given id. */
-  get_parcellation_by_id_atlases__atlas_id__parcellations__parcellation_id__get: {
+  get_single_parcellation_detail_atlases__atlas_id__parcellations__parcellation_id__get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1674,7 +1679,7 @@ export interface operations {
    * Get a detailed view on a single spatial feature.
    * A parcellation id and region id can be provided optional to get more details.
    */
-  get_single_spatial_feature_detail_atlases__atlas_id__spaces__space_id__features__feature_id__get: {
+  get_single_detailed_spatial_feature_atlases__atlas_id__spaces__space_id__features__feature_id__get: {
     parameters: {
       path: {
         feature_id: string
@@ -1682,8 +1687,8 @@ export interface operations {
         space_id: string
       }
       query: {
-        parcellation_id: string
-        region: string
+        parcellation_id?: string
+        region?: string
         bbox?: string
       }
     }
@@ -1706,7 +1711,7 @@ export interface operations {
     }
   }
   /** Return all possible feature names and links to get more details */
-  get_spatial_features_from_space_atlases__atlas_id__spaces__space_id__features_get: {
+  get_all_spatial_features_for_space_atlases__atlas_id__spaces__space_id__features_get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1736,7 +1741,7 @@ export interface operations {
       }
     }
   }
-  get_one_space_volumes_atlases__atlas_id__spaces__space_id__volumes_get: {
+  get_volumes_for_space_atlases__atlas_id__spaces__space_id__volumes_get: {
     parameters: {
       path: {
         atlas_id: string
@@ -1759,7 +1764,7 @@ export interface operations {
     }
   }
   /** Returns one space for given id, with links to further resources */
-  get_one_space_by_id_atlases__atlas_id__spaces__space_id__get: {
+  get_single_space_detail_atlases__atlas_id__spaces__space_id__get: {
     parameters: {
       path: {
         atlas_id: string
diff --git a/src/atlasComponents/sapi/stories.base.ts b/src/atlasComponents/sapi/stories.base.ts
index f4162b72d80ec585472dbe40e77423336f0ec630..51fde4f0cd5695f6055398e8bd9ec39ed469c541 100644
--- a/src/atlasComponents/sapi/stories.base.ts
+++ b/src/atlasComponents/sapi/stories.base.ts
@@ -1,5 +1,5 @@
 import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionalFeatureModel, SapiRegionModel, SapiSpaceModel } from "."
-import { SapiParcellationFeatureModel } from "./type"
+import { cleanIeegSessionDatasets, SapiParcellationFeatureModel, SapiSpatialFeatureModel, SxplrCleanedFeatureModel } from "./type"
 import addons from '@storybook/addons';
 import { DARKTHEME } from "src/util/injectionTokens";
 import { APP_INITIALIZER, NgZone } from "@angular/core";
@@ -101,11 +101,11 @@ export async function getJba29Regions(): Promise<SapiRegionModel[]> {
   return await getParcRegions(atlasId.human, parcId.human.jba29, spaceId.human.mni152)
 }
 
-export async function getHoc1Left(spaceId=null): Promise<SapiRegionModel> {
+export async function getHoc1Right(spaceId=null): Promise<SapiRegionModel> {
   if (!spaceId) {
-    return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20left`)).json()
+    return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20right`)).json()
   }
-  return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20left?space_id=${encodeURIComponent(spaceId)}`)).json()
+  return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20right?space_id=${encodeURIComponent(spaceId)}`)).json()
 }
 
 export async function get44Left(spaceId=null): Promise<SapiRegionModel> {
@@ -115,14 +115,37 @@ export async function get44Left(spaceId=null): Promise<SapiRegionModel> {
   return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/area%2044%20left?space_id=${encodeURIComponent(spaceId)}`)).json()
 }
 
-export async function getHoc1Features(): Promise<SapiRegionalFeatureModel[]> {
-  return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20left/features`)).json()
+export async function getHoc1RightSpatialFeatures(): Promise<SxplrCleanedFeatureModel[]> {
+  const json: SapiSpatialFeatureModel[] = await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/spaces/${spaceId.human.mni152}/features?parcellation_id=2.9&region=hoc1%20right`)).json()
+  return cleanIeegSessionDatasets(json.filter(it => it['@type'] === "siibra/features/ieegSession"))
 }
 
-export async function getHoc1FeatureDetail(featId: string): Promise<SapiRegionalFeatureModel>{
-  return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20left/features/${encodeURIComponent(featId)}`)).json()
+export async function getHoc1RightFeatures(): Promise<SapiRegionalFeatureModel[]> {
+  return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20right/features`)).json()
+}
+
+export async function getHoc1RightFeatureDetail(featId: string): Promise<SapiRegionalFeatureModel>{
+  return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/regions/hoc1%20right/features/${encodeURIComponent(featId)}`)).json()
 }
 
 export async function getJba29Features(): Promise<SapiParcellationFeatureModel[]> {
   return await (await fetch(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/parcellations/${parcId.human.jba29}/features`)).json()
 }
+
+export async function getBigbrainSpatialFeatures(): Promise<SapiSpatialFeatureModel[]>{
+  const bbox = [
+    [-1000, -1000, -1000],
+    [1000, 1000, 1000]
+  ]
+  const url = new URL(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/spaces/${spaceId.human.bigbrain}/features`)
+  url.searchParams.set(`bbox`, JSON.stringify(bbox))
+  return await (await fetch(url.toString())).json()
+}
+
+export async function getMni152SpatialFeatureHoc1Right(): Promise<SapiSpatialFeatureModel[]>{
+  
+  const url = new URL(`${SAPI.bsEndpoint}/atlases/${atlasId.human}/spaces/${spaceId.human.mni152}/features`)
+  url.searchParams.set(`parcellation_id`, parcId.human.jba29)
+  url.searchParams.set("region", 'hoc1 right')
+  return await (await fetch(url.toString())).json()
+}
diff --git a/src/atlasComponents/sapi/type.ts b/src/atlasComponents/sapi/type.ts
index 77a94d21f0ebc6ad92236fe2324642bf746615a2..97519d6fd6fcf91e68880e7f8e359f508897815b 100644
--- a/src/atlasComponents/sapi/type.ts
+++ b/src/atlasComponents/sapi/type.ts
@@ -1,6 +1,6 @@
 import { OperatorFunction } from "rxjs"
 import { map } from "rxjs/operators"
-import { components } from "./schema"
+import { components, operations, paths } from "./schema"
 
 export type IdName = {
   id: string
@@ -15,35 +15,17 @@ export type SapiAtlasModel = components["schemas"]["SapiAtlasModel"]
 export type SapiSpaceModel = components["schemas"]["SapiSpaceModel"]
 export type SapiParcellationModel = components["schemas"]["SapiParcellationModel"]
 export type SapiRegionModel = components["schemas"]["siibra__openminds__SANDS__v3__atlas__parcellationEntityVersion__Model"]
-export type SapiRegionMapInfoModel = components["schemas"]["NiiMetadataModel"]
 
-export type SapiSpatialFeatureModel = components["schemas"]["VOIDataModel"]
+export type SapiRegionMapInfoModel = components["schemas"]["NiiMetadataModel"]
 export type SapiVOIDataResponse = components["schemas"]["VOIDataModel"]
-
 export type SapiVolumeModel = components["schemas"]["VolumeModel"]
 export type SapiDatasetModel = components["schemas"]["DatasetJsonModel"]
-
 export type SpyNpArrayDataModel = components["schemas"]["NpArrayDataModel"]
-
-
-export function FeatureTypeGuard(input: SapiFeatureModel) {
-  if (input.type === "siibra/core/dataset") {
-    return input as SapiDatasetModel
-  }
-  if (input.type === "siibra/features/connectivity") {
-    return input as SapiParcellationFeatureMatrixModel
-  }
-  if (input.type === "siibra/features/receptor") {
-    return input as SapiRegionalFeatureReceptorModel
-  }
-  if (input.type === "siibra/features/voi") {
-    return input as SapiVOIDataResponse
-  }
-  if (input.type === "spy/serialization-error") {
-    return input as SapiSerializationErrorModel
-  }
-  throw new Error(`cannot parse type: ${input}`)
-}
+export type SapiIeegSessionModel = components["schemas"]["IEEGSessionModel"]
+/**
+ * utility types
+ */
+type PathReturn<T extends keyof paths> = Required<paths[T]["get"]["responses"][200]["content"]["application/json"]>
 
 /**
  * serialization error type
@@ -51,16 +33,53 @@ export function FeatureTypeGuard(input: SapiFeatureModel) {
 export type SapiSerializationErrorModel = components["schemas"]["SerializationErrorModel"]
 
 /**
- * datafeatures
+ * datafeatures from operations
  */
-export type SapiRegionalFeatureReceptorModel = components["schemas"]["ReceptorDatasetModel"]
-export type SapiRegionalFeatureModel = components["schemas"]["BaseDatasetJsonModel"] | SapiRegionalFeatureReceptorModel
 
-export type SapiParcellationFeatureMatrixModel = components["schemas"]["ConnectivityMatrixDataModel"]
-export type SapiParcellationFeatureModel = SapiParcellationFeatureMatrixModel | SapiSerializationErrorModel
+export type SapiRegionalFeatureModel = PathReturn<"/atlases/{atlas_id}/parcellations/{parcellation_id}/regions/{region_id}/features/{feature_id}">
+export type SapiParcellationFeatureModel = PathReturn<"/atlases/{atlas_id}/parcellations/{parcellation_id}/features/{feature_id}">
+export type SapiSpatialFeatureModel = PathReturn<"/atlases/{atlas_id}/spaces/{space_id}/features/{feature_id}">
 
 export type SapiFeatureModel = SapiRegionalFeatureModel | SapiSpatialFeatureModel | SapiParcellationFeatureModel
 
+/**
+ * specific data features
+ */
+
+export type SapiRegionalFeatureReceptorModel = components["schemas"]["ReceptorDatasetModel"]
+export type SapiParcellationFeatureMatrixModel = components["schemas"]["ConnectivityMatrixDataModel"]
+
+
+export const CLEANED_IEEG_DATASET_TYPE = 'sxplr/cleanedIeegDataset'
+export type CleanedIeegDataset = Required<
+  Omit<SapiDatasetModel, "@type"> & {
+    '@type': 'sxplr/cleanedIeegDataset'
+    sessions: Record<string, Omit<SapiIeegSessionModel, "dataset">>
+  }
+>
+
+export function cleanIeegSessionDatasets(ieegSessions: SapiIeegSessionModel[]): CleanedIeegDataset[]{
+  const returnArr: CleanedIeegDataset[] = []
+  for (const sess of ieegSessions) {
+    const { dataset, ...itemToAppend } = sess
+    const existing = returnArr.find(it => it["@id"] === dataset["@id"])
+    if (!existing) {
+      returnArr.push({
+        ...dataset,
+        '@type': CLEANED_IEEG_DATASET_TYPE,
+        sessions: {
+          [sess.sub_id]: itemToAppend
+        }
+      })
+      continue
+    }
+    existing.sessions[sess.sub_id] = itemToAppend
+  }
+  return returnArr
+}
+
+export type SxplrCleanedFeatureModel = CleanedIeegDataset
+
 export function guardPipe<
   InputType,
   GuardType extends InputType
diff --git a/src/atlasComponents/sapiViews/core/atlas/module.ts b/src/atlasComponents/sapiViews/core/atlas/module.ts
index a41cdb25c60ea1255837923285522a32ca85dfcc..691d41303c80c52229423586c9243d27fc419479 100644
--- a/src/atlasComponents/sapiViews/core/atlas/module.ts
+++ b/src/atlasComponents/sapiViews/core/atlas/module.ts
@@ -7,6 +7,7 @@ import { SapiViewsUtilModule } from "../../util";
 import { SapiViewsCoreParcellationModule } from "../parcellation";
 import { SapiViewsCoreSpaceModule } from "../space";
 import { SapiViewsCoreAtlasAtlasDropdownSelector } from "./dropdownAtlasSelector/dropdownAtlasSelector.component";
+import { SapiViewsCoreAtlasSplashScreen } from "./splashScreen/splashScreen.component";
 import { SapiViewsCoreAtlasAtlasTmplParcSelector } from "./tmplParcSelector/tmplParcSelector.component";
 
 @NgModule({
@@ -22,10 +23,12 @@ import { SapiViewsCoreAtlasAtlasTmplParcSelector } from "./tmplParcSelector/tmpl
   declarations: [
     SapiViewsCoreAtlasAtlasDropdownSelector,
     SapiViewsCoreAtlasAtlasTmplParcSelector,
+    SapiViewsCoreAtlasSplashScreen,
   ],
   exports: [
     SapiViewsCoreAtlasAtlasDropdownSelector,
     SapiViewsCoreAtlasAtlasTmplParcSelector,
+    SapiViewsCoreAtlasSplashScreen,
   ]
 })
 
diff --git a/src/atlasComponents/splashScreen/splashScreen/splashScreen.component.ts b/src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.component.ts
similarity index 95%
rename from src/atlasComponents/splashScreen/splashScreen/splashScreen.component.ts
rename to src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.component.ts
index 775b1a486bc18ec333ce8aec1a32ccdcc8c14091..056e3660c4243ee41bff9e5090354bd6e6fb2deb 100644
--- a/src/atlasComponents/splashScreen/splashScreen/splashScreen.component.ts
+++ b/src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.component.ts
@@ -14,7 +14,7 @@ import { atlasSelection } from "src/state"
   changeDetection: ChangeDetectionStrategy.OnPush,
 })
 
-export class SplashScreen {
+export class SapiViewsCoreAtlasSplashScreen {
 
   public finishedLoading: boolean = false
 
diff --git a/src/atlasComponents/splashScreen/splashScreen/splashScreen.style.css b/src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.style.css
similarity index 100%
rename from src/atlasComponents/splashScreen/splashScreen/splashScreen.style.css
rename to src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.style.css
diff --git a/src/atlasComponents/splashScreen/splashScreen/splashScreen.template.html b/src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.template.html
similarity index 100%
rename from src/atlasComponents/splashScreen/splashScreen/splashScreen.template.html
rename to src/atlasComponents/sapiViews/core/atlas/splashScreen/splashScreen.template.html
diff --git a/src/atlasComponents/sapiViews/core/datasets/dataset/dataset.stories.ts b/src/atlasComponents/sapiViews/core/datasets/dataset/dataset.stories.ts
index ff2a0406288b6db8a48c20e7de29f6b29edcb0a3..acec7a744768e383bdb511d15b4a8d537b9e0633 100644
--- a/src/atlasComponents/sapiViews/core/datasets/dataset/dataset.stories.ts
+++ b/src/atlasComponents/sapiViews/core/datasets/dataset/dataset.stories.ts
@@ -2,7 +2,7 @@ import { CommonModule } from "@angular/common"
 import { HttpClientModule } from "@angular/common/http"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI } from "src/atlasComponents/sapi"
-import { getHoc1FeatureDetail, getHoc1Features, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1RightFeatureDetail, getHoc1RightFeatures, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { SapiViewsCoreDatasetModule } from ".."
 import { DatasetView } from "./dataset.component"
 
@@ -35,9 +35,9 @@ const Template: Story<DatasetView> = (args: DatasetView, { loaded }) => {
 }
 
 const loadFeat = async () => {
-  const features = await getHoc1Features()
-  const receptorfeat = features.find(f => f.type === "siibra/core/dataset")
-  const feature = await getHoc1FeatureDetail(receptorfeat["@id"])
+  const features = await getHoc1RightFeatures()
+  const receptorfeat = features.find(f => f['@type'] === "siibra/core/dataset")
+  const feature = await getHoc1RightFeatureDetail(receptorfeat["@id"])
   return {
     feature
   }
diff --git a/src/atlasComponents/sapiViews/core/region/region/chip/region.chip.stories.ts b/src/atlasComponents/sapiViews/core/region/region/chip/region.chip.stories.ts
index 1fc06697565f11e974950f757052ead015238ed6..ec74e25aadf0b5f3d00ef164efd2ff19238259bb 100644
--- a/src/atlasComponents/sapiViews/core/region/region/chip/region.chip.stories.ts
+++ b/src/atlasComponents/sapiViews/core/region/region/chip/region.chip.stories.ts
@@ -1,8 +1,8 @@
 import { CommonModule } from "@angular/common"
 import { HttpClientModule } from "@angular/common/http"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
-import { SAPI, SapiParcellationModel } from "src/atlasComponents/sapi"
-import { atlasId, getAtlas, provideDarkTheme, getParc, getHumanAtlas, getJba29, getMni152, getHoc1Left, get44Left } from "src/atlasComponents/sapi/stories.base"
+import { SAPI } from "src/atlasComponents/sapi"
+import { provideDarkTheme, getHumanAtlas, getJba29, getMni152, getHoc1Right, get44Left } from "src/atlasComponents/sapi/stories.base"
 import { AngularMaterialModule } from "src/sharedModules"
 import { SapiViewsCoreRegionModule } from "../../module"
 import { SapiViewsCoreRegionRegionChip } from "./region.chip.component"
@@ -72,7 +72,7 @@ Default.loaders = [
     const atlas = await getHumanAtlas()
     const parcellation = await getJba29()
     const template = await getMni152()
-    const region = await getHoc1Left()
+    const region = await getHoc1Right()
 
     return {
       atlas,
diff --git a/src/atlasComponents/sapiViews/core/region/region/listItem/region.listItem.stories.ts b/src/atlasComponents/sapiViews/core/region/region/listItem/region.listItem.stories.ts
index 900bd2e0a0f01a7ec5797aec22c19bb539aee4a7..abc0bef7a287e6f8e8d2f284d52d0bf0b99f9258 100644
--- a/src/atlasComponents/sapiViews/core/region/region/listItem/region.listItem.stories.ts
+++ b/src/atlasComponents/sapiViews/core/region/region/listItem/region.listItem.stories.ts
@@ -2,7 +2,7 @@ import { CommonModule } from "@angular/common"
 import { HttpClientModule } from "@angular/common/http"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI } from "src/atlasComponents/sapi"
-import { getHoc1Left, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1Right, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { SapiViewsCoreRegionModule } from "../../module"
 import { SapiViewsCoreRegionRegionListItem } from "./region.listItem.component"
 
@@ -55,7 +55,7 @@ const loadRegions = async () => {
   const human = await getHumanAtlas()
   const mni152 = await getMni152()
   const jba29 = await getJba29()
-  const hoc1left = await getHoc1Left(mni152["@id"])
+  const hoc1left = await getHoc1Right(mni152["@id"])
 
   return {
     human,
diff --git a/src/atlasComponents/sapiViews/core/region/region/region.features.directive.ts b/src/atlasComponents/sapiViews/core/region/region/region.features.directive.ts
index d542fc05dd988f4f599b292633b20445402f8dea..9c3cad17f525199cc4f91b21a890dff98c822235 100644
--- a/src/atlasComponents/sapiViews/core/region/region/region.features.directive.ts
+++ b/src/atlasComponents/sapiViews/core/region/region/region.features.directive.ts
@@ -2,6 +2,7 @@ import { Directive, OnChanges, SimpleChanges } from "@angular/core";
 import { BehaviorSubject, merge, Observable } from "rxjs";
 import { switchMap,  filter, startWith, shareReplay, mapTo, delay, tap } from "rxjs/operators";
 import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionalFeatureModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi";
+import { SxplrCleanedFeatureModel } from "src/atlasComponents/sapi/type";
 import { SapiViewsCoreRegionRegionBase } from "./region.base.directive";
 
 @Directive({
@@ -27,7 +28,7 @@ export class SapiViewsCoreRegionRegionalFeatureDirective extends SapiViewsCoreRe
     super(sapi)
   }
 
-  private features$: Observable<SapiRegionalFeatureModel[]> = this.ATPR$.pipe(
+  private features$: Observable<(SapiRegionalFeatureModel|SxplrCleanedFeatureModel)[]> = this.ATPR$.pipe(
     filter(arg => {
       if (!arg) return false
       const { atlas, parcellation, region, template } = arg
@@ -36,7 +37,7 @@ export class SapiViewsCoreRegionRegionalFeatureDirective extends SapiViewsCoreRe
     switchMap(({ atlas, parcellation, region, template }) => this.sapi.getRegionFeatures(atlas["@id"], parcellation["@id"], template["@id"], region.name)),
   )
 
-  public listOfFeatures$: Observable<SapiRegionalFeatureModel[]> = this.features$.pipe(
+  public listOfFeatures$: Observable<(SapiRegionalFeatureModel|SxplrCleanedFeatureModel)[]> = this.features$.pipe(
     startWith([]),
     shareReplay(1),
   )
diff --git a/src/atlasComponents/sapiViews/core/region/region/rich/region.rich.stories.ts b/src/atlasComponents/sapiViews/core/region/region/rich/region.rich.stories.ts
index 551ed5a081fb5536fc91ff2e2d4c2196aed3740f..6e9f8907cd68facc3c60f31b6e28cadbb4873573 100644
--- a/src/atlasComponents/sapiViews/core/region/region/rich/region.rich.stories.ts
+++ b/src/atlasComponents/sapiViews/core/region/region/rich/region.rich.stories.ts
@@ -2,7 +2,7 @@ import { CommonModule } from "@angular/common"
 import { HttpClientModule } from "@angular/common/http"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI } from "src/atlasComponents/sapi"
-import { atlasId, getHoc1Left, getHumanAtlas, getJba29, getJba29Regions, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1Right, getHumanAtlas, getJba29, getJba29Regions, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { SapiViewsCoreRegionModule } from "../../module"
 import { SapiViewsCoreRegionRegionRich } from "./region.rich.component"
 import { action } from '@storybook/addon-actions';
@@ -61,7 +61,7 @@ const loadRegions = async () => {
   const human = await getHumanAtlas()
   const mni152 = await getMni152()
   const jba29 = await getJba29()
-  const hoc1left = await getHoc1Left(mni152["@id"])
+  const hoc1left = await getHoc1Right(mni152["@id"])
   return {
     human,
     mni152,
diff --git a/src/atlasComponents/sapiViews/features/connectivity/connectivityMatrix/connectivityMatrix.component.ts b/src/atlasComponents/sapiViews/features/connectivity/connectivityMatrix/connectivityMatrix.component.ts
index 69cd8b70d89a6d9fc65be10e8448da65ff25ce88..44fa05d6623595e6100e4e86149f52c6fe5b4bf1 100644
--- a/src/atlasComponents/sapiViews/features/connectivity/connectivityMatrix/connectivityMatrix.component.ts
+++ b/src/atlasComponents/sapiViews/features/connectivity/connectivityMatrix/connectivityMatrix.component.ts
@@ -31,7 +31,7 @@ export class ConnectivityMatrixView implements OnChanges, AfterViewInit{
   
   private async fetchMatrixData(){
     this.matrixData = null
-    const matrix = await this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"]).getFeatureInstance(this.featureId)
+    const matrix = await this.sapi.getParcellation(this.atlas["@id"], this.parcellation["@id"]).getFeatureInstance(this.featureId).toPromise()
     if ((matrix as SapiSerializationErrorModel)?.type === "spy/serialization-error") {
       return
     }
diff --git a/src/atlasComponents/sapiViews/features/entry/entry.component.ts b/src/atlasComponents/sapiViews/features/entry/entry.component.ts
index 79ee7640af146039fb2fc14d566c12daf7bef396..53b27fb3087946cb260a1a2087a93e1cacb776bb 100644
--- a/src/atlasComponents/sapiViews/features/entry/entry.component.ts
+++ b/src/atlasComponents/sapiViews/features/entry/entry.component.ts
@@ -1,5 +1,9 @@
-import { Component, Input } from "@angular/core";
-import { SapiFeatureModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi";
+import { Component, Input, OnDestroy } from "@angular/core";
+import { Store } from "@ngrx/store";
+import { AnnotationLayer, TNgAnnotationPoint } from "src/atlasComponents/annotations";
+import { SapiFeatureModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel, CLEANED_IEEG_DATASET_TYPE } from "src/atlasComponents/sapi";
+import { IeegOnFocusEvent, ContactPoint, Electrode, Session, IeegOnDefocusEvent } from "../ieeg";
+import { atlasSelection, annotation, atlasAppearance } from "src/state"
 
 @Component({
   selector: 'sxplr-sapiviews-features-entry',
@@ -9,7 +13,7 @@ import { SapiFeatureModel, SapiParcellationModel, SapiRegionModel, SapiSpaceMode
   ]
 })
 
-export class FeatureEntryCmp{
+export class FeatureEntryCmp implements OnDestroy{
 
   /**
    * in future, hopefully feature detail can be queried with just id,
@@ -31,6 +35,145 @@ export class FeatureEntryCmp{
   feature: SapiFeatureModel
 
   featureType = {
-    receptor: "siibra/features/receptor"
+    receptor: "siibra/features/receptor",
+    ieeg: CLEANED_IEEG_DATASET_TYPE
+  }
+
+  static readonly IEEG_ANNOTATION_LAYER_RED = `ieeg-annotation-layer-red`
+  static readonly IEEG_ANNOTATION_LAYER_WHITE = `ieeg-annotation-layer-white`
+  private ieegRedAnnLayer: AnnotationLayer
+  private ieegWhiteAnnLayer: AnnotationLayer
+  
+  ieegOnFocus(ev: IeegOnFocusEvent){
+    if (ev.contactPoint) {
+      /**
+       * navigate to the point
+       */
+      this.store.dispatch(
+        atlasSelection.actions.navigateTo({
+          navigation: {
+            position: ev.contactPoint.point.coordinates.map(v => v.value * 1e6)
+          },
+          animation: true
+        })
+      )
+      return
+    }
+    if (ev.session) {
+      /**
+       * 
+       */
+      if (!this.ieegRedAnnLayer) {
+        this.ieegRedAnnLayer = new AnnotationLayer(FeatureEntryCmp.IEEG_ANNOTATION_LAYER_RED, "#ff0000")
+      }
+      if (!this.ieegWhiteAnnLayer) {
+        this.ieegWhiteAnnLayer = new AnnotationLayer(FeatureEntryCmp.IEEG_ANNOTATION_LAYER_WHITE, "#ffffff")
+      }
+      const allInRoiPoints: TNgAnnotationPoint[] = this.getPointsFromSession(ev.session, true)
+      const allNonInRoiPoints: TNgAnnotationPoint[] = this.getPointsFromSession(ev.session, false)
+      for (const pt of allInRoiPoints) {
+        this.ieegRedAnnLayer.addAnnotation(pt)
+      }
+      for (const pt of allNonInRoiPoints) {
+        this.ieegWhiteAnnLayer.addAnnotation(pt)
+      }
+      this.store.dispatch(
+        annotation.actions.addAnnotations({
+          annotations: [...allInRoiPoints, ...allNonInRoiPoints].map(p => {
+            return { "@id": p.id }
+          })
+        })
+      )
+      this.store.dispatch(
+        atlasAppearance.actions.setOctantRemoval({
+          flag: false
+        })
+      )
+    }
+  }
+  ieegOnDefocus(ev: IeegOnDefocusEvent){
+    if (ev.session) {
+      const allInRoiPoints: TNgAnnotationPoint[] = this.getPointsFromSession(ev.session, true)
+      const allNonInRoiPoints: TNgAnnotationPoint[] = this.getPointsFromSession(ev.session, false)
+
+      this.store.dispatch(
+        annotation.actions.rmAnnotations({
+          annotations: [...allInRoiPoints, ...allNonInRoiPoints].map(p => {
+            return { "@id": p.id }
+          })
+        })
+      )
+
+      this.store.dispatch(
+        atlasAppearance.actions.setOctantRemoval({
+          flag: true
+        })
+      )
+
+      if (this.ieegRedAnnLayer) {
+        for (const pt of allInRoiPoints) {
+          this.ieegRedAnnLayer.removeAnnotation(pt)
+        }
+      }
+      
+      if (this.ieegWhiteAnnLayer) {
+        for (const pt of allNonInRoiPoints) {
+          this.ieegWhiteAnnLayer.removeAnnotation(pt)
+        }
+      }
+      
+
+    }
+  }
+  ngOnDestroy(): void {
+    if (this.ieegRedAnnLayer) this.ieegRedAnnLayer.dispose()
+    if (this.ieegWhiteAnnLayer) this.ieegWhiteAnnLayer.dispose()
+  }
+
+  constructor(
+    private store: Store
+  ){
+
+  }
+
+  private getPointsFromSession(session: Session<string>, inRoi: boolean):TNgAnnotationPoint[]{
+    const allPoints: TNgAnnotationPoint[] = []
+    for (const electrodeKey in session.electrodes) {
+      const electrode = session.electrodes[electrodeKey]
+      const points = this.getPointsFromElectrode(electrode, inRoi)
+      allPoints.push(...points)
+    }
+    return allPoints.map(pt => {
+      return {
+        ...pt,
+        id: `${session.sub_id}:${pt.id}`
+      }
+    })
+  }
+
+  private getPointsFromElectrode(electrode: Electrode<string>, inRoi: boolean): TNgAnnotationPoint[] {
+    const allPoints: TNgAnnotationPoint[] = []
+    for (const ctptKey in electrode.contact_points) {
+      const ctpt = electrode.contact_points[ctptKey]
+      if (!inRoi !== !ctpt.inRoi) {
+        continue
+      }
+      const point = this.getPointFromCtPt(ctpt)
+      allPoints.push(point)
+    }
+    return allPoints.map(pt => {
+      return {
+        ...pt,
+        id: `${electrode.electrode_id}:${pt.id}`
+      }
+    })
+  }
+
+  private getPointFromCtPt(ctpt: ContactPoint<string>): TNgAnnotationPoint {
+    return {
+      id: ctpt.id,
+      point: ctpt.point.coordinates.map(coord => coord.value * 1e6 ) as [number, number, number],
+      type: 'point'
+    }
   }
 }
diff --git a/src/atlasComponents/sapiViews/features/entry/entry.template.html b/src/atlasComponents/sapiViews/features/entry/entry.template.html
index 0affeaa6282725139eb7fd7af2258061ff7d1b44..38a00def6eba0d9546e5c729431e4d53a05292bb 100644
--- a/src/atlasComponents/sapiViews/features/entry/entry.template.html
+++ b/src/atlasComponents/sapiViews/features/entry/entry.template.html
@@ -1,9 +1,22 @@
-<div [ngSwitch]="feature?.type">
-  <sxplr-sapiviews-features-receptor-entry *ngSwitchCase="featureType.receptor"
+<div [ngSwitch]="feature?.['@type']">
+  <sxplr-sapiviews-features-receptor-entry
+    *ngSwitchCase="featureType.receptor"
     [sxplr-sapiviews-features-receptor-atlas]="atlas"
     [sxplr-sapiviews-features-receptor-parcellation]="parcellation"
     [sxplr-sapiviews-features-receptor-template]="space"
     [sxplr-sapiviews-features-receptor-region]="region"
     [sxplr-sapiviews-features-receptor-featureid]="feature['@id']">
   </sxplr-sapiviews-features-receptor-entry>
+  <sxplr-sapiviews-features-ieeg-ieegdataset
+    *ngSwitchCase="featureType.ieeg"  
+    [sxplr-sapiviews-features-ieeg-ieegdataset-atlas]="atlas"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-space]="space"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-parcellation]="parcellation"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-region]="region"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-feature]="feature"
+    (sxplr-sapiviews-features-ieeg-ieegdataset-on-focus)="ieegOnFocus($event)"
+    (sxplr-sapiviews-features-ieeg-ieegdataset-on-defocus)="ieegOnDefocus($event)"
+  >
+
+  </sxplr-sapiviews-features-ieeg-ieegdataset>
 </div>
diff --git a/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.component.ts b/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.component.ts
index d7fcb675825a2a3692e9acb8800f6181ff359627..6fb2e383091f37a59d814180e1fa208575b2af74 100644
--- a/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.component.ts
+++ b/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.component.ts
@@ -1,6 +1,6 @@
 import { Component, Input } from "@angular/core";
 import { SapiFeatureModel, SapiRegionalFeatureModel, SapiSpatialFeatureModel, SapiParcellationFeatureModel } from "src/atlasComponents/sapi";
-import { SapiDatasetModel, SapiParcellationFeatureMatrixModel, SapiRegionalFeatureReceptorModel, SapiSerializationErrorModel, SapiVOIDataResponse } from "src/atlasComponents/sapi/type";
+import { CleanedIeegDataset, CLEANED_IEEG_DATASET_TYPE, SapiDatasetModel, SapiParcellationFeatureMatrixModel, SapiRegionalFeatureReceptorModel, SapiSerializationErrorModel, SapiVOIDataResponse, SxplrCleanedFeatureModel } from "src/atlasComponents/sapi/type";
 
 @Component({
   selector: `sxplr-sapiviews-features-entry-list-item`,
@@ -12,23 +12,27 @@ import { SapiDatasetModel, SapiParcellationFeatureMatrixModel, SapiRegionalFeatu
 
 export class SapiViewsFeaturesEntryListItem{
   @Input('sxplr-sapiviews-features-entry-list-item-feature')
-  feature: SapiFeatureModel
+  feature: SapiFeatureModel | SxplrCleanedFeatureModel
 
   @Input('sxplr-sapiviews-features-entry-list-item-ripple')
   ripple = true
 
   get label(): string{
     if (!this.feature) return null
-    const { type } = this.feature
+    const { '@type': type } = this.feature
     if (
       type === "siibra/core/dataset" ||
       type === "siibra/features/receptor" ||
-      type === "siibra/features/voi"
+      type === "siibra/features/voi" ||
+      type === CLEANED_IEEG_DATASET_TYPE
     ) {
-      return (this.feature as (SapiDatasetModel | SapiRegionalFeatureReceptorModel | SapiVOIDataResponse) ).metadata.fullName
+      return (this.feature as (SapiDatasetModel | SapiRegionalFeatureReceptorModel | SapiVOIDataResponse | CleanedIeegDataset) ).metadata.fullName
     }
 
-    if (type === "siibra/features/connectivity") {
+    if (
+      type === "siibra/features/connectivity" ||
+      type === "siibra/features/connectivity/streamlineCounts"
+    ) {
       return (this.feature as SapiParcellationFeatureMatrixModel).name
     }
     if (type === "spy/serialization-error") {
diff --git a/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.template.html b/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.template.html
index 5bbc24ee23c600789b6c3000e4bcbe8d73a407e3..76f584328b3e46b5a240defb44e98e7cc2abe4a2 100644
--- a/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.template.html
+++ b/src/atlasComponents/sapiViews/features/entryListItem/entryListItem.template.html
@@ -1,8 +1,10 @@
 <div matRipple [matRippleDisabled]="!ripple"
   class="sxplr-p-2">
 
-  <mat-chip-list [ngSwitch]="feature.type" class="sxplr-scale-80 transform-origin-left-center">
-    <mat-chip *ngSwitchCase="'siibra/features/receptor'"
+  <mat-chip-list
+    *ngIf="feature | featureBadgeFlag"
+    class="sxplr-scale-80 transform-origin-left-center">
+    <mat-chip
       [color]="feature | featureBadgeColour"
       selected>
       {{ feature | featureBadgeName }}
diff --git a/src/atlasComponents/sapiViews/features/entryListItem/entryListitem.stories.ts b/src/atlasComponents/sapiViews/features/entryListItem/entryListitem.stories.ts
index 434fe9e1ec4fee2181e27077222441200d56dc3a..a93cd9816a00d9f29567b8a55ecfe481030e8c31 100644
--- a/src/atlasComponents/sapiViews/features/entryListItem/entryListitem.stories.ts
+++ b/src/atlasComponents/sapiViews/features/entryListItem/entryListitem.stories.ts
@@ -1,7 +1,7 @@
 import { CommonModule } from "@angular/common"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SapiFeatureModel } from "src/atlasComponents/sapi"
-import { getHoc1Features, getJba29Features, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1RightFeatures, getHoc1RightSpatialFeatures, getJba29Features, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { AngularMaterialModule } from "src/sharedModules"
 import { SapiViewsFeaturesEntryListItem } from "./entryListItem.component"
 import { Component, EventEmitter, Input, Output } from "@angular/core"
@@ -66,7 +66,10 @@ RegionalFeatures.args = {
 }
 RegionalFeatures.loaders = [
   async () => {
-    const features = await getHoc1Features()
+    const features = [
+      ...(await getHoc1RightSpatialFeatures()),
+      ...(await getHoc1RightFeatures())
+    ]
     return {
       features
     }
diff --git a/src/atlasComponents/sapiViews/features/featureBadgeColor.pipe.ts b/src/atlasComponents/sapiViews/features/featureBadgeColor.pipe.ts
index 4e7704c1afe9cf250cf0e8417a05ef0ecb2b8486..474d6a2adfe72257c35a406abde767ab7054f143 100644
--- a/src/atlasComponents/sapiViews/features/featureBadgeColor.pipe.ts
+++ b/src/atlasComponents/sapiViews/features/featureBadgeColor.pipe.ts
@@ -1,5 +1,5 @@
 import { Pipe, PipeTransform } from "@angular/core";
-import { SapiFeatureModel } from "src/atlasComponents/sapi";
+import { SapiFeatureModel, SxplrCleanedFeatureModel, CLEANED_IEEG_DATASET_TYPE } from "src/atlasComponents/sapi";
 
 @Pipe({
   name: 'featureBadgeColour',
@@ -7,10 +7,13 @@ import { SapiFeatureModel } from "src/atlasComponents/sapi";
 })
 
 export class FeatureBadgeColourPipe implements PipeTransform{
-  public transform(regionalFeature: SapiFeatureModel) {
-    if (regionalFeature.type === "siibra/features/receptor") {
+  public transform(regionalFeature: SapiFeatureModel|SxplrCleanedFeatureModel) {
+    if (regionalFeature['@type'] === "siibra/features/receptor") {
       return "accent"
     }
+    if (regionalFeature['@type'] === CLEANED_IEEG_DATASET_TYPE) {
+      return "primary"
+    }
     return "default"
   }
 }
diff --git a/src/atlasComponents/sapiViews/features/featureBadgeFlag.pipe.ts b/src/atlasComponents/sapiViews/features/featureBadgeFlag.pipe.ts
new file mode 100644
index 0000000000000000000000000000000000000000..986edffac941e522ee27d76dd3ab626aa40b993d
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/featureBadgeFlag.pipe.ts
@@ -0,0 +1,14 @@
+import { Pipe, PipeTransform } from "@angular/core";
+import { SapiFeatureModel, SxplrCleanedFeatureModel, CLEANED_IEEG_DATASET_TYPE } from "src/atlasComponents/sapi";
+
+@Pipe({
+  name: 'featureBadgeFlag',
+  pure: true
+})
+
+export class FeatureBadgeFlagPipe implements PipeTransform{
+  public transform(regionalFeature: SapiFeatureModel|SxplrCleanedFeatureModel) {
+    return regionalFeature['@type'] === "siibra/features/receptor"
+      || regionalFeature['@type'] === CLEANED_IEEG_DATASET_TYPE
+  }
+}
diff --git a/src/atlasComponents/sapiViews/features/featureBadgeName.pipe.ts b/src/atlasComponents/sapiViews/features/featureBadgeName.pipe.ts
index 8072a85081587b7847123fafdbedcb355b0efcca..33570440c6aa4c0f601d7171cac61cce7c42e712 100644
--- a/src/atlasComponents/sapiViews/features/featureBadgeName.pipe.ts
+++ b/src/atlasComponents/sapiViews/features/featureBadgeName.pipe.ts
@@ -1,5 +1,5 @@
 import { Pipe, PipeTransform } from "@angular/core";
-import { SapiFeatureModel } from "src/atlasComponents/sapi";
+import { SapiFeatureModel, SxplrCleanedFeatureModel, CLEANED_IEEG_DATASET_TYPE } from "src/atlasComponents/sapi";
 
 @Pipe({
   name: 'featureBadgeName',
@@ -7,10 +7,13 @@ import { SapiFeatureModel } from "src/atlasComponents/sapi";
 })
 
 export class FeatureBadgeNamePipe implements PipeTransform{
-  public transform(regionalFeature: SapiFeatureModel) {
-    if (regionalFeature.type === "siibra/features/receptor") {
+  public transform(regionalFeature: SapiFeatureModel|SxplrCleanedFeatureModel) {
+    if (regionalFeature['@type'] === "siibra/features/receptor") {
       return "receptor density"
     }
+    if (regionalFeature["@type"] === CLEANED_IEEG_DATASET_TYPE) {
+      return "IEEG dataset"
+    }
     return null
   }
 }
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.component.ts b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.component.ts
new file mode 100644
index 0000000000000000000000000000000000000000..de23194ff366b475d57954b3050aa2cf94cfb256
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.component.ts
@@ -0,0 +1,113 @@
+import { Component, EventEmitter, Input, OnChanges, OnDestroy, Output, SimpleChanges } from "@angular/core";
+import { BehaviorSubject, forkJoin } from "rxjs";
+import { SAPI } from "src/atlasComponents/sapi/sapi.service";
+import { CleanedIeegDataset, cleanIeegSessionDatasets, SapiAtlasModel, SapiIeegSessionModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi/type";
+
+export type Session<SId extends string> = CleanedIeegDataset['sessions'][SId]
+export type Electrode<EId extends string> = Session<string>['electrodes'][EId]
+export type ContactPoint<CId extends string> = Electrode<string>['contact_points'][CId]
+
+export type IeegOnFocusEvent = {
+  contactPoint: ContactPoint<string>
+  electrode: Electrode<string>
+  session: Session<string>
+}
+
+export type IeegOnDefocusEvent = {
+  contactPoint: ContactPoint<string>
+  electrode: Electrode<string>
+  session: Session<string>
+}
+
+@Component({
+  selector: `sxplr-sapiviews-features-ieeg-ieegdataset`,
+  templateUrl: `./ieegDataset.template.html`,
+  styleUrls: [
+    `./ieegDataset.style.css`
+  ]
+})
+
+export class IEEGDatasetCmp implements OnChanges{
+
+  @Input('sxplr-sapiviews-features-ieeg-ieegdataset-atlas')
+  public atlas: SapiAtlasModel
+  
+  @Input('sxplr-sapiviews-features-ieeg-ieegdataset-space')
+  public space: SapiSpaceModel
+
+  @Input('sxplr-sapiviews-features-ieeg-ieegdataset-parcellation')
+  public parcellation: SapiParcellationModel
+
+  @Input('sxplr-sapiviews-features-ieeg-ieegdataset-region')
+  public region: SapiRegionModel
+  
+  /**
+   * we must assume that the passed feature does not have the detail flag on
+   * We need to fetch the 
+   */
+  @Input('sxplr-sapiviews-features-ieeg-ieegdataset-feature')
+  public feature: CleanedIeegDataset
+  public detailedFeature: CleanedIeegDataset
+
+  @Output('sxplr-sapiviews-features-ieeg-ieegdataset-on-focus')
+  public onFocus = new EventEmitter<IeegOnFocusEvent>()
+
+  @Output('sxplr-sapiviews-features-ieeg-ieegdataset-on-defocus')
+  public onDefocus = new EventEmitter<IeegOnDefocusEvent>()
+  
+  public busy$ = new BehaviorSubject<boolean>(false)
+
+  ngOnChanges(changes: SimpleChanges): void {
+    if (!this.feature) {
+      return
+    }
+    if (this.feature && this.feature["@type"] !== "sxplr/cleanedIeegDataset") {
+      throw new Error(`expected @type to be sxplr-cleaned-ieeg-dataset, but is ${this.feature['@type']}.`)
+    }
+    this.busy$.next(true)
+    
+    forkJoin(
+      Object.entries(this.feature.sessions).map(([ key, session ]) => {
+        return this.sapi.getSpace(this.atlas["@id"], this.space["@id"]).getFeatureInstance(session["@id"], { parcellationId: this.parcellation["@id"], region: this.region.name })
+      })
+    ).subscribe(feats => {
+
+      const ieegSessions: SapiIeegSessionModel[] = feats.filter(feat => feat["@type"] === "siibra/features/ieegSession")
+      const features = cleanIeegSessionDatasets(ieegSessions)
+      const foundFeat = features.find(f => f["@id"] === this.feature["@id"])
+      if (foundFeat) {
+        this.detailedFeature = foundFeat
+      }
+      this.busy$.next(false)
+    })
+  }
+
+  public onContactPointClicked(cpt: ContactPoint<string>, ele: Electrode<string>, sess: Session<string>){
+    this.onFocus.emit({
+      contactPoint: cpt,
+      electrode: ele,
+      session: sess
+    })
+  }
+
+  public onPanelOpen(session: Session<string>){
+    this.onFocus.emit({
+      contactPoint: null,
+      electrode: null,
+      session: session
+    })
+  }
+
+  public onPanelClose(session: Session<string>){
+    this.onDefocus.emit({
+      contactPoint: null,
+      electrode: null,
+      session: session
+    })
+  }
+
+  constructor(private sapi: SAPI){
+
+  }
+
+}
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.stories.ts b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.stories.ts
new file mode 100644
index 0000000000000000000000000000000000000000..c9f08880e4525ab8c2d9f550abee83bf60c876fc
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.stories.ts
@@ -0,0 +1,113 @@
+import { Meta, moduleMetadata, Story } from "@storybook/angular"
+import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi"
+import { getHoc1Right, getHumanAtlas, getJba29, getMni152, provideDarkTheme, getMni152SpatialFeatureHoc1Right } from "src/atlasComponents/sapi/stories.base"
+import { SxplrSapiViewsFeaturesIeegModule } from ".."
+import { Component } from "@angular/core"
+import { cleanIeegSessionDatasets, SapiSpatialFeatureModel } from "src/atlasComponents/sapi/type"
+import { action } from "@storybook/addon-actions"
+
+@Component({
+  selector: 'ieeg-entry-wrapper-cmp',
+  template: `
+  <sxplr-sapiviews-features-ieeg-ieegdataset
+    [sxplr-sapiviews-features-ieeg-ieegdataset-atlas]="atlas"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-space]="template"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-parcellation]="parcellation"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-region]="region"
+    [sxplr-sapiviews-features-ieeg-ieegdataset-feature]="feature"
+    (sxplr-sapiviews-features-ieeg-ieegdataset-on-focus)="handleCtptClick($event)"
+    (sxplr-sapiviews-features-ieeg-ieegdataset-on-defocus)="handleOnDeFocus($event)"
+  >
+  </sxplr-sapiviews-features-ieeg-ieegdataset>
+  `,
+  styles: [
+    `
+    :host
+    {
+      display: block;
+      width: 20rem;
+    }
+    `
+  ]
+})
+class EntryWrappercls {
+  atlas: SapiAtlasModel
+  template: SapiSpaceModel
+  feature: SapiSpatialFeatureModel
+  parcellation: SapiParcellationModel
+  region: SapiRegionModel
+
+  handleOnFocus(cpt: unknown){}
+  handleOnDeFocus(cpt: unknown) {}
+}
+
+export default {
+  component: EntryWrappercls,
+  decorators: [
+    moduleMetadata({
+      imports: [
+        SxplrSapiViewsFeaturesIeegModule,
+      ],
+      providers: [
+        SAPI,
+        ...provideDarkTheme,
+      ],
+      declarations: [
+        EntryWrappercls
+      ]
+    })
+  ],
+} as Meta
+
+const Template: Story<EntryWrappercls> = (args: EntryWrappercls, { loaded }) => {
+  const { atlas, parc, space, region, feature } = loaded
+  return ({
+    props: {
+      ...args,
+      atlas: atlas,
+      parcellation: parc,
+      template: space,
+      region: region,
+      feature,
+      handleOnFocus: action('handleOnFocus'),
+      handleOnDeFocus: action('handleOnDeFocus')
+    },
+  })
+}
+
+const loadFeat = async () => {
+  const atlas = await getHumanAtlas()
+  const space = await getMni152()
+  const parc = await getJba29()
+  const region = await getHoc1Right()
+  
+  const features = await getMni152SpatialFeatureHoc1Right()
+  const spatialFeats = features.filter(f => f["@type"] === "siibra/features/ieegSession")
+  const feature = cleanIeegSessionDatasets(spatialFeats)[0]
+  return {
+    atlas,
+    space,
+    parc,
+    region,
+    feature
+  }
+}
+
+export const Default = Template.bind({})
+Default.args = {
+
+}
+Default.loaders = [
+  async () => {
+    const {
+      atlas,
+      space,
+      feature,
+      parc,
+      region,
+    } = await loadFeat()
+    return {
+      atlas, space, feature, parc, region  
+    }
+  }
+]
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.style.css b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.style.css
new file mode 100644
index 0000000000000000000000000000000000000000..1c554eef70e8adae01cba4530c534a389ce6c93a
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.style.css
@@ -0,0 +1,4 @@
+mat-form-field
+{
+  width: 100%;
+}
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.template.html b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.template.html
new file mode 100644
index 0000000000000000000000000000000000000000..af7464f5e24b254d42985ef55766f755696c4909
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/ieeg/ieegDataset/ieegDataset.template.html
@@ -0,0 +1,112 @@
+<spinner-cmp *ngIf="busy$ | async; else resultTmpl">
+</spinner-cmp>
+
+<ng-template #resultTmpl>
+
+  <mat-accordion *ngIf="!!detailedFeature">
+    <ng-template
+      ngFor
+      [ngForOf]="detailedFeature.sessions | keyvalue"
+      let-sessionKeyVal>
+  
+      <ng-template
+        [ngIf]="sessionKeyVal.value.inRoi"
+        [ngTemplateOutlet]="sessionTmpl"
+        [ngTemplateOutletContext]="{
+          $implicit: sessionKeyVal.value
+        }">
+  
+      </ng-template>
+  
+    </ng-template>
+  </mat-accordion>
+  
+</ng-template>
+
+<!-- session template -->
+<ng-template #sessionTmpl let-session>
+  <mat-expansion-panel
+    (opened)="onPanelOpen(session)"
+    (closed)="onPanelClose(session)">
+    <mat-expansion-panel-header>
+      SessionID: {{ session.sub_id }}
+    </mat-expansion-panel-header>
+
+    <ng-template matExpansionPanelContent>
+      <ng-template
+        ngFor
+        [ngForOf]="session.electrodes | keyvalue | inRoi"
+        let-electrodeKeyVal>
+        <ng-template
+          [ngTemplateOutlet]="electrodeTmpl"
+          [ngTemplateOutletContext]="{
+            electrode: electrodeKeyVal.value,
+            session: session
+          }">
+
+        </ng-template>
+      </ng-template>
+
+      <mat-divider></mat-divider>
+      <ng-template
+        ngFor
+        [ngForOf]="session.electrodes | keyvalue | inRoi : false"
+        let-electrodeKeyVal>
+        <div class="sxplr-very-muted">
+          <ng-template
+            [ngTemplateOutlet]="electrodeTmpl"
+            [ngTemplateOutletContext]="{
+              electrode: electrodeKeyVal.value,
+              session: session
+            }">
+
+          </ng-template>
+        </div>
+      </ng-template>
+    </ng-template>
+  </mat-expansion-panel>
+</ng-template>
+
+<!-- electrode template -->
+<ng-template
+  #electrodeTmpl
+  let-electrode="electrode"
+  let-session="session">
+  <mat-form-field appearance="fill">
+    <mat-label>
+      ElectrodeID: {{ electrode.electrode_id }}
+    </mat-label>
+    <mat-chip-list>
+      <ng-template
+        ngFor
+        [ngForOf]="electrode.contact_points | keyvalue"
+        let-contactPointKeyVal>
+
+        <ng-template
+          [ngTemplateOutlet]="contactPointTmpl"
+          [ngTemplateOutletContext]="{
+            contactPointKey: contactPointKeyVal.key,
+            contactPoint: contactPointKeyVal.value,
+            electrode: electrode,
+            session: session
+          }">
+        </ng-template>
+      </ng-template>
+    </mat-chip-list>
+  </mat-form-field>
+</ng-template>
+
+<!-- contact point template -->
+<ng-template
+  #contactPointTmpl
+  let-contactPoint="contactPoint"
+  let-key="contactPointKey"
+  let-electrode="electrode"
+  let-session="session">
+  <mat-chip
+    (click)="onContactPointClicked(contactPoint, electrode, session)"
+    [color]="contactPoint.inRoi ? 'primary' : 'default'"
+    selected>
+    {{ key }}
+  </mat-chip>
+</ng-template>
\ No newline at end of file
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.component.ts b/src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.component.ts
deleted file mode 100644
index 9725ac61ea28969bf932c600e7b82521b9b0ab5f..0000000000000000000000000000000000000000
--- a/src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.component.ts
+++ /dev/null
@@ -1,26 +0,0 @@
-import { Component } from "@angular/core";
-
-type Landmark = {} & {
-  showInSliceView
-}
-
-@Component({
-  templateUrl: `./ieegSession.template.html`,
-  styleUrls: [
-    `./ieegSession.style.css`
-  ]
-})
-
-export class IEEGSessionCmp{
-  private loadedLms: Landmark[]
-
-  private unloadLandmarks(){}
-  private loadlandmarks(lms: Landmark[]){}
-  private handleDatumExpansion(dataset: any){
-
-  }
-  private handleContactPtClick(contactPt){
-    // navigate there
-
-  }
-}
\ No newline at end of file
diff --git a/src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.template.html b/src/atlasComponents/sapiViews/features/ieeg/ieegSession/ieegSession.template.html
deleted file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..0000000000000000000000000000000000000000
diff --git a/src/atlasComponents/sapiViews/features/ieeg/inRoi.pipe.ts b/src/atlasComponents/sapiViews/features/ieeg/inRoi.pipe.ts
new file mode 100644
index 0000000000000000000000000000000000000000..4f215c8ccd96ff7af503abc521e3c6558383c234
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/ieeg/inRoi.pipe.ts
@@ -0,0 +1,19 @@
+import { Pipe, PipeTransform } from "@angular/core";
+
+interface InRoi {
+  key: string
+  value: {
+    inRoi: boolean
+  }
+}
+
+@Pipe({
+  name: 'inRoi',
+  pure: true
+})
+
+export class InRoiPipe implements PipeTransform{
+  public transform(list: InRoi[], inroi=true): InRoi[] {
+    return list.filter(it => it.value.inRoi === inroi)
+  }
+}
diff --git a/src/atlasComponents/sapiViews/features/ieeg/index.ts b/src/atlasComponents/sapiViews/features/ieeg/index.ts
index 663fabd8603621b891428afeb0d68e861690cfd4..757808e777ca4f96b83bba521ab6c71d3903cfaa 100644
--- a/src/atlasComponents/sapiViews/features/ieeg/index.ts
+++ b/src/atlasComponents/sapiViews/features/ieeg/index.ts
@@ -1 +1,2 @@
-export { IEEGSessionCmp } from "./ieegSession/ieegSession.component"
\ No newline at end of file
+export { IEEGDatasetCmp, IeegOnFocusEvent, IeegOnDefocusEvent, ContactPoint, Electrode, Session } from "./ieegDataset/ieegDataset.component"
+export { SxplrSapiViewsFeaturesIeegModule } from "./module"
\ No newline at end of file
diff --git a/src/atlasComponents/sapiViews/features/ieeg/module.ts b/src/atlasComponents/sapiViews/features/ieeg/module.ts
new file mode 100644
index 0000000000000000000000000000000000000000..c91161eac8e261121aaa58e583265961b324c007
--- /dev/null
+++ b/src/atlasComponents/sapiViews/features/ieeg/module.ts
@@ -0,0 +1,33 @@
+import { CommonModule } from "@angular/common";
+import { NgModule } from "@angular/core";
+import { MatChipsModule } from "@angular/material/chips";
+import { MatDividerModule } from "@angular/material/divider";
+import { MatExpansionModule } from "@angular/material/expansion";
+import { MatFormFieldModule } from "@angular/material/form-field";
+import { BrowserAnimationsModule } from "@angular/platform-browser/animations";
+import { SAPIModule } from "src/atlasComponents/sapi/module";
+import { SpinnerModule } from "src/components/spinner";
+import { IEEGDatasetCmp } from "./ieegDataset/ieegDataset.component";
+import { InRoiPipe } from "./inRoi.pipe";
+
+@NgModule({
+  imports: [
+    CommonModule,
+    MatExpansionModule,
+    MatChipsModule,
+    MatFormFieldModule,
+    MatDividerModule,
+    BrowserAnimationsModule,
+    SpinnerModule,
+    SAPIModule,
+  ],
+  declarations: [
+    IEEGDatasetCmp,
+    InRoiPipe,
+  ],
+  exports: [
+    IEEGDatasetCmp,
+  ]
+})
+
+export class SxplrSapiViewsFeaturesIeegModule{}
\ No newline at end of file
diff --git a/src/atlasComponents/sapiViews/features/module.ts b/src/atlasComponents/sapiViews/features/module.ts
index 654d96c9ca9143516658b3505c9916a83df26858..6ee7b852c0400d3bb9b6af371f8f930c4bfb2ceb 100644
--- a/src/atlasComponents/sapiViews/features/module.ts
+++ b/src/atlasComponents/sapiViews/features/module.ts
@@ -5,12 +5,13 @@ import { appendScriptFactory, APPEND_SCRIPT_TOKEN } from "src/util/constants"
 import { FeatureEntryCmp } from "./entry/entry.component"
 import { SapiViewsFeaturesEntryListItem } from "./entryListItem/entryListItem.component"
 import { FeatureBadgeColourPipe } from "./featureBadgeColor.pipe"
+import { FeatureBadgeFlagPipe } from "./featureBadgeFlag.pipe"
 import { FeatureBadgeNamePipe } from "./featureBadgeName.pipe"
 import * as ieeg from "./ieeg"
 import * as receptor from "./receptors"
 
 const {
-  IEEGSessionCmp
+  SxplrSapiViewsFeaturesIeegModule
 } = ieeg
 const {
   ReceptorViewModule
@@ -20,13 +21,14 @@ const {
   imports: [
     CommonModule,
     ReceptorViewModule,
+    SxplrSapiViewsFeaturesIeegModule,
     AngularMaterialModule,
   ],
   declarations: [
-    IEEGSessionCmp,
     FeatureEntryCmp,
     FeatureBadgeNamePipe,
     FeatureBadgeColourPipe,
+    FeatureBadgeFlagPipe,
     SapiViewsFeaturesEntryListItem,
   ],
   providers: [
@@ -37,7 +39,6 @@ const {
     }
   ],
   exports: [
-    IEEGSessionCmp,
     FeatureEntryCmp,
     SapiViewsFeaturesEntryListItem,
   ]
diff --git a/src/atlasComponents/sapiViews/features/receptors/autoradiography/autoradiograph.stories.ts b/src/atlasComponents/sapiViews/features/receptors/autoradiography/autoradiograph.stories.ts
index 5ebfdce9870f959574846ebd56383535d376fd4b..093ec6a110eaca060b0bf3e48204026ee5ed1946 100644
--- a/src/atlasComponents/sapiViews/features/receptors/autoradiography/autoradiograph.stories.ts
+++ b/src/atlasComponents/sapiViews/features/receptors/autoradiography/autoradiograph.stories.ts
@@ -5,7 +5,7 @@ import { FormsModule } from "@angular/forms"
 import { BrowserAnimationsModule } from "@angular/platform-browser/animations"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi"
-import { getHoc1FeatureDetail, getHoc1Features, getHoc1Left, getHumanAtlas, getJba29, getMni152 } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1RightFeatureDetail, getHoc1RightFeatures, getHoc1Right, getHumanAtlas, getJba29, getMni152 } from "src/atlasComponents/sapi/stories.base"
 import { SapiRegionalFeatureReceptorModel } from "src/atlasComponents/sapi/type"
 import { AngularMaterialModule } from "src/sharedModules"
 import { Autoradiography } from "./autoradiography.component"
@@ -106,11 +106,11 @@ const Template: Story<AutoRadiographWrapperCls> = (args: AutoRadiographWrapperCl
 const loadFeat = async () => {
   const atlas = await getHumanAtlas()
   const parc = await getJba29()
-  const region = await getHoc1Left()
+  const region = await getHoc1Right()
   const space = await getMni152()
-  const features = await getHoc1Features()
-  const receptorfeat = features.find(f => f.type === "siibra/features/receptor")
-  const feature = await getHoc1FeatureDetail(receptorfeat["@id"])
+  const features = await getHoc1RightFeatures()
+  const receptorfeat = features.find(f => f['@type'] === "siibra/features/receptor")
+  const feature = await getHoc1RightFeatureDetail(receptorfeat["@id"])
   return {
     atlas,
     parc,
diff --git a/src/atlasComponents/sapiViews/features/receptors/base.ts b/src/atlasComponents/sapiViews/features/receptors/base.ts
index b393969c20c50862e35eabe9b8efe49738bc57eb..cbcd75fc2460c847e907d4c312eb0eb9ea19b081 100644
--- a/src/atlasComponents/sapiViews/features/receptors/base.ts
+++ b/src/atlasComponents/sapiViews/features/receptors/base.ts
@@ -74,9 +74,9 @@ export abstract class BaseReceptor{
       this.error = `featureId needs to be defined, but is not`
       return
     }
-    const result = await this.sapi.getRegion(this.atlas["@id"], this.parcellation["@id"], this.region.name).getFeatureInstance(this.featureId, this.template["@id"])
-    if (result.type !== "siibra/features/receptor") {
-      throw new Error(`BaseReceptor Error. Expected .type to be "siibra/features/receptor", but was "${result.type}"`)
+    const result = await this.sapi.getRegion(this.atlas["@id"], this.parcellation["@id"], this.region.name).getFeatureInstance(this.featureId, this.template["@id"]).toPromise()
+    if (result["@type"] !== "siibra/features/receptor") {
+      throw new Error(`BaseReceptor Error. Expected .type to be "siibra/features/receptor", but was "${result['@type']}"`)
     }
     return result
   }
diff --git a/src/atlasComponents/sapiViews/features/receptors/entry/entry.stories.ts b/src/atlasComponents/sapiViews/features/receptors/entry/entry.stories.ts
index 0c69f821626c7590721e6e91054d4e39633ea633..63f07ee1ef4f6dd57c402e07d08a4e9c5d742f01 100644
--- a/src/atlasComponents/sapiViews/features/receptors/entry/entry.stories.ts
+++ b/src/atlasComponents/sapiViews/features/receptors/entry/entry.stories.ts
@@ -1,10 +1,8 @@
 import { CommonModule, DOCUMENT } from "@angular/common"
 import { HttpClientModule } from "@angular/common/http"
-import { FormsModule } from "@angular/forms"
-import { BrowserAnimationsModule } from "@angular/platform-browser/animations"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi"
-import { getHoc1FeatureDetail, getHoc1Features, getHoc1Left, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1RightFeatureDetail, getHoc1RightFeatures, getHoc1Right, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { AngularMaterialModule } from "src/sharedModules"
 import { Entry } from "./entry.component"
 import { ReceptorViewModule } from ".."
@@ -89,11 +87,11 @@ const Template: Story<Entry> = (args: Entry, { loaded }) => {
 const loadFeat = async () => {
   const atlas = await getHumanAtlas()
   const parc = await getJba29()
-  const region = await getHoc1Left()
+  const region = await getHoc1Right()
   const space = await getMni152()
-  const features = await getHoc1Features()
-  const receptorfeat = features.find(f => f.type === "siibra/features/receptor")
-  const feature = await getHoc1FeatureDetail(receptorfeat["@id"])
+  const features = await getHoc1RightFeatures()
+  const receptorfeat = features.find(f => f['@type'] === "siibra/features/receptor")
+  const feature = await getHoc1RightFeatureDetail(receptorfeat["@id"])
   return {
     atlas,
     parc,
diff --git a/src/atlasComponents/sapiViews/features/receptors/fingerprint/fingerprint.stories.ts b/src/atlasComponents/sapiViews/features/receptors/fingerprint/fingerprint.stories.ts
index 7c5da4f82f24a859db259439ce6fef8ec71e29c3..1c3327ac1470cc2a7d650aa3b5196f70958dbbe2 100644
--- a/src/atlasComponents/sapiViews/features/receptors/fingerprint/fingerprint.stories.ts
+++ b/src/atlasComponents/sapiViews/features/receptors/fingerprint/fingerprint.stories.ts
@@ -3,7 +3,7 @@ import { HttpClientModule } from "@angular/common/http"
 import { Component, EventEmitter, Output } from "@angular/core"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi"
-import { getHoc1FeatureDetail, getHoc1Features, getHoc1Left, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1RightFeatureDetail, getHoc1RightFeatures, getHoc1Right, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { SapiRegionalFeatureReceptorModel } from "src/atlasComponents/sapi/type"
 import { AngularMaterialModule } from "src/sharedModules"
 import { appendScriptFactory, APPEND_SCRIPT_TOKEN } from "src/util/constants"
@@ -88,11 +88,11 @@ const Template: Story<FingerprintWrapperCls> = (args: FingerprintWrapperCls, { l
 const loadFeat = async () => {
   const atlas = await getHumanAtlas()
   const parc = await getJba29()
-  const region = await getHoc1Left()
+  const region = await getHoc1Right()
   const space = await getMni152()
-  const features = await getHoc1Features()
-  const receptorfeat = features.find(f => f.type === "siibra/features/receptor")
-  const feature = await getHoc1FeatureDetail(receptorfeat["@id"])
+  const features = await getHoc1RightFeatures()
+  const receptorfeat = features.find(f => f['@type'] === "siibra/features/receptor")
+  const feature = await getHoc1RightFeatureDetail(receptorfeat["@id"])
   return {
     atlas,
     parc,
diff --git a/src/atlasComponents/sapiViews/features/receptors/profile/profile.stories.ts b/src/atlasComponents/sapiViews/features/receptors/profile/profile.stories.ts
index f4dc8b4bdaadb96aff3ca76ad0f69450c7a0aeef..83d309f52d008d14183329f0539cf179c0354867 100644
--- a/src/atlasComponents/sapiViews/features/receptors/profile/profile.stories.ts
+++ b/src/atlasComponents/sapiViews/features/receptors/profile/profile.stories.ts
@@ -6,7 +6,7 @@ import { BrowserAnimationsModule } from "@angular/platform-browser/animations"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { BehaviorSubject, Subject } from "rxjs"
 import { SAPI, SapiAtlasModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi"
-import { addAddonEventListener, getHoc1FeatureDetail, getHoc1Features, getHoc1Left, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { addAddonEventListener, getHoc1RightFeatureDetail, getHoc1RightFeatures, getHoc1Right, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
 import { SapiRegionalFeatureReceptorModel } from "src/atlasComponents/sapi/type"
 import { AngularMaterialModule } from "src/sharedModules"
 import { appendScriptFactory, APPEND_SCRIPT_TOKEN } from "src/util/constants"
@@ -115,11 +115,11 @@ const Template: Story<ProfileWrapperCls> = (args: ProfileWrapperCls, { loaded })
 const loadFeat = async () => {
   const atlas = await getHumanAtlas()
   const parc = await getJba29()
-  const region = await getHoc1Left()
+  const region = await getHoc1Right()
   const space = await getMni152()
-  const features = await getHoc1Features()
-  const receptorfeat = features.find(f => f.type === "siibra/features/receptor")
-  const feature = await getHoc1FeatureDetail(receptorfeat["@id"])
+  const features = await getHoc1RightFeatures()
+  const receptorfeat = features.find(f => f['@type'] === "siibra/features/receptor")
+  const feature = await getHoc1RightFeatureDetail(receptorfeat["@id"])
   return {
     atlas,
     parc,
diff --git a/src/atlasComponents/sapiViews/richDataset.stories.ts b/src/atlasComponents/sapiViews/richDataset.stories.ts
index c49035dbe93ff1d54764413660bea9afd4bbef9e..4904bf1d163283ab146de866abd5274bd2a19c29 100644
--- a/src/atlasComponents/sapiViews/richDataset.stories.ts
+++ b/src/atlasComponents/sapiViews/richDataset.stories.ts
@@ -3,9 +3,9 @@ import { HttpClientModule } from "@angular/common/http"
 import { Component } from "@angular/core"
 import { Meta, moduleMetadata, Story } from "@storybook/angular"
 import { SAPI } from "src/atlasComponents/sapi"
-import { getHoc1FeatureDetail, getHoc1Features, getHoc1Left, getHumanAtlas, getJba29, getMni152, provideDarkTheme } from "src/atlasComponents/sapi/stories.base"
+import { getHoc1RightFeatureDetail, getHoc1RightFeatures, getHoc1Right, getHumanAtlas, getJba29, getMni152, provideDarkTheme, getMni152SpatialFeatureHoc1Right } from "src/atlasComponents/sapi/stories.base"
 import { AngularMaterialModule } from "src/sharedModules"
-import { SapiAtlasModel, SapiFeatureModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "../sapi/type"
+import { cleanIeegSessionDatasets, SapiAtlasModel, SapiFeatureModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "../sapi/type"
 import { SapiViewsCoreDatasetModule } from "./core/datasets"
 import { SapiViewsFeaturesModule } from "./features"
 
@@ -88,7 +88,7 @@ const loadRegionMetadata = async () => {
   const atlas = await getHumanAtlas()
   const parcellation = await getJba29()
   const template = await getMni152()
-  const region = await getHoc1Left()
+  const region = await getHoc1Right()
   return {
     atlas, 
     parcellation, 
@@ -98,7 +98,7 @@ const loadRegionMetadata = async () => {
 }
 
 const loadFeat = async () => {
-  const features = await getHoc1Features()
+  const features = await getHoc1RightFeatures()
   return { features }
 }
 
@@ -112,10 +112,25 @@ ReceptorDataset.loaders = [
   },
   async () => {
     const { features } = await loadFeat()
-    const receptorfeat = features.find(f => f.type === "siibra/features/receptor")
-    const feature = await getHoc1FeatureDetail(receptorfeat["@id"])
-    return {
-      feature
-    }
+    const receptorfeat = features.find(f => f['@type'] === "siibra/features/receptor")
+    const feature = await getHoc1RightFeatureDetail(receptorfeat["@id"])
+    return { feature }
+  }
+]
+
+export const IeegDataset = Template.bind({})
+IeegDataset.args = {
+
+}
+IeegDataset.loaders = [
+  async () => {
+    return await loadRegionMetadata()
+  },
+  async () => {
+    const features = await getMni152SpatialFeatureHoc1Right()
+    const spatialFeats = features.filter(f => f["@type"] === "siibra/features/ieegSession")
+    const feature = cleanIeegSessionDatasets(spatialFeats)[0]
+    
+    return { feature }
   }
 ]
diff --git a/src/atlasComponents/splashScreen/index.ts b/src/atlasComponents/splashScreen/index.ts
deleted file mode 100644
index 0750a03038aaecc1a9de8097d87ecd240121e418..0000000000000000000000000000000000000000
--- a/src/atlasComponents/splashScreen/index.ts
+++ /dev/null
@@ -1,2 +0,0 @@
-export { SplashScreen } from "./splashScreen/splashScreen.component";
-export { SplashUiModule } from './module'
\ No newline at end of file
diff --git a/src/atlasComponents/splashScreen/module.ts b/src/atlasComponents/splashScreen/module.ts
deleted file mode 100644
index 587e1217dad6d50acbe9f78b7f9074b3c0e844c8..0000000000000000000000000000000000000000
--- a/src/atlasComponents/splashScreen/module.ts
+++ /dev/null
@@ -1,25 +0,0 @@
-import { CommonModule } from "@angular/common";
-import { NgModule } from "@angular/core";
-import { ComponentsModule } from "src/components";
-import { KgTosModule } from "src/ui/kgtos/module";
-import { AngularMaterialModule } from "src/sharedModules";
-import { UtilModule } from "src/util";
-import { SplashScreen } from "./splashScreen/splashScreen.component";
-
-@NgModule({
-  imports: [
-    AngularMaterialModule,
-    CommonModule,
-    UtilModule,
-    KgTosModule,
-    ComponentsModule,
-  ],
-  declarations: [
-    SplashScreen,
-  ],
-  exports: [
-    SplashScreen,
-  ]
-})
-
-export class SplashUiModule{}
\ No newline at end of file
diff --git a/src/atlasComponents/userAnnotations/tools/service.ts b/src/atlasComponents/userAnnotations/tools/service.ts
index 546cd1238464c9830f8778d91bc38d1810c9c62c..1381520da9c9a7fae35e5203c9e40a5790c7aa07 100644
--- a/src/atlasComponents/userAnnotations/tools/service.ts
+++ b/src/atlasComponents/userAnnotations/tools/service.ts
@@ -16,6 +16,8 @@ import { retry } from 'common/util'
 import { MatSnackBar } from "@angular/material/snack-bar";
 import { actions } from "src/state/atlasSelection";
 import { atlasSelection } from "src/state";
+import { SapiSpaceModel } from "src/atlasComponents/sapi";
+import { AnnotationLayer } from "src/atlasComponents/annotations";
 
 const LOCAL_STORAGE_KEY = 'userAnnotationKey'
 
@@ -85,11 +87,11 @@ export class ModularUserAnnotationToolService implements OnDestroy{
 
   private previewNgAnnIds: string[] = []
 
-  private ngAnnotationLayer: any
+  private annotationLayer: AnnotationLayer
   private activeToolName: string
   private forcedAnnotationRefresh$ = new BehaviorSubject(null)
 
-  private selectedTmpl: any
+  private selectedTmpl: SapiSpaceModel
   private selectedTmpl$ = this.store.pipe(
     select(atlasSelection.selectors.selectedTemplate),
   )
@@ -321,7 +323,7 @@ export class ModularUserAnnotationToolService implements OnDestroy{
      */
     this.subscription.push(
       nehubaViewer$.subscribe(() => {
-        this.ngAnnotationLayer = null
+        this.annotationLayer = null
       })
     )
 
@@ -411,23 +413,12 @@ export class ModularUserAnnotationToolService implements OnDestroy{
           this.clearAllPreviewAnnotations()
         }
         for (let idx = 0; idx < previewNgAnnotation.length; idx ++) {
-          const localAnnotations = this.ngAnnotationLayer.layer.localAnnotations
-          const annSpec = {
-            ...parseNgAnnotation(previewNgAnnotation[idx]),
+          const spec = {
+            ...previewNgAnnotation[idx],
             id: `${ModularUserAnnotationToolService.TMP_PREVIEW_ANN_ID}_${idx}`
           }
-          const annRef = localAnnotations.references.get(annSpec.id)
-          if (annRef) {
-            localAnnotations.update(
-              annRef,
-              annSpec
-            )
-          } else {
-            localAnnotations.add(
-              annSpec
-            )
-          }
-          this.previewNgAnnIds[idx] = annSpec.id
+          this.annotationLayer.updateAnnotation(spec)
+          this.previewNgAnnIds[idx] = spec.id
         }
       })
     )
@@ -439,7 +430,7 @@ export class ModularUserAnnotationToolService implements OnDestroy{
       this.forcedAnnotationRefresh$,
       this.spaceFilteredManagedAnnotations$.pipe(
         switchMap(switchMapWaitFor({
-          condition: () => !!this.ngAnnotationLayer,
+          condition: () => !!this.annotationLayer,
           leading: true
         })),
       )
@@ -479,20 +470,8 @@ export class ModularUserAnnotationToolService implements OnDestroy{
             this.deleteNgAnnotationById(annotation.id)
             continue
           }
-          if (!this.ngAnnotationLayer) continue
-          const localAnnotations = this.ngAnnotationLayer.layer.localAnnotations
-          const annRef = localAnnotations.references.get(annotation.id)
-          const annSpec = parseNgAnnotation(annotation)
-          if (annRef) {
-            localAnnotations.update(
-              annRef,
-              annSpec
-            )
-          } else {
-            localAnnotations.add(
-              annSpec
-            )
-          }
+          if (!this.annotationLayer) continue
+          this.annotationLayer.updateAnnotation(annotation)
         }
       })
     )
@@ -506,26 +485,18 @@ export class ModularUserAnnotationToolService implements OnDestroy{
       ).subscribe(viewerMode => {
         this.currMode = viewerMode
         if (viewerMode === ModularUserAnnotationToolService.VIEWER_MODE) {
-          if (this.ngAnnotationLayer) this.ngAnnotationLayer.setVisible(true)
+          if (this.annotationLayer) this.annotationLayer.setVisible(true)
           else {
             const viewer = (window as any).viewer
-            const voxelSize = IAV_VOXEL_SIZES_NM[this.selectedTmpl.fullId]
-            if (!voxelSize) throw new Error(`voxelSize of ${this.selectedTmpl.fullId} cannot be found!`)
-            const layer = viewer.layerSpecification.getLayer(
+            const voxelSize = IAV_VOXEL_SIZES_NM[this.selectedTmpl["@id"]]
+            if (!voxelSize) throw new Error(`voxelSize of ${this.selectedTmpl["@id"]} cannot be found!`)
+            if (this.annotationLayer) {
+              this.annotationLayer.dispose()
+            }
+            this.annotationLayer = new AnnotationLayer(
               ModularUserAnnotationToolService.ANNOTATION_LAYER_NAME,
-              {
-                ...ModularUserAnnotationToolService.USER_ANNOTATION_LAYER_SPEC,
-                // since voxel coordinates are no longer defined, so voxel size will always be 1/1/1
-                transform: [
-                  [1, 0, 0, 0],
-                  [0, 1, 0, 0],
-                  [0, 0, 1, 0],
-                  [0, 0, 0, 1],
-                ]
-              }
+              ModularUserAnnotationToolService.USER_ANNOTATION_LAYER_SPEC.annotationColor
             )
-            this.ngAnnotationLayer = viewer.layerManager.addManagedLayer(layer)
-
             /**
              * on template changes, the layer gets lost
              * force redraw annotations if layer needs to be recreated
@@ -533,7 +504,7 @@ export class ModularUserAnnotationToolService implements OnDestroy{
             this.forcedAnnotationRefresh$.next(null)
           }
         } else {
-          if (this.ngAnnotationLayer) this.ngAnnotationLayer.setVisible(false)
+          if (this.annotationLayer) this.annotationLayer.setVisible(false)
         }
       })
     )
@@ -667,12 +638,7 @@ export class ModularUserAnnotationToolService implements OnDestroy{
   }
 
   private deleteNgAnnotationById(annId: string) {
-    const localAnnotations = this.ngAnnotationLayer.layer.localAnnotations
-    const annRef = localAnnotations.references.get(annId)
-    if (annRef) {
-      localAnnotations.delete(annRef)
-      localAnnotations.references.delete(annId)
-    }
+    this.annotationLayer.removeAnnotation({ id: annId })
   }
 
   public defaultTool: AbsToolClass<any>
@@ -750,7 +716,7 @@ export class ModularUserAnnotationToolService implements OnDestroy{
   private currMode: string
   switchAnnotationMode(mode: 'on' | 'off' | 'toggle' = 'toggle') {
 
-    let payload = null
+    let payload: 'annotating' = null
     if (mode === 'on') payload = ARIA_LABELS.VIEWER_MODE_ANNOTATING
     if (mode === 'off') {
       if (this.currMode === ARIA_LABELS.VIEWER_MODE_ANNOTATING) payload = null
@@ -763,7 +729,7 @@ export class ModularUserAnnotationToolService implements OnDestroy{
     }
     this.store.dispatch(
       actions.setViewerMode({
-        viewerMode: "annotating"
+        viewerMode: payload
       })
     )
   }
diff --git a/src/components/flatHierarchy/treeView/treeControl.ts b/src/components/flatHierarchy/treeView/treeControl.ts
new file mode 100644
index 0000000000000000000000000000000000000000..e664e5984ce4350f3e3f6d746a28fd2487ad0e34
--- /dev/null
+++ b/src/components/flatHierarchy/treeView/treeControl.ts
@@ -0,0 +1,100 @@
+
+type IsParent<T> = (child: T, parent: T) => boolean
+
+export class Tree<T extends object>{
+
+  private _nodes: T[] = []
+  protected set nodes(nodes: T[]) {
+    if (nodes === this._nodes) return
+    this._nodes = nodes
+    this.resetWeakMaps()
+  }
+  protected get nodes() {
+    return this._nodes
+  }
+
+  private _isParent: IsParent<T> = (c, p) => false
+  protected set isParent(fn: IsParent<T>){
+    if (fn === this._isParent) return
+    this._isParent = fn
+    this.resetWeakMaps()
+  }
+  protected get isParent(){
+    return this._isParent
+  }
+  public someAncestor(node: T, predicate: (anc: T) => boolean) {
+    const parent = this.getParent(node)
+    if (!parent) {
+      return false
+    }
+    if (predicate(parent)) {
+      return true
+    }
+    return this.someAncestor(parent, predicate)
+  }
+  public getParent(node: T): T {
+    if (!this.parentWeakMap.has(node)) {
+      for (const parentNode of this.nodes) {
+        if (this.isParent(node, parentNode)) {
+          this.parentWeakMap.set(node, parentNode)
+          break
+        }
+      }
+    }
+    return this.parentWeakMap.get(node)
+  }
+  public getChildren(node: T): T[] {
+    if (!this.childrenWeakMap.has(node)) {
+      const children = this.nodes.filter(childNode => this.isParent(childNode, node))
+      this.childrenWeakMap.set(node, children)
+      for (const c of children) {
+        this.parentWeakMap.set(c, node)
+      }
+    }
+    return this.childrenWeakMap.get(node)
+  }
+  public getLevel(node: T): number {
+    let level = -1, cursor = node
+    const maxLevel = 32
+    do {
+      if (level >= maxLevel) {
+        level = 0
+        break
+      }
+      level++
+      cursor = this.getParent(cursor)
+    } while (!!cursor)
+    return level
+  }
+  protected childrenWeakMap = new WeakMap<T, T[]>()
+  protected parentWeakMap = new WeakMap<T, T>()
+  protected nodeAncestorIsLast = new WeakMap<T, boolean[]>()
+
+  get rootNodes() {
+    const root = this.nodes.filter(node => !this.getParent(node))
+    for (const el of root) {
+      this.parentWeakMap.set(el, null)
+      this.nodeAncestorIsLast.set(el, [])
+    }
+    return root
+  }
+
+  constructor(
+    _nodes: T[] = [],
+    _isParent: IsParent<T> = (c, p) => false
+  ){
+    this._nodes = _nodes
+    this._isParent = _isParent
+  }
+
+  private resetWeakMaps() {
+
+    /**
+     * on new nodes passed, reset all maps
+     * otherwise, tree will show stale data and will not update
+     */
+    this.childrenWeakMap = new WeakMap()
+    this.parentWeakMap = new WeakMap()
+    this.nodeAncestorIsLast = new WeakMap()
+  }
+}
diff --git a/src/components/flatHierarchy/treeView/treeView.component.ts b/src/components/flatHierarchy/treeView/treeView.component.ts
index cab03376d07031cf42a1f2bc137edf8ef5c9a912..99d55b39dc6e811e495fca162b83db92e3d2bfb9 100644
--- a/src/components/flatHierarchy/treeView/treeView.component.ts
+++ b/src/components/flatHierarchy/treeView/treeView.component.ts
@@ -2,6 +2,7 @@ import { FlatTreeControl } from "@angular/cdk/tree";
 import { MatTreeFlatDataSource, MatTreeFlattener } from "@angular/material/tree"
 import { ChangeDetectionStrategy, Component, EventEmitter, HostBinding, Input, OnChanges, Output, SimpleChanges, TemplateRef } from "@angular/core";
 import { TreeNode } from "../const"
+import { Tree } from "./treeControl"
 
 @Component({
   selector: `sxplr-flat-hierarchy-tree-view`,
@@ -13,15 +14,15 @@ import { TreeNode } from "../const"
   exportAs: 'flatHierarchyTreeView'
 })
 
-export class SxplrFlatHierarchyTreeView<T extends object> implements OnChanges{
+export class SxplrFlatHierarchyTreeView<T extends object> extends Tree<T> implements OnChanges{
   @HostBinding('class')
   class = 'sxplr-custom-cmp'
 
   @Input('sxplr-flat-hierarchy-nodes')
-  nodes: T[] = []
+  sxplrNodes: T[] = []
 
   @Input('sxplr-flat-hierarchy-is-parent')
-  isParent: (child: T, parent: T) => boolean
+  sxplrIsParent: (child: T, parent: T) => boolean
 
   @Input('sxplr-flat-hierarchy-render-node-tmpl')
   renderNodeTmplRef: TemplateRef<T>
@@ -42,57 +43,15 @@ export class SxplrFlatHierarchyTreeView<T extends object> implements OnChanges{
   nodeClicked = new EventEmitter<T>()
 
   ngOnChanges(changes: SimpleChanges): void {
-    if (changes.nodes) {
-
-      /**
-       * on new nodes passed, reset all maps
-       * otherwise, tree will show stale data and will not update
-       */
-      this.childrenWeakMap = new WeakMap()
-      this.parentWeakMap = new WeakMap()
-      this.nodeAncestorIsLast = new WeakMap()
-      
-      const root = this.nodes.filter(node => !this.getParent(node))
-      for (const el of root) {
-        this.parentWeakMap.set(el, null)
-        this.nodeAncestorIsLast.set(el, [])
-      }
-      this.dataSource.data = root
+    if (changes.sxplrNodes || changes.sxplrIsParent) {
+      this.nodes = this.sxplrNodes
+      this.isParent = this.sxplrIsParent
+      this.dataSource.data = this.rootNodes
       if (this.expandOnInit) {
         this.treeControl.expandAll()
       }
     }
   }
-  
-  private getLevel(node: T): number {
-    let level = -1, cursor = node
-    const maxLevel = 32
-    do {
-      if (level >= maxLevel) {
-        level = 0
-        break
-      }
-      level++
-      cursor = this.getParent(cursor)
-    } while (!!cursor)
-    return level
-  }
-
-  private getParent(node: T): T {
-    if (!this.parentWeakMap.has(node)) {
-      for (const parentNode of this.nodes) {
-        if (this.isParent(node, parentNode)) {
-          this.parentWeakMap.set(node, parentNode)
-          break
-        }
-      }
-    }
-    return this.parentWeakMap.get(node)
-  }
-
-  private childrenWeakMap = new WeakMap<T, T[]>()
-  private parentWeakMap = new WeakMap<T, T>()
-  private nodeAncestorIsLast = new WeakMap<T, boolean[]>()
 
   private getNodeAncestorIsLast(node: T, visited = new WeakSet<T>() ): boolean[] {
     if (!this.nodeAncestorIsLast.has(node)) {
@@ -115,16 +74,6 @@ export class SxplrFlatHierarchyTreeView<T extends object> implements OnChanges{
     }
     return this.nodeAncestorIsLast.get(node)
   }
-  private getChildren(node: T): T[] {
-    if (!this.childrenWeakMap.has(node)) {
-      const children = this.nodes.filter(childNode => this.isParent(childNode, node))
-      this.childrenWeakMap.set(node, children)
-      for (const c of children) {
-        this.parentWeakMap.set(c, node)
-      }
-    }
-    return this.childrenWeakMap.get(node)
-  }
 
   public treeControl = new FlatTreeControl<TreeNode<T>>(
     ({ level }) => level,
@@ -177,6 +126,6 @@ export class SxplrFlatHierarchyTreeView<T extends object> implements OnChanges{
   }
 
   constructor(){
-    
+    super()
   }
 }
diff --git a/src/extra_styles.css b/src/extra_styles.css
index d7e99033c285ee0b2f3894cadd4dae90631098c3..c4cd571217731a53be10b0b21b9d9e9520757471 100644
--- a/src/extra_styles.css
+++ b/src/extra_styles.css
@@ -858,6 +858,12 @@ iav-cmp-viewer-container .mat-chip-list-wrapper
   flex-wrap: nowrap;
 }
 
+sxplr-sapiviews-features-ieeg-ieegdataset .mat-chip-list-wrapper
+{
+  overflow-y: hidden;
+  overflow-x: auto;
+}
+
 iav-cmp-viewer-container poly-update-cmp .mat-chip-list-wrapper
 {
   flex-wrap: wrap;
diff --git a/src/routerModule/routeStateTransform.service.ts b/src/routerModule/routeStateTransform.service.ts
index 7bb2ae41a0c584bc69fae676ec90315c91a09067..3769be747cb1d2194df43637b6d043c445a59dda 100644
--- a/src/routerModule/routeStateTransform.service.ts
+++ b/src/routerModule/routeStateTransform.service.ts
@@ -104,6 +104,7 @@ export class RouteStateTransformSvc {
       selectedTemplate,
       selectedParcellation,
       selectedRegions,
+      allParcellationRegions
     }
   }
 
@@ -180,11 +181,12 @@ export class RouteStateTransformSvc {
 
 
     try {
-      const { selectedAtlas, selectedParcellation, selectedRegions = [], selectedTemplate } = await this.getATPR(returnObj as TUrlPathObj<string[], TUrlAtlas<string[]>>)
+      const { selectedAtlas, selectedParcellation, selectedRegions = [], selectedTemplate, allParcellationRegions } = await this.getATPR(returnObj as TUrlPathObj<string[], TUrlAtlas<string[]>>)
       returnState["[state.atlasSelection]"].selectedAtlas = selectedAtlas
       returnState["[state.atlasSelection]"].selectedParcellation = selectedParcellation
       returnState["[state.atlasSelection]"].selectedTemplate = selectedTemplate
-      returnState["[state.atlasSelection]"].selectedRegions = selectedRegions
+      returnState["[state.atlasSelection]"].selectedRegions = selectedRegions || []
+      returnState["[state.atlasSelection]"].selectedParcellationAllRegions = allParcellationRegions || []
       returnState["[state.atlasSelection]"].navigation = parsedNavObj
     } catch (e) {
       // if error, show error on UI?
@@ -193,7 +195,13 @@ export class RouteStateTransformSvc {
     return returnState
   }
 
-  cvtStateToRoute(state: MainState) {
+  cvtStateToRoute(_state: MainState) {
+    
+    /**
+     * need to create new references here
+     * or else, the memoized selector will spit out undefined
+     */
+    const state:MainState = JSON.parse(JSON.stringify(_state))
 
     const selectedAtlas = atlasSelection.selectors.selectedAtlas(state)
     const selectedParcellation = atlasSelection.selectors.selectedParcellation(state)
diff --git a/src/routerModule/router.service.ts b/src/routerModule/router.service.ts
index 3a05c6a11fab226f243d6331146fabec4dd1c27f..44f6983f90ef1eb95c3b701d2fc6f93f998b52ce 100644
--- a/src/routerModule/router.service.ts
+++ b/src/routerModule/router.service.ts
@@ -3,7 +3,7 @@ import { APP_BASE_HREF } from "@angular/common";
 import { Inject } from "@angular/core";
 import { NavigationEnd, Router } from '@angular/router'
 import { Store } from "@ngrx/store";
-import { debounceTime, distinctUntilChanged, filter, map, mapTo, shareReplay, startWith, switchMap, switchMapTo, take, tap, withLatestFrom } from "rxjs/operators";
+import { debounceTime, distinctUntilChanged, filter, finalize, map, mapTo, shareReplay, startWith, switchMap, switchMapTo, take, tap, withLatestFrom } from "rxjs/operators";
 import { encodeCustomState, decodeCustomState, verifyCustomState } from "./util";
 import { BehaviorSubject, combineLatest, concat, EMPTY, merge, NEVER, Observable, of, timer } from 'rxjs'
 import { scan } from 'rxjs/operators'
@@ -120,9 +120,19 @@ export class RouterService {
     /**
      * does work too well =( 
      */
-    navEnd$.pipe(
-      map(navEv => navEv.urlAfterRedirects)
+     concat(
+      onload$.pipe(
+        mapTo(false)
+      ),
+      timer(160).pipe(
+        mapTo(false)
+      ),
+      ready$.pipe(
+        map(val => !!val)
+      )
     ).pipe(
+      switchMap(() => navEnd$),
+      map(navEv => navEv.urlAfterRedirects),
       switchMap(url =>
         routeToStateTransformSvc.cvtRouteToState(
           router.parseUrl(
diff --git a/src/state/annotations/actions.ts b/src/state/annotations/actions.ts
index da4ad8edeb6f86d3f80a5d8d3a310d56dc353428..daaddd8ce723f92010ab287f01056314e5a6b838 100644
--- a/src/state/annotations/actions.ts
+++ b/src/state/annotations/actions.ts
@@ -2,18 +2,20 @@ import { createAction, props } from "@ngrx/store"
 import { nameSpace } from "./const"
 import { Annotation } from "./store"
 
-const clearAllAnnotations = createAction(
+export const clearAllAnnotations = createAction(
   `${nameSpace} clearAllAnnotations`
 )
 
-const rmAnnotations = createAction(
-  `${nameSpace} rmAnnotation`,
+export const rmAnnotations = createAction(
+  `${nameSpace} rmAnnotations`,
   props<{
     annotations: Annotation[]
   }>()
 )
 
-export const actions = {
-  clearAllAnnotations,
-  rmAnnotations,
-}
+export const addAnnotations = createAction(
+  `${nameSpace} addAnnotations`,
+  props<{
+    annotations: Annotation[]
+  }>()
+)
diff --git a/src/state/annotations/index.ts b/src/state/annotations/index.ts
index 4071cad11b68b6473c88bb7d7374a4d1de77767d..4ad0f0680a29a2c7725e37ffa614f74122a0e152 100644
--- a/src/state/annotations/index.ts
+++ b/src/state/annotations/index.ts
@@ -1,4 +1,4 @@
-export { actions } from "./actions"
+export * as actions from "./actions"
 export { Annotation, AnnotationState, reducer, defaultState } from "./store"
 export { nameSpace } from "./const"
-export * as selectors from "./selectors"
\ No newline at end of file
+export * as selectors from "./selectors"
diff --git a/src/state/annotations/store.ts b/src/state/annotations/store.ts
index 2cb8146bfabd329d4a80b60bb3dff6c9a41663f8..113220b473143036be868d2479282d70bb2d33d7 100644
--- a/src/state/annotations/store.ts
+++ b/src/state/annotations/store.ts
@@ -1,4 +1,5 @@
-import { createReducer } from "@ngrx/store"
+import { createReducer, on } from "@ngrx/store"
+import * as actions from "./actions"
 
 export type Annotation = {
   "@id": string
@@ -13,7 +14,29 @@ export const defaultState: AnnotationState = {
 }
 
 const reducer = createReducer(
-  defaultState
+  defaultState,
+  on(
+    actions.addAnnotations,
+    (state, { annotations }) => {
+      return {
+        ...state,
+        annotations: [
+          ...state.annotations,
+          ...annotations,
+        ]
+      }
+    }
+  ),
+  on(
+    actions.rmAnnotations,
+    (state, { annotations }) => {
+      const annIdToBeRemoved = annotations.map(ann => ann["@id"])
+      return {
+        ...state,
+        annotations: state.annotations.filter(ann => !annIdToBeRemoved.includes(ann["@id"]) )
+      }
+    }
+  )
 )
 
 export {
diff --git a/src/state/atlasSelection/actions.ts b/src/state/atlasSelection/actions.ts
index f96dd19ee44328028247e58bba9f0b14b30aac85..8787234b909287c331473dfe6d0cceb578375111 100644
--- a/src/state/atlasSelection/actions.ts
+++ b/src/state/atlasSelection/actions.ts
@@ -24,7 +24,7 @@ export const selectParcellation = createAction(
 )
 
 /**
- * setATP is called as a final step to (potentially) set:
+ * setAtlasSelectionState is called as a final step to (potentially) set:
  * - selectedAtlas
  * - selectedTemplate
  * - selectedParcellation
@@ -36,13 +36,9 @@ export const selectParcellation = createAction(
  * We may setup post hook for navigation adjustments/etc.
  * Probably easier is simply subscribe to store and react to selectedTemplate selector
  */
-export const setATP = createAction(
-  `${nameSpace} setATP`,
-  props<{
-    atlas?: SapiAtlasModel,
-    template?: SapiSpaceModel,
-    parcellation?: SapiParcellationModel,
-  }>()
+export const setAtlasSelectionState = createAction(
+  `${nameSpace} setAtlasSelectionState`,
+  props<Partial<AtlasSelectionState>>()
 )
 
 export const setSelectedParcellationAllRegions = createAction(
diff --git a/src/state/atlasSelection/effects.ts b/src/state/atlasSelection/effects.ts
index ae69fa17c4345bd3e1f5d77873be1f37dd0cf4cb..6b988a8db2347fc1d0e3fe70cbb41b2cdba8744e 100644
--- a/src/state/atlasSelection/effects.ts
+++ b/src/state/atlasSelection/effects.ts
@@ -1,28 +1,62 @@
 import { Injectable } from "@angular/core";
 import { Actions, createEffect, ofType } from "@ngrx/effects";
-import { concat, forkJoin, merge, of } from "rxjs";
+import { concat, forkJoin, merge, Observable, of } from "rxjs";
 import { filter, map, mapTo, switchMap, switchMapTo, take, tap, withLatestFrom } from "rxjs/operators";
-import { SAPI, SapiParcellationModel, SAPIRegion, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi";
+import { SAPI, SapiAtlasModel, SapiParcellationModel, SAPIRegion, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi";
 import * as mainActions from "../actions"
 import { select, Store } from "@ngrx/store";
 import { selectors, actions } from '.'
 import { fromRootStore } from "./util";
+import { AtlasSelectionState } from "./const"
 import { ParcellationIsBaseLayer } from "src/atlasComponents/sapiViews/core/parcellation/parcellationIsBaseLayer.pipe";
 import { OrderParcellationByVersionPipe } from "src/atlasComponents/sapiViews/core/parcellation/parcellationVersion.pipe";
-import { atlasAppearance, atlasSelection } from "..";
+import { atlasAppearance } from "..";
 import { ParcellationSupportedInSpacePipe } from "src/atlasComponents/sapiViews/util/parcellationSupportedInSpace.pipe";
 
+type OnTmplParcHookArg = {
+  previous: {
+    atlas: SapiAtlasModel
+    template: SapiSpaceModel
+    parcellation: SapiParcellationModel
+  }
+  current: {
+    atlas: SapiAtlasModel
+    template: SapiSpaceModel
+    parcellation: SapiParcellationModel
+  }
+}
+
 @Injectable()
 export class Effect {
 
-  parcSupportedInSpacePipe = new ParcellationSupportedInSpacePipe(this.sapiSvc)
+  onTemplateParcSelectionPostHook: ((arg: OnTmplParcHookArg) => Observable<Partial<AtlasSelectionState>>)[] = [
+    /**
+     * This hook gets the region associated with the selected parcellation and template,
+     * and then set selectedParcellationAllRegions to it
+     */
+    ({ current }) => {
+      const { atlas, parcellation, template } = current
+      return (
+        !!atlas && !!parcellation && !!template
+        ? this.sapiSvc.getParcRegions(atlas["@id"], parcellation["@id"], template["@id"])
+        : of([])
+      ).pipe(
+        map(regions => {
+          return {
+            selectedParcellationAllRegions: regions
+          }
+        })
+      )
+    }
+  ]
 
+  parcSupportedInSpacePipe = new ParcellationSupportedInSpacePipe(this.sapiSvc)
   onTemplateParcSelection = createEffect(() => merge<{ template: SapiSpaceModel, parcellation: SapiParcellationModel }>(
     this.action.pipe(
       ofType(actions.selectTemplate),
       map(({ template }) => {
         return {
-          template, 
+          template,
           parcellation: null
         }
       })
@@ -52,6 +86,7 @@ export class Effect {
            */
           if (flag) {
             return of({
+              atlas: currAtlas,
               template: template || currTmpl,
               parcellation: parcellation || currParc,
             })
@@ -71,6 +106,7 @@ export class Effect {
               take(1),
               map(parcellation => {
                 return {
+                  atlas: currAtlas,
                   template,
                   parcellation
                 }
@@ -89,6 +125,7 @@ export class Effect {
               take(1),
               map(template => {
                 return {
+                  atlas: currAtlas,
                   template,
                   parcellation
                 }
@@ -97,15 +134,28 @@ export class Effect {
           }
           throw new Error(`neither template nor parcellation has been defined!`)
         }),
-        map(({ parcellation, template }) => {
-          return actions.setATP({
-            parcellation,
-            template
-          })
-        })
+        switchMap(({ atlas, template, parcellation }) => 
+          forkJoin(
+            this.onTemplateParcSelectionPostHook.map(fn => fn({ previous: { atlas: currAtlas, template: currTmpl, parcellation: currParc }, current: { atlas, template, parcellation } }))
+          ).pipe(
+            map(partialStates => {
+              let returnState: Partial<AtlasSelectionState> = {
+                selectedAtlas: atlas,
+                selectedTemplate: template,
+                selectedParcellation: parcellation
+              }
+              for (const s of partialStates) {
+                returnState = {
+                  ...returnState,
+                  ...s,
+                }
+              }
+              return actions.setAtlasSelectionState(returnState)
+            })
+          )
+        )
       )
-    }),
-
+    })
   ))
 
   onAtlasSelectionSelectTmplParc = createEffect(() => this.action.pipe(
@@ -131,35 +181,30 @@ export class Effect {
           this.sapiSvc.getSpaceDetail(atlas["@id"], spaceId["@id"])
         )
       ).pipe(
-        map(spaces => {
+        switchMap(spaces => {
           const selectedSpace = spaces.find(s => /152/.test(s.fullName)) || spaces[0]
-          return actions.setATP({
-            atlas,
-            template: selectedSpace,
-            parcellation
-          })
-        })
-      )
-    }),
-  ))
+          return forkJoin(
+            this.onTemplateParcSelectionPostHook.map(fn => fn({ previous: null, current: { atlas, parcellation, template: selectedSpace } }))
+          ).pipe(
+            map(partialStates => {
 
-  onATPSelectionGetAndSetAllRegions = createEffect(() => this.store.pipe(
-    atlasSelection.fromRootStore.distinctATP(),
-    switchMap(({ atlas, template, parcellation }) => 
-      !!atlas && !!template && !!parcellation
-      ? this.sapiSvc.getParcRegions(atlas["@id"], parcellation["@id"], template["@id"]).pipe(
-          map(regions => 
-            actions.setSelectedParcellationAllRegions({
-              regions
+              let returnState: Partial<AtlasSelectionState> = {
+                selectedAtlas: atlas,
+                selectedTemplate: selectedSpace,
+                selectedParcellation: parcellation
+              }
+              for (const s of partialStates) {
+                returnState = {
+                  ...returnState,
+                  ...s,
+                }
+              }
+              return actions.setAtlasSelectionState(returnState)
             })
           )
-      )
-      : of(
-        actions.setSelectedParcellationAllRegions({
-          regions: []
         })
       )
-    )
+    })
   ))
 
   onATPSelectionClearBaseLayerColorMap = createEffect(() => this.store.pipe(
diff --git a/src/state/atlasSelection/store.ts b/src/state/atlasSelection/store.ts
index 45bc4f669ead58ed58c6af97e3cb45e2c601f14c..08848c1efa9b81e649bfc8d7c29d3cc6581f77ed 100644
--- a/src/state/atlasSelection/store.ts
+++ b/src/state/atlasSelection/store.ts
@@ -24,13 +24,11 @@ export const defaultState: AtlasSelectionState = {
 const reducer = createReducer(
   defaultState,
   on(
-    actions.setATP,
-    (state, { atlas, parcellation, template }) => {
+    actions.setAtlasSelectionState,
+    (state, partialState) => {
       return {
         ...state,
-        selectedAtlas: atlas || state.selectedAtlas,
-        selectedTemplate: template || state.selectedTemplate,
-        selectedParcellation: parcellation || state.selectedParcellation,
+        ...partialState
       }
     }
   ),
@@ -116,6 +114,15 @@ const reducer = createReducer(
       }
     }
   ),
+  on(
+    actions.selectAtlas,
+    (state, { atlas }) => {
+      return {
+        ...state,
+        selectedAtlas: atlas
+      }
+    }
+  ),
   on(
     actions.dismissBreadCrumb,
     (state, { id }) => {
diff --git a/src/state/index.ts b/src/state/index.ts
index d465bfb4a624ead5445fdf23388dd0e9bbedcc42..3eba9c31857ad2db855c3c9c8e4c461c8fd488ee 100644
--- a/src/state/index.ts
+++ b/src/state/index.ts
@@ -35,13 +35,11 @@ function generalApplyStateReducer(reducer: ActionReducer<MainState>): ActionRedu
   return function(_state, action) {
     let state = _state
     if (action.type === generalApplyState.type) {
-      state = {
-        ...state,
-        /**
-         * typing is a bit scuffed, but works
-         */
-        ...(action as any).state
-      }
+      state = JSON.parse(
+        JSON.stringify(
+          (action as any).state
+        )
+      ) 
     }
     return reducer(state, action)
   }
diff --git a/src/viewerModule/module.ts b/src/viewerModule/module.ts
index a4d1fc05f373b2ca33076f7c8d690bfb9c8f7e1b..a485a115773c2953b3396c72a0d054d925fa85f6 100644
--- a/src/viewerModule/module.ts
+++ b/src/viewerModule/module.ts
@@ -1,7 +1,6 @@
 import { CommonModule } from "@angular/common";
 import { NgModule } from "@angular/core";
 import { Observable } from "rxjs";
-import { SplashUiModule } from "src/atlasComponents/splashScreen";
 import { ComponentsModule } from "src/components";
 import { ContextMenuModule, ContextMenuService, TContextMenuReg } from "src/contextMenuModule";
 import { LayoutModule } from "src/layouts/layout.module";
@@ -33,7 +32,6 @@ import { DialogModule } from "src/ui/dialogInfo/module";
     ThreeSurferModule,
     LayoutModule,
     AngularMaterialModule,
-    SplashUiModule,
     TopMenuModule,
     UtilModule,
     ComponentsModule,
diff --git a/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.effects.ts b/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.effects.ts
index e74aee0c302bdf627dbe60b1e7a0cd758ff705e5..934f5ba8d3147fba7292b51436c2bdc1357f8417 100644
--- a/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.effects.ts
+++ b/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.effects.ts
@@ -37,8 +37,8 @@ export class LayerCtrlEffects {
     ),
     switchMap(([ regions, { atlas, parcellation, template } ]) => {
       const sapiRegion = this.sapi.getRegion(atlas["@id"], parcellation["@id"], regions[0].name)
-      return sapiRegion.getMapInfo(template["@id"])
-        .then(val => 
+      return sapiRegion.getMapInfo(template["@id"]).pipe(
+        map(val => 
           atlasAppearance.actions.addCustomLayer({
             customLayer: {
               clType: "customlayer/nglayer",
@@ -52,13 +52,14 @@ export class LayerCtrlEffects {
               })
             }
           })
-        )
+        ),
+        catchError((err, obs) => of(
+          atlasAppearance.actions.removeCustomLayer({
+            id: NehubaLayerControlService.PMAP_LAYER_NAME
+          })
+        ))
+      )
     }),
-    catchError((err, obs) => of(
-      atlasAppearance.actions.removeCustomLayer({
-        id: NehubaLayerControlService.PMAP_LAYER_NAME
-      })
-    ))
   ))
 
   onATP$ = this.store.pipe(
diff --git a/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts b/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts
index ad0528023661161f926a263545e72bc268f3c6d9..2f86c53b2a37395d57f7805a6df835025c018398 100644
--- a/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts
+++ b/src/viewerModule/nehuba/layerCtrl.service/layerCtrl.service.ts
@@ -3,15 +3,13 @@ import { select, Store } from "@ngrx/store";
 import { BehaviorSubject, combineLatest, merge, Observable, Subject, Subscription } from "rxjs";
 import { debounceTime, distinctUntilChanged, filter, map, shareReplay, switchMap, tap, withLatestFrom } from "rxjs/operators";
 import { IColorMap, INgLayerCtrl, TNgLayerCtrl } from "./layerCtrl.util";
-import { IAuxMesh } from '../store'
-import { IVolumeTypeDetail } from "src/util/siibraApiConstants/types";
-import { SAPI, SapiParcellationModel } from "src/atlasComponents/sapi";
-import { SAPISpace, SAPIRegion } from "src/atlasComponents/sapi/core";
+import { SAPIRegion } from "src/atlasComponents/sapi/core";
 import { getParcNgId } from "../config.service"
 import { getRegionLabelIndex } from "../config.service/util";
 import { annotation, atlasAppearance, atlasSelection } from "src/state";
 import { serializeSegment } from "../util";
 import { LayerCtrlEffects } from "./layerCtrl.effects";
+import { arrayEqual } from "src/util/array";
 
 export const BACKUP_COLOR = {
   red: 255,
@@ -96,33 +94,6 @@ export class NehubaLayerControlService implements OnDestroy{
       ...cmAux
     }))
   )
-  
-  private auxMeshes$: Observable<IAuxMesh[]> = this.selectedATP$.pipe(
-    map(({ template }) => template),
-    switchMap(tmpl => this.sapiSvc.registry.get<SAPISpace>(tmpl["@id"]).getVolumes().pipe(
-      map(
-        tmplVolumes => {
-          const auxMeshArr: IAuxMesh[] = []
-          for (const vol of tmplVolumes) {
-            if (vol.data.detail["neuroglancer/precompmesh"]) {
-              const detail = vol.data.detail as IVolumeTypeDetail["neuroglancer/precompmesh"]
-              for (const auxMesh of detail["neuroglancer/precompmesh"].auxMeshes) {
-                auxMeshArr.push({
-                  "@id": `auxmesh-${tmpl["@id"]}-${auxMesh.name}`,
-                  labelIndicies: auxMesh.labelIndicies,
-                  name: auxMesh.name,
-                  ngId: '',
-                  rgb: [255, 255, 255],
-                  visible: auxMesh.name !== "Sulci"
-                })
-              }
-            }
-          }
-          return auxMeshArr
-        }
-      )
-    ))
-  )
 
   private sub: Subscription[] = []
 
@@ -132,7 +103,6 @@ export class NehubaLayerControlService implements OnDestroy{
 
   constructor(
     private store$: Store<any>,
-    private sapiSvc: SAPI,
     private layerEffects: LayerCtrlEffects,
   ){
 
@@ -166,43 +136,22 @@ export class NehubaLayerControlService implements OnDestroy{
       })
     )
 
-    this.sub.push(
-      this.store$.pipe(
-        select(atlasAppearance.selectors.customLayers),
-        map(cl => cl.filter(l => l.clType === "customlayer/colormap").length > 0),
-        distinctUntilChanged()
-      ).subscribe(flag => {
-        const pmapLayer = this.ngLayersRegister.find(l => l.id === NehubaLayerControlService.PMAP_LAYER_NAME)
-        if (!pmapLayer) return
-        const payload = {
-          type: 'update',
-          payload: {
-            [NehubaLayerControlService.PMAP_LAYER_NAME]: {
-              visible: !flag
-            }
-          }
-        } as TNgLayerCtrl<'update'>
-        this.manualNgLayersControl$.next(payload)
-      })
-    )
-
     /**
      * on custom landmarks loaded, set mesh transparency
      */
     this.sub.push(
       this.store$.pipe(
         select(annotation.selectors.annotations),
-        withLatestFrom(this.auxMeshes$)
-      ).subscribe(([landmarks, auxMeshes]) => {
-        
+        withLatestFrom(this.defaultNgLayers$)
+      ).subscribe(([landmarks, { tmplAuxNgLayers }]) => {
         const payload: {
           [key: string]: number
         } = {}
         const alpha = landmarks.length > 0
           ? 0.2
           : 1.0
-        for (const auxMesh of auxMeshes) {
-          payload[auxMesh.ngId] = alpha
+        for (const ngId in tmplAuxNgLayers) {
+          payload[ngId] = alpha
         }
         
         this.manualNgLayersControl$.next({
@@ -242,11 +191,28 @@ export class NehubaLayerControlService implements OnDestroy{
     })
   )
 
-  public visibleLayer$: Observable<string[]> = this.expectedLayerNames$.pipe(
-    map(expectedLayerNames => {
-      const ngIdSet = new Set<string>([...expectedLayerNames])
-      return Array.from(ngIdSet)
-    })
+  public visibleLayer$: Observable<string[]> = combineLatest([
+    this.expectedLayerNames$.pipe(
+      map(expectedLayerNames => {
+        const ngIdSet = new Set<string>([...expectedLayerNames])
+        return Array.from(ngIdSet)
+      })
+    ),
+    this.store$.pipe(
+      select(atlasAppearance.selectors.customLayers),
+      map(cl => {
+        const otherColormapExist = cl.filter(l => l.clType === "customlayer/colormap").length > 0
+        const pmapExist = cl.filter(l => l.clType === "customlayer/nglayer").length > 0
+        return pmapExist && !otherColormapExist
+      }),
+      distinctUntilChanged(),
+      map(flag => flag
+        ? [ NehubaLayerControlService.PMAP_LAYER_NAME ]
+        : []
+      )
+    )
+  ]).pipe(
+    map(([ expectedLayerNames, pmapLayer ]) => [...expectedLayerNames, ...pmapLayer])
   )
 
   /**
@@ -303,6 +269,9 @@ export class NehubaLayerControlService implements OnDestroy{
   private ngLayers$ = this.store$.pipe(
     select(atlasAppearance.selectors.customLayers),
     map(customLayers => customLayers.filter(l => l.clType === "customlayer/nglayer") as atlasAppearance.NgLayerCustomLayer[]),
+    distinctUntilChanged(
+      arrayEqual((o, n) => o.id === n.id)
+    ),
     map(customLayers => {
       const newLayers = customLayers.filter(l => {
         const registeredLayerNames = this.ngLayersRegister.map(l => l.id)
diff --git a/src/viewerModule/nehuba/mesh.service/mesh.service.ts b/src/viewerModule/nehuba/mesh.service/mesh.service.ts
index c1aadf90a5fdda983bc101105652574020317a58..6313ccba3200e4195fe17ae03dfa522daa5e7ef6 100644
--- a/src/viewerModule/nehuba/mesh.service/mesh.service.ts
+++ b/src/viewerModule/nehuba/mesh.service/mesh.service.ts
@@ -1,10 +1,13 @@
 import { Injectable, OnDestroy } from "@angular/core";
 import { select, Store } from "@ngrx/store";
-import { merge, Observable, of } from "rxjs";
+import { combineLatest, merge, Observable, of } from "rxjs";
 import { map, switchMap } from "rxjs/operators";
 import { IMeshesToLoad } from '../constants'
 import { selectorAuxMeshes } from "../store";
 import { LayerCtrlEffects } from "../layerCtrl.service/layerCtrl.effects";
+import { atlasSelection } from "src/state";
+import { Tree } from "src/components/flatHierarchy/treeView/treeControl"
+import { getParcNgId, getRegionLabelIndex } from "../config.service";
 
 /**
  * control mesh loading etc
@@ -33,13 +36,55 @@ export class NehubaMeshService implements OnDestroy {
   private ngLayers$ = this.effect.onATPDebounceNgLayers$
 
   public loadMeshes$: Observable<IMeshesToLoad> = merge(
-    this.ngLayers$.pipe(
-      switchMap(ngLayers => {
+    combineLatest([
+      this.store$.pipe(
+        atlasSelection.fromRootStore.distinctATP(),
+      ),
+      this.store$.pipe(
+        select(atlasSelection.selectors.selectedParcAllRegions),
+      ),
+      this.store$.pipe(
+        select(atlasSelection.selectors.selectedRegions),
+      )
+    ]).pipe(
+      switchMap(([{ atlas, template, parcellation }, regions, selectedRegions]) => {
+        const tree = new Tree(
+          regions,
+          (c, p) => (c.hasParent || []).some(_p => _p["@id"] === p["@id"])
+        )
+
+        const ngIdRecord: Record<string, number[]> = {}
+        if (selectedRegions.length > 0) {
+          for (const r of selectedRegions) {
+            const ngId = getParcNgId(atlas, template, parcellation, r)
+            const regionLabelIndex = getRegionLabelIndex( atlas, template, parcellation, r )
+            if (!ngIdRecord[ngId]) {
+              ngIdRecord[ngId] = []
+            }
+            ngIdRecord[ngId].push(regionLabelIndex)
+          }
+        } else {
+          for (const r of regions) {
+            const regionLabelIndex = getRegionLabelIndex( atlas, template, parcellation, r )
+            if (!regionLabelIndex) {
+              continue
+            }
+            if (
+              tree.someAncestor(r, (anc) => !!getRegionLabelIndex(atlas, template, parcellation, anc))
+            ) {
+              continue
+            }
+            const ngId = getParcNgId(atlas, template, parcellation, r)
+            if (!ngIdRecord[ngId]) {
+              ngIdRecord[ngId] = []
+            }
+            ngIdRecord[ngId].push(regionLabelIndex)
+          }  
+        }
         const arr: IMeshesToLoad[] = []
-        const { parcNgLayers } = ngLayers
   
-        for (const ngId in parcNgLayers) {
-          const {labelIndicies} = parcNgLayers[ngId]
+        for (const ngId in ngIdRecord) {
+          const labelIndicies = ngIdRecord[ngId]
           arr.push({
             labelIndicies,
             layer: { name: ngId }
diff --git a/src/viewerModule/nehuba/nehubaViewerGlue/nehubaViewerGlue.component.ts b/src/viewerModule/nehuba/nehubaViewerGlue/nehubaViewerGlue.component.ts
index 964fdbb5646f7dd3edd385d6859e5ea22d3eba36..707a473bfe8a82b3ebb865bb4691639a0cdcc222 100644
--- a/src/viewerModule/nehuba/nehubaViewerGlue/nehubaViewerGlue.component.ts
+++ b/src/viewerModule/nehuba/nehubaViewerGlue/nehubaViewerGlue.component.ts
@@ -2,11 +2,10 @@ import { AfterViewInit, ChangeDetectionStrategy, ChangeDetectorRef, Component, E
 import { select, Store } from "@ngrx/store";
 import { Subject, Subscription } from "rxjs";
 import { ClickInterceptor, CLICK_INTERCEPTOR_INJECTOR } from "src/util";
-import { debounceTime, distinctUntilChanged, filter, map, startWith, switchMap, take } from "rxjs/operators";
+import { distinctUntilChanged, startWith } from "rxjs/operators";
 import { ARIA_LABELS } from 'common/constants'
 import { LoggingService } from "src/logging";
 import { EnumViewerEvt, IViewer, TViewerEvent } from "../../viewer.interface";
-import { NehubaViewerUnit } from "../nehubaViewer/nehubaViewer.component";
 import { NehubaViewerContainerDirective, TMouseoverEvent } from "../nehubaViewerInterface/nehubaViewerInterface.directive";
 import { API_SERVICE_SET_VIEWER_HANDLE_TOKEN, TSetViewerHandle } from "src/atlasViewer/atlasViewer.apiService.service";
 import { NehubaMeshService } from "../mesh.service";
@@ -19,13 +18,10 @@ import { getShader } from "src/util/constants";
 import { EnumColorMapName } from "src/util/colorMaps";
 import { MatDialog } from "@angular/material/dialog";
 import { AtlasWorkerService } from "src/atlasViewer/atlasViewer.workerService.service";
-import { SapiAtlasModel, SapiParcellationModel, SapiRegionModel, SapiSpaceModel } from "src/atlasComponents/sapi";
-import { NehubaConfig, getNehubaConfig, getParcNgId, getRegionLabelIndex } from "../config.service";
+import { SapiRegionModel } from "src/atlasComponents/sapi";
+import { NehubaConfig, getParcNgId, getRegionLabelIndex } from "../config.service";
 import { SET_MESHES_TO_LOAD } from "../constants";
 import { annotation, atlasAppearance, atlasSelection, userInteraction } from "src/state";
-import { NgLayerCustomLayer } from "src/state/atlasAppearance";
-import { arrayEqual } from "src/util/array";
-import { LayerCtrlEffects } from "../layerCtrl.service/layerCtrl.effects";
 
 export const INVALID_FILE_INPUT = `Exactly one (1) nifti file is required!`
 
@@ -80,14 +76,10 @@ export class NehubaGlueCmp implements IViewer<'nehuba'>, OnDestroy, AfterViewIni
 
   private onhoverSegments: SapiRegionModel[] = []
   private onDestroyCb: (() => void)[] = []
-  private viewerUnit: NehubaViewerUnit
   private multiNgIdsRegionsLabelIndexMap = new Map<string, Map<number, SapiRegionModel>>()
 
   public nehubaConfig: NehubaConfig
-  private navigation: any
-  private newViewer$ = new Subject()
 
-  
   public customLandmarks$ = this.store$.pipe(
     select(annotation.selectors.annotations),
   )
@@ -187,7 +179,6 @@ export class NehubaGlueCmp implements IViewer<'nehuba'>, OnDestroy, AfterViewIni
     /**
      * clear existing container
      */
-    this.viewerUnit = null
     this.nehubaContainerDirective && this.nehubaContainerDirective.clear()
   }
 
@@ -256,14 +247,6 @@ export class NehubaGlueCmp implements IViewer<'nehuba'>, OnDestroy, AfterViewIni
     if (setViewerHandle) {
       console.warn(`NYI viewer handle is deprecated`)
     }
-
-    // listen to navigation change from store
-    const navSub = this.store$.pipe(
-      select(atlasSelection.selectors.navigation)
-    ).subscribe(nav => {
-      this.navigation = nav
-    })
-    this.onDestroyCb.push(() => navSub.unsubscribe())
   }