You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@isis.apache.org by jo...@apache.org on 2021/05/10 07:11:45 UTC

[isis] 08/12: ui package content restructured

This is an automated email from the ASF dual-hosted git repository.

joergrade pushed a commit to branch ISIS-2505_Catch_Up_With_Demo_Examples
in repository https://gitbox.apache.org/repos/asf/isis.git

commit bf18fba416b123c7daabb8f80562067b563df9f5
Author: Jörg Rade <jo...@kuehne-nagel.com>
AuthorDate: Wed May 5 21:52:47 2021 +0200

    ui package content restructured
---
 .../kotlin/org/apache/isis/client/kroviz/App.kt    |   2 +-
 .../org/apache/isis/client/kroviz/core/Session.kt  |   2 +-
 .../kroviz/core/aggregator/ActionDispatcher.kt     |   4 +-
 .../kroviz/core/aggregator/AggregatorWithLayout.kt |   2 +-
 .../kroviz/core/aggregator/BaseAggregator.kt       |   2 +-
 .../core/aggregator/DomainTypesAggregator.kt       |   2 +-
 .../kroviz/core/aggregator/DownloadDispatcher.kt   |   2 +-
 .../kroviz/core/aggregator/ErrorDispatcher.kt      |   2 +-
 .../kroviz/core/aggregator/ListAggregator.kt       |   2 +-
 .../kroviz/core/aggregator/NavigationDispatcher.kt |   2 +-
 .../kroviz/core/aggregator/ObjectAggregator.kt     |   4 +-
 .../client/kroviz/core/aggregator/SvgDispatcher.kt |   2 +-
 .../kroviz/core/aggregator/UndefinedDispatcher.kt  |   2 +-
 .../isis/client/kroviz/core/event/EventStore.kt    |   2 +-
 .../isis/client/kroviz/core/event/LogEntry.kt      |   4 +-
 .../kroviz/core/event/ResourceSpecification.kt     |   2 +-
 .../client/kroviz/core/event/RoXmlHttpRequest.kt   |   4 +-
 .../isis/client/kroviz/handler/BaseHandler.kt      |   2 +-
 .../client/kroviz/handler/DomainTypesHandler.kt    |   4 +-
 .../isis/client/kroviz/ui/builder/ColBuilder.kt    |   2 +-
 .../client/kroviz/ui/builder/FieldSetBuilder.kt    |   6 +-
 .../isis/client/kroviz/ui/builder/LayoutBuilder.kt |   2 +-
 .../isis/client/kroviz/ui/builder/RowBuilder.kt    |   4 +-
 .../isis/client/kroviz/ui/builder/TabBuilder.kt    |   2 +-
 .../client/kroviz/ui/builder/TabGroupBuilder.kt    |   2 +-
 .../client/kroviz/ui/{kv => chart}/ChartFactory.kt |   3 +-
 .../client/kroviz/ui/{kv => chart}/ChartModel.kt   |   2 +-
 .../kroviz/ui/{kv => chart}/EventChartModel.kt     |   2 +-
 .../ui/{samples => chart}/SampleChartModel.kt      |   4 +-
 .../client/kroviz/ui/{kv => core}/ColumnFactory.kt |   2 +-
 .../client/kroviz/ui/{kv => core}/Constants.kt     |   2 +-
 .../client/kroviz/ui/{ => core}/Displayable.kt     |   2 +-
 .../isis/client/kroviz/ui/{ => core}/FormItem.kt   |   2 +-
 .../client/kroviz/ui/{kv => core}/MenuFactory.kt   |   2 +-
 .../isis/client/kroviz/ui/{kv => core}/RoApp.kt    |   7 +-
 .../isis/client/kroviz/ui/{kv => core}/RoDialog.kt |  16 +-
 .../client/kroviz/ui/{kv => core}/RoDisplay.kt     |   3 +-
 .../client/kroviz/ui/{kv => core}/RoIconBar.kt     |  12 +-
 .../client/kroviz/ui/{kv => core}/RoMenuBar.kt     |  15 +-
 .../client/kroviz/ui/{kv => core}/RoStatusBar.kt   |   8 +-
 .../isis/client/kroviz/ui/{kv => core}/RoTable.kt  |   2 +-
 .../isis/client/kroviz/ui/{kv => core}/RoView.kt   |   5 +-
 .../client/kroviz/ui/{kv => core}/UiManager.kt     |   4 +-
 .../isis/client/kroviz/ui/{kv => dialog}/About.kt  |   6 +-
 .../kroviz/ui/{kv => dialog}/ActionPrompt.kt       |   6 +-
 .../client/kroviz/ui/{ => dialog}/BrowserWindow.kt |   5 +-
 .../isis/client/kroviz/ui/{ => dialog}/Command.kt  |   2 +-
 .../client/kroviz/ui/{ => dialog}/DiagramDialog.kt |  42 +-
 .../kroviz/ui/{ => dialog}/DownloadDialog.kt       |   5 +-
 .../client/kroviz/ui/{ => dialog}/ErrorDialog.kt   |   5 +-
 .../kroviz/ui/{ => dialog}/EventExportDialog.kt    |   5 +-
 .../kroviz/ui/{ => dialog}/EventLogDetail.kt       |   8 +-
 .../client/kroviz/ui/{ => dialog}/FileDialog.kt    |   5 +-
 .../client/kroviz/ui/{kv => dialog}/LoginPrompt.kt |   7 +-
 .../kroviz/ui/{ => dialog}/NotificationDialog.kt   |   7 +-
 .../kroviz/ui/{samples => dialog}/SvgInline.kt     |   7 +-
 .../kroviz/ui/{ => dialog}/UndefinedDialog.kt      |   5 +-
 .../apache/isis/client/kroviz/ui/kv/RoTabPanel.kt  |  50 ---
 .../ui/kv/{ => override}/RoManagerBootstrap.kt     |   2 +-
 .../isis/client/kroviz/ui/kv/override/RoTab.kt     | 204 ++++++++++
 .../client/kroviz/ui/kv/override/RoTabPanel.kt     | 437 +++++++++++++++++++++
 .../client/kroviz/ui/kv/{ => override}/RoWindow.kt |  64 +--
 .../kroviz/ui/{kv => panel}/DropdownSearch.kt      |  16 +-
 .../client/kroviz/ui/{kv => panel}/EventChart.kt   |   3 +-
 .../kroviz/ui/{kv => panel}/EventLogTable.kt       |   5 +-
 .../kroviz/ui/{kv => panel}/EventLogTableMgr.kt    |  10 +-
 .../kroviz/ui/{kv => panel}/FormPanelFactory.kt    |   4 +-
 .../client/kroviz/ui/{samples => panel}/GeoMap.kt  |   6 +-
 .../kroviz/ui/{samples => panel}/PlantumlPanel.kt  |   2 +-
 .../client/kroviz/ui/{samples => panel}/SvgMap.kt  |   2 +-
 .../client/kroviz/ui/{kv => panel}/SvgPanel.kt     |   2 +-
 .../isis/client/kroviz/ui/{ => uml}/PumlBuilder.kt |   4 +-
 .../isis/client/kroviz/ui/{ => uml}/UmlDiagram.kt  |   2 +-
 .../client/kroviz/utils/ScalableVectorGraphic.kt   |   2 +-
 .../apache/isis/client/kroviz/utils/UmlUtils.kt    |   2 +-
 .../apache/isis/client/kroviz/utils/XmlHelper.kt   |   2 +-
 .../apache/isis/client/kroviz/IntegrationTest.kt   |   4 +-
 .../client/kroviz/core/event/EventStoreTest.kt     |   2 +-
 .../kroviz/snapshots/ResponseRegressionTest.kt     |   4 +-
 .../isis/client/kroviz/snapshots/TestRequest.kt    |   2 +-
 .../isis/client/kroviz/ui/PumlBuilderTest.kt       |   3 +-
 81 files changed, 867 insertions(+), 241 deletions(-)

diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/App.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/App.kt
index 3162eb9..34a3976 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/App.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/App.kt
@@ -18,7 +18,7 @@
  */
 package org.apache.isis.client.kroviz
 
-import org.apache.isis.client.kroviz.ui.kv.RoApp
+import org.apache.isis.client.kroviz.ui.core.RoApp
 import io.kvision.Application
 import io.kvision.pace.Pace
 import io.kvision.panel.root
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/Session.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/Session.kt
index 58b9bd4..c8f98f4 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/Session.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/Session.kt
@@ -18,7 +18,7 @@
  */
 package org.apache.isis.client.kroviz.core
 
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 /**
  * Keep track of connected server.
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ActionDispatcher.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ActionDispatcher.kt
index 8dd7121..e1fc669 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ActionDispatcher.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ActionDispatcher.kt
@@ -20,8 +20,8 @@ package org.apache.isis.client.kroviz.core.aggregator
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.*
-import org.apache.isis.client.kroviz.ui.kv.ActionPrompt
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.dialog.ActionPrompt
+import org.apache.isis.client.kroviz.ui.core.Constants
 import org.apache.isis.client.kroviz.utils.Point
 import org.apache.isis.client.kroviz.utils.Utils
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/AggregatorWithLayout.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/AggregatorWithLayout.kt
index ec26351..1b1901b 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/AggregatorWithLayout.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/AggregatorWithLayout.kt
@@ -4,7 +4,7 @@ import org.apache.isis.client.kroviz.core.model.DisplayModelWithLayout
 import org.apache.isis.client.kroviz.layout.Layout
 import org.apache.isis.client.kroviz.to.Represention
 import org.apache.isis.client.kroviz.to.TObject
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 
 abstract class AggregatorWithLayout : BaseAggregator() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/BaseAggregator.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/BaseAggregator.kt
index 8815925..7c3b47b 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/BaseAggregator.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/BaseAggregator.kt
@@ -23,7 +23,7 @@ import org.apache.isis.client.kroviz.core.event.RoXmlHttpRequest
 import org.apache.isis.client.kroviz.core.model.DisplayModel
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.TObject
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 
 /**
  * An Aggregator:
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DomainTypesAggregator.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DomainTypesAggregator.kt
index c76554a..2f0f8b4 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DomainTypesAggregator.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DomainTypesAggregator.kt
@@ -21,7 +21,7 @@ package org.apache.isis.client.kroviz.core.aggregator
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.core.model.DiagramDM
 import org.apache.isis.client.kroviz.to.*
-import org.apache.isis.client.kroviz.ui.kv.RoStatusBar
+import org.apache.isis.client.kroviz.ui.core.RoStatusBar
 
 class DomainTypesAggregator(val url: String) : BaseAggregator() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DownloadDispatcher.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DownloadDispatcher.kt
index df70276..48fe1f6 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DownloadDispatcher.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/DownloadDispatcher.kt
@@ -19,7 +19,7 @@
 package org.apache.isis.client.kroviz.core.aggregator
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
-import org.apache.isis.client.kroviz.ui.FileDialog
+import org.apache.isis.client.kroviz.ui.dialog.FileDialog
 
 class DownloadDispatcher(val actionTitle: String) : BaseAggregator() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ErrorDispatcher.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ErrorDispatcher.kt
index 5e1864d..89ccc28 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ErrorDispatcher.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ErrorDispatcher.kt
@@ -22,7 +22,7 @@ import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.core.event.ResourceSpecification
 import org.apache.isis.client.kroviz.to.HttpError
-import org.apache.isis.client.kroviz.ui.ErrorDialog
+import org.apache.isis.client.kroviz.ui.dialog.ErrorDialog
 
 class ErrorDispatcher : BaseAggregator() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ListAggregator.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ListAggregator.kt
index 04dd84f..e7c9363 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ListAggregator.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ListAggregator.kt
@@ -24,7 +24,7 @@ import org.apache.isis.client.kroviz.core.model.ListDM
 import org.apache.isis.client.kroviz.layout.Layout
 import org.apache.isis.client.kroviz.to.*
 import org.apache.isis.client.kroviz.to.bs3.Grid
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 /** sequence of operations:
  * (0) list
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/NavigationDispatcher.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/NavigationDispatcher.kt
index 0d73aa1..cf03840 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/NavigationDispatcher.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/NavigationDispatcher.kt
@@ -20,7 +20,7 @@ package org.apache.isis.client.kroviz.core.aggregator
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.mb.Menubars
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 class NavigationDispatcher() : BaseAggregator() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ObjectAggregator.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ObjectAggregator.kt
index 8791686..0143747 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ObjectAggregator.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/ObjectAggregator.kt
@@ -23,8 +23,8 @@ import org.apache.isis.client.kroviz.core.model.ObjectDM
 import org.apache.isis.client.kroviz.layout.Layout
 import org.apache.isis.client.kroviz.to.*
 import org.apache.isis.client.kroviz.to.bs3.Grid
-import org.apache.isis.client.kroviz.ui.ErrorDialog
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.dialog.ErrorDialog
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 /** sequence of operations:
  * (0) Menu Action              User clicks BasicTypes.String -> handled by ActionDispatcher
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/SvgDispatcher.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/SvgDispatcher.kt
index 9c57c79..0f65e88 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/SvgDispatcher.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/SvgDispatcher.kt
@@ -19,7 +19,7 @@
 package org.apache.isis.client.kroviz.core.aggregator
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
-import org.apache.isis.client.kroviz.ui.kv.SvgPanel
+import org.apache.isis.client.kroviz.ui.panel.SvgPanel
 import org.apache.isis.client.kroviz.utils.DomUtil
 import org.apache.isis.client.kroviz.utils.UUID
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/UndefinedDispatcher.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/UndefinedDispatcher.kt
index afcf993..d2ea778 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/UndefinedDispatcher.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/aggregator/UndefinedDispatcher.kt
@@ -19,7 +19,7 @@
 package org.apache.isis.client.kroviz.core.aggregator
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
-import org.apache.isis.client.kroviz.ui.UndefinedDialog
+import org.apache.isis.client.kroviz.ui.dialog.UndefinedDialog
 
 class UndefinedDispatcher : BaseAggregator() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/EventStore.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/EventStore.kt
index 4e72a2b..31ec377 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/EventStore.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/EventStore.kt
@@ -21,7 +21,7 @@ package org.apache.isis.client.kroviz.core.event
 import org.apache.isis.client.kroviz.core.aggregator.BaseAggregator
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.mb.Menubars
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
 import io.kvision.panel.SimplePanel
 import io.kvision.state.observableListOf
 import org.apache.isis.client.kroviz.core.aggregator.SvgDispatcher
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/LogEntry.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/LogEntry.kt
index 269d626..44046af 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/LogEntry.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/LogEntry.kt
@@ -23,8 +23,8 @@ import kotlinx.serialization.Contextual
 import kotlinx.serialization.Serializable
 import org.apache.isis.client.kroviz.core.aggregator.BaseAggregator
 import org.apache.isis.client.kroviz.to.TransferObject
-import org.apache.isis.client.kroviz.ui.kv.Constants
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.Constants
+import org.apache.isis.client.kroviz.ui.core.UiManager
 import org.apache.isis.client.kroviz.utils.Utils.removeHexCode
 import kotlin.js.Date
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/ResourceSpecification.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/ResourceSpecification.kt
index 5b13cd8..e5eadd5 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/ResourceSpecification.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/ResourceSpecification.kt
@@ -18,7 +18,7 @@
  */
 package org.apache.isis.client.kroviz.core.event
 
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 import org.apache.isis.client.kroviz.utils.Utils
 
 class ResourceSpecification(
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/RoXmlHttpRequest.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/RoXmlHttpRequest.kt
index 34350cc..3065402 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/RoXmlHttpRequest.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/core/event/RoXmlHttpRequest.kt
@@ -24,8 +24,8 @@ import org.apache.isis.client.kroviz.handler.ResponseHandler
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.Method
 import org.apache.isis.client.kroviz.to.TObject
-import org.apache.isis.client.kroviz.ui.kv.Constants
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.Constants
+import org.apache.isis.client.kroviz.ui.core.UiManager
 import org.apache.isis.client.kroviz.utils.Utils
 import org.w3c.xhr.XMLHttpRequest
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/BaseHandler.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/BaseHandler.kt
index 2a8a856..38c1a40 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/BaseHandler.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/BaseHandler.kt
@@ -20,7 +20,7 @@ package org.apache.isis.client.kroviz.handler
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.TransferObject
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 
 /**
  * Handle responses to XmlHttpRequests asynchronously,
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/DomainTypesHandler.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/DomainTypesHandler.kt
index f31cf1e..8e3ca73 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/DomainTypesHandler.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/handler/DomainTypesHandler.kt
@@ -22,11 +22,11 @@ import kotlinx.serialization.json.Json
 import org.apache.isis.client.kroviz.core.aggregator.DomainTypesAggregator
 import org.apache.isis.client.kroviz.to.DomainTypes
 import org.apache.isis.client.kroviz.to.TransferObject
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 class DomainTypesHandler : org.apache.isis.client.kroviz.handler.BaseHandler() {
 
-    
+
     override fun parse(response: String): TransferObject {
         return Json.decodeFromString(DomainTypes.serializer(), response)
     }
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/ColBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/ColBuilder.kt
index 37db5ff..85054c4 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/ColBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/ColBuilder.kt
@@ -20,7 +20,7 @@ package org.apache.isis.client.kroviz.ui.builder
 
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.bs3.Col
-import org.apache.isis.client.kroviz.ui.kv.RoDisplay
+import org.apache.isis.client.kroviz.ui.core.RoDisplay
 import io.kvision.core.*
 import io.kvision.core.FlexWrap
 import io.kvision.panel.*
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/FieldSetBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/FieldSetBuilder.kt
index 14f2462..abfa17a 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/FieldSetBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/FieldSetBuilder.kt
@@ -21,9 +21,9 @@ package org.apache.isis.client.kroviz.ui.builder
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.TypeMapper
 import org.apache.isis.client.kroviz.to.bs3.FieldSet
-import org.apache.isis.client.kroviz.ui.FormItem
-import org.apache.isis.client.kroviz.ui.kv.FormPanelFactory
-import org.apache.isis.client.kroviz.ui.kv.RoDisplay
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.panel.FormPanelFactory
+import org.apache.isis.client.kroviz.ui.core.RoDisplay
 import io.kvision.form.FormPanel
 
 class FieldSetBuilder {
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/LayoutBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/LayoutBuilder.kt
index 313eb97..bcef92f 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/LayoutBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/LayoutBuilder.kt
@@ -20,7 +20,7 @@ package org.apache.isis.client.kroviz.ui.builder
 
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.bs3.Grid
-import org.apache.isis.client.kroviz.ui.kv.RoDisplay
+import org.apache.isis.client.kroviz.ui.core.RoDisplay
 import io.kvision.core.CssSize
 import io.kvision.core.UNIT
 import io.kvision.panel.VPanel
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/RowBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/RowBuilder.kt
index aae7ee0..1ca17ab 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/RowBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/RowBuilder.kt
@@ -20,8 +20,8 @@ package org.apache.isis.client.kroviz.ui.builder
 
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.bs3.Row
-import org.apache.isis.client.kroviz.ui.kv.MenuFactory
-import org.apache.isis.client.kroviz.ui.kv.RoDisplay
+import org.apache.isis.client.kroviz.ui.core.MenuFactory
+import org.apache.isis.client.kroviz.ui.core.RoDisplay
 import io.kvision.core.*
 import io.kvision.core.FlexWrap
 import io.kvision.panel.*
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabBuilder.kt
index b5157ce..f529c31 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabBuilder.kt
@@ -20,7 +20,7 @@ package org.apache.isis.client.kroviz.ui.builder
 
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.bs3.Tab
-import org.apache.isis.client.kroviz.ui.kv.RoDisplay
+import org.apache.isis.client.kroviz.ui.core.RoDisplay
 import io.kvision.core.Component
 import io.kvision.core.CssSize
 import io.kvision.core.UNIT
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabGroupBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabGroupBuilder.kt
index 3eadad5..4c61b12 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabGroupBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/builder/TabGroupBuilder.kt
@@ -20,7 +20,7 @@ package org.apache.isis.client.kroviz.ui.builder
 
 import org.apache.isis.client.kroviz.to.TObject
 import org.apache.isis.client.kroviz.to.bs3.TabGroup
-import org.apache.isis.client.kroviz.ui.kv.RoDisplay
+import org.apache.isis.client.kroviz.ui.core.RoDisplay
 import io.kvision.core.Component
 import io.kvision.core.CssSize
 import io.kvision.core.UNIT
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ChartFactory.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/ChartFactory.kt
similarity index 91%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ChartFactory.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/ChartFactory.kt
index aa01ab2..99fa4c6 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ChartFactory.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/ChartFactory.kt
@@ -16,9 +16,10 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.chart
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
+import org.apache.isis.client.kroviz.ui.panel.EventChart
 
 class ChartFactory {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ChartModel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/ChartModel.kt
similarity index 95%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ChartModel.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/ChartModel.kt
index 006a0e1..50e271a 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ChartModel.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/ChartModel.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.chart
 
 import io.kvision.chart.DataSets
 import io.kvision.core.Color
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventChartModel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/EventChartModel.kt
similarity index 98%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventChartModel.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/EventChartModel.kt
index e9c1f15..5efcbe6 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventChartModel.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/EventChartModel.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.chart
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import io.kvision.chart.DataSets
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SampleChartModel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/SampleChartModel.kt
similarity index 95%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SampleChartModel.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/SampleChartModel.kt
index 8ba7e53..517aa6e 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SampleChartModel.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/chart/SampleChartModel.kt
@@ -16,9 +16,9 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-package org.apache.isis.client.kroviz.ui.samples
+package org.apache.isis.client.kroviz.ui.chart
 
-import org.apache.isis.client.kroviz.ui.kv.ChartModel
+import org.apache.isis.client.kroviz.ui.chart.ChartModel
 import io.kvision.chart.DataSets
 import io.kvision.core.Color
 import io.kvision.i18n.I18n
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ColumnFactory.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/ColumnFactory.kt
similarity index 99%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ColumnFactory.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/ColumnFactory.kt
index 9891c57..3cce9e9 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ColumnFactory.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/ColumnFactory.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.core.model.Exposer
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/Constants.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/Constants.kt
similarity index 96%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/Constants.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/Constants.kt
index e94a8e0..8cb4e8c 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/Constants.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/Constants.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 object Constants {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/Displayable.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/Displayable.kt
similarity index 95%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/Displayable.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/Displayable.kt
index b09af47..c66f228 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/Displayable.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/Displayable.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.core
 
 interface Displayable {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/FormItem.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/FormItem.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/FormItem.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/FormItem.kt
index d9f47c4..f4ec776 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/FormItem.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/FormItem.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.to.Member
 import org.apache.isis.client.kroviz.to.ValueType
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/MenuFactory.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/MenuFactory.kt
similarity index 99%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/MenuFactory.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/MenuFactory.kt
index 99a49a4..a1c0f4c 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/MenuFactory.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/MenuFactory.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.core.event.RoXmlHttpRequest
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoApp.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoApp.kt
similarity index 88%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoApp.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoApp.kt
index bc13bc9..067db26 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoApp.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoApp.kt
@@ -16,18 +16,19 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
+import io.kvision.core.CssSize
+import io.kvision.core.UNIT
 import io.kvision.panel.HPanel
 import io.kvision.panel.SimplePanel
-import io.kvision.utils.perc
 
 object RoApp : SimplePanel() {
     init {
         this.add(RoMenuBar.navbar)
 
         val view = HPanel(classes = setOf("main")) {
-            width = 100.perc
+            width = CssSize(100, UNIT.perc)
         }
         view.add(RoIconBar.panel)
         view.add(RoView.tabPanel)
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoDialog.kt
similarity index 90%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoDialog.kt
index 81c1d75..5861921 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoDialog.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import io.kvision.core.CssSize
 import io.kvision.core.JustifyContent
@@ -29,13 +29,14 @@ import io.kvision.panel.HPanel
 import io.kvision.panel.vPanel
 import io.kvision.utils.perc
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.Command
-import org.apache.isis.client.kroviz.ui.DiagramDialog
-import org.apache.isis.client.kroviz.ui.Displayable
-import org.apache.isis.client.kroviz.ui.FormItem
+import org.apache.isis.client.kroviz.ui.dialog.Command
+import org.apache.isis.client.kroviz.ui.dialog.DiagramDialog
+import org.apache.isis.client.kroviz.ui.panel.FormPanelFactory
+import org.apache.isis.client.kroviz.ui.kv.override.RoWindow
 import org.apache.isis.client.kroviz.utils.Direction
 import org.apache.isis.client.kroviz.utils.IconManager
 import org.apache.isis.client.kroviz.utils.Point
+import io.kvision.html.Link as KvisionHtmlLink
 
 class RoDialog(
         caption: String,
@@ -43,8 +44,9 @@ class RoDialog(
         val command: Command,
         defaultAction: String = "OK",
         widthPerc: Int = 30,
-        heightPerc: Int = 100) :
-        Displayable, RoWindow(caption = caption, closeButton = true) {
+        heightPerc: Int = 100,
+        menu: List<KvisionHtmlLink>? = null) :
+        Displayable, RoWindow(caption = caption, closeButton = true, menu = menu) {
 
     private val okButton = Button(
             text = defaultAction,
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoDisplay.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoDisplay.kt
similarity index 95%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoDisplay.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoDisplay.kt
index 2dc18d5..0774216 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoDisplay.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoDisplay.kt
@@ -16,11 +16,10 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.core.model.ObjectDM
 import org.apache.isis.client.kroviz.to.TObject
-import org.apache.isis.client.kroviz.ui.Displayable
 import org.apache.isis.client.kroviz.ui.builder.LayoutBuilder
 import io.kvision.core.CssSize
 import io.kvision.core.FontStyle
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoIconBar.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoIconBar.kt
similarity index 94%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoIconBar.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoIconBar.kt
index 667dd56..9320245 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoIconBar.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoIconBar.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import kotlinx.browser.document
 import kotlinx.dom.removeClass
@@ -24,7 +24,7 @@ import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.core.event.ResourceSpecification
 import org.apache.isis.client.kroviz.core.model.Exposer
 import org.apache.isis.client.kroviz.to.TObject
-import org.apache.isis.client.kroviz.ui.kv.MenuFactory.buildForTitle
+import org.apache.isis.client.kroviz.ui.core.MenuFactory.buildForTitle
 import org.apache.isis.client.kroviz.utils.IconManager
 import org.apache.isis.client.kroviz.utils.Utils
 import io.kvision.core.CssSize
@@ -44,15 +44,15 @@ object RoIconBar : SimplePanel() {
     init {
         panel.addCssClass("icon-bar")
         panel.title = "Drop objects, factories, or actions here"
-        this.add(createDeleteIcon())
+        add(createDeleteIcon())
         panel.setDropTargetData(Constants.stdMimeType) { id ->
             when {
                 Utils.isUrl(id!!) ->
-                    this.add(createObjectIcon(id)!!)
+                    add(createObjectIcon(id)!!)
                 id.contains(Constants.actionSeparator) ->
-                    this.add(createActionIcon(id))
+                    add(createActionIcon(id))
                 else ->
-                    this.add(createFactoryIcon(id))
+                    add(createFactoryIcon(id))
             }
         }
         hide()
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoMenuBar.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoMenuBar.kt
similarity index 89%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoMenuBar.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoMenuBar.kt
index deff983..c7c4565 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoMenuBar.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoMenuBar.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import io.kvision.core.CssSize
 import io.kvision.core.UNIT
@@ -31,10 +31,15 @@ import io.kvision.panel.vPanel
 import kotlinx.browser.window
 import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.to.mb.Menubars
-import org.apache.isis.client.kroviz.ui.samples.GeoMap
-import org.apache.isis.client.kroviz.ui.samples.SampleChartModel
-import org.apache.isis.client.kroviz.ui.samples.SvgInline
-import org.apache.isis.client.kroviz.ui.samples.SvgMap
+import org.apache.isis.client.kroviz.ui.panel.DropdownSearch
+import org.apache.isis.client.kroviz.ui.dialog.About
+import org.apache.isis.client.kroviz.ui.dialog.LoginPrompt
+import org.apache.isis.client.kroviz.ui.panel.GeoMap
+import org.apache.isis.client.kroviz.ui.chart.SampleChartModel
+import org.apache.isis.client.kroviz.ui.dialog.SvgInline
+import org.apache.isis.client.kroviz.ui.panel.EventChart
+import org.apache.isis.client.kroviz.ui.panel.EventLogTable
+import org.apache.isis.client.kroviz.ui.panel.SvgMap
 import org.apache.isis.client.kroviz.utils.IconManager
 import org.apache.isis.client.kroviz.utils.Point
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoStatusBar.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoStatusBar.kt
similarity index 94%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoStatusBar.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoStatusBar.kt
index c0e79d0..5c46fbf 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoStatusBar.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoStatusBar.kt
@@ -16,14 +16,14 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.core.event.EventState
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.core.model.DiagramDM
-import org.apache.isis.client.kroviz.ui.DiagramDialog
-import org.apache.isis.client.kroviz.ui.NotificationDialog
-import org.apache.isis.client.kroviz.ui.UmlDiagram
+import org.apache.isis.client.kroviz.ui.dialog.DiagramDialog
+import org.apache.isis.client.kroviz.ui.dialog.NotificationDialog
+import org.apache.isis.client.kroviz.ui.uml.UmlDiagram
 import org.apache.isis.client.kroviz.utils.IconManager
 import io.kvision.core.*
 import io.kvision.html.Button
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoTable.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoTable.kt
similarity index 98%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoTable.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoTable.kt
index 71285e6..c28c64d 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoTable.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoTable.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.core.model.Exposer
 import org.apache.isis.client.kroviz.core.model.ListDM
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoView.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoView.kt
similarity index 92%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoView.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoView.kt
index 8152a45..802d1c9 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoView.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/RoView.kt
@@ -16,13 +16,14 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import org.apache.isis.client.kroviz.utils.IconManager
 import io.kvision.core.BsBorder
 import io.kvision.core.Component
 import io.kvision.core.addBsBorder
 import io.kvision.panel.SimplePanel
+import org.apache.isis.client.kroviz.ui.kv.override.RoTabPanel
 
 /**
  * Area between menu bar at the top and the status bar at the bottom.
@@ -63,10 +64,12 @@ object RoView {
     }
 
     fun findActive(): SimplePanel? {
+        console.log("[RV.findActive]")
         val index = tabPanel.activeIndex
         if (index > 0) {
             val tabs = tabPanel.getTabs()
             val tab = tabs.get(index) as SimplePanel
+            console.log(tab)
             return (tab)
         }
         return null
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/UiManager.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/UiManager.kt
similarity index 98%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/UiManager.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/UiManager.kt
index fdb6718..f9f7b81 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/UiManager.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/core/UiManager.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.core
 
 import kotlinx.browser.window
 import org.apache.isis.client.kroviz.core.Session
@@ -82,6 +82,8 @@ object UiManager {
     }
 
     fun closeView(tab: SimplePanel) {
+        console.log("[UM.closeView]")
+        console.log(tab)
         val tt = tab.title
         if (tt != null) {
             EventStore.closeView(tt)
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/About.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/About.kt
similarity index 93%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/About.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/About.kt
index fe79cbc..dd354fe 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/About.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/About.kt
@@ -17,11 +17,11 @@
  * under the License.
  */
 
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.Command
-import org.apache.isis.client.kroviz.ui.FormItem
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 import org.apache.isis.client.kroviz.utils.UUID
 
 class About : Command() {
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ActionPrompt.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/ActionPrompt.kt
similarity index 95%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ActionPrompt.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/ActionPrompt.kt
index 687da2a..26353fa 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/ActionPrompt.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/ActionPrompt.kt
@@ -16,19 +16,19 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.to.Action
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.Parameter
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.Command
-import org.apache.isis.client.kroviz.ui.FormItem
+import org.apache.isis.client.kroviz.ui.core.FormItem
 import org.apache.isis.client.kroviz.utils.Point
 import org.apache.isis.client.kroviz.utils.Utils
 import io.kvision.core.StringPair
 import io.kvision.form.select.SimpleSelect
 import io.kvision.form.text.TextArea
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 
 class ActionPrompt(val action: Action) : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/BrowserWindow.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/BrowserWindow.kt
similarity index 88%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/BrowserWindow.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/BrowserWindow.kt
index 7dce413..cb17990 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/BrowserWindow.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/BrowserWindow.kt
@@ -16,10 +16,11 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 
 class BrowserWindow(val url: String) : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/Command.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/Command.kt
similarity index 96%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/Command.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/Command.kt
index 8f47ab7..a1ec9bb 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/Command.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/Command.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.aggregator.ActionDispatcher
 import org.apache.isis.client.kroviz.core.event.RoXmlHttpRequest
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/DiagramDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/DiagramDialog.kt
similarity index 72%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/DiagramDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/DiagramDialog.kt
index 6428dcf..e419ec9 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/DiagramDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/DiagramDialog.kt
@@ -16,13 +16,17 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
-import org.apache.isis.client.kroviz.core.aggregator.SvgDispatcher
 import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.*
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.MenuFactory
+import org.apache.isis.client.kroviz.ui.core.RoDialog
+import org.apache.isis.client.kroviz.ui.core.UiManager
+import org.apache.isis.client.kroviz.ui.panel.FormPanelFactory
 import org.apache.isis.client.kroviz.utils.*
+import io.kvision.html.Link as KvisionHtmlLink
 
 class DiagramDialog(
         var label: String,
@@ -47,35 +51,29 @@ class DiagramDialog(
                 caption = "Diagram",
                 items = formItems,
                 command = this,
-                defaultAction = "Pin"
+                defaultAction = "Pin",
+                menu = buildMenu()
         )
     }
 
     override fun execute() {
         pin()
- //       dialog.close()
     }
 
     private fun pin() {
-//        val newImage = getDiagram()
-//        val newCallBack = buildNewPanel()
-//        DomUtil.replaceWith(newCallBack, newImage)
-        val logEntry = EventStore.findBy(callBack as UUID)
-        val svgStr = logEntry.getResponse()
-        val panel = SvgPanel()
-        panel.renderSvg(svgStr)
-        UiManager.add("Diagram", panel)
+        val newImage = getDiagram()
+        val newCallBack = buildNewPanel()
+        DomUtil.replaceWith(newCallBack, newImage)
+        dialog.close()
     }
 
     private fun getDiagram(): ScalableVectorGraphic {
         val logEntry = EventStore.findBy(callBack as UUID)
         val svgStr = logEntry.getResponse()
-        console.log("[DiagramDialog.getDiagram]")
-        console.log(svgStr)
         return ScalableVectorGraphic(svgStr)
     }
 
-    private fun buildNewPanel() : UUID {
+    private fun buildNewPanel(): UUID {
         val newUuid = UUID()
         val formItems = mutableListOf<FormItem>()
         val newFi = FormItem("svg", ValueType.SVG_INLINE, callBack = newUuid)
@@ -96,4 +94,16 @@ class DiagramDialog(
         DomUtil.replaceWith(callBack as UUID, svg)
     }
 
+    fun buildMenu(): List<KvisionHtmlLink> {
+        val menu = mutableListOf<KvisionHtmlLink>()
+        val action = MenuFactory.buildActionLink(
+                label = "pin",
+                menuTitle = "pin")
+        action.onClick {
+            pin()
+        }
+        menu.add(action)
+        return menu
+    }
+
 }
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/DownloadDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/DownloadDialog.kt
similarity index 89%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/DownloadDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/DownloadDialog.kt
index 5feb57f..9e38e2a 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/DownloadDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/DownloadDialog.kt
@@ -17,10 +17,11 @@
  * under the License.
  */
 
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 import org.apache.isis.client.kroviz.utils.DomUtil
 
 class DownloadDialog(val fileName:String, val content:String) : Command() {
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/ErrorDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/ErrorDialog.kt
similarity index 92%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/ErrorDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/ErrorDialog.kt
index 85d5418..9ced7b1 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/ErrorDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/ErrorDialog.kt
@@ -16,12 +16,13 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.HttpError
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 
 class ErrorDialog(val logEntry: LogEntry) : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/EventExportDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/EventExportDialog.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/EventExportDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/EventExportDialog.kt
index 5a0ac39..54f5c95 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/EventExportDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/EventExportDialog.kt
@@ -16,16 +16,17 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.event.EventState
 import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.core.event.ReplayEvent
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 import io.kvision.core.StringPair
 import io.kvision.form.select.SimpleSelect
+import org.apache.isis.client.kroviz.ui.core.FormItem
 
 class EventExportDialog() : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/EventLogDetail.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/EventLogDetail.kt
similarity index 90%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/EventLogDetail.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/EventLogDetail.kt
index 97aee27..ca6209f 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/EventLogDetail.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/EventLogDetail.kt
@@ -16,12 +16,14 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.Constants
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.uml.PumlBuilder
+import org.apache.isis.client.kroviz.ui.core.Constants
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 import org.apache.isis.client.kroviz.utils.Utils
 import org.apache.isis.client.kroviz.utils.XmlHelper
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/FileDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/FileDialog.kt
similarity index 91%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/FileDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/FileDialog.kt
index 279df5d..d566d3a 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/FileDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/FileDialog.kt
@@ -16,12 +16,13 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.ResultValue
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 
 class FileDialog(val logEntry: LogEntry) : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/LoginPrompt.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/LoginPrompt.kt
similarity index 92%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/LoginPrompt.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/LoginPrompt.kt
index 427019d..c7d87da 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/LoginPrompt.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/LoginPrompt.kt
@@ -16,15 +16,16 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.Command
-import org.apache.isis.client.kroviz.ui.FormItem
+import org.apache.isis.client.kroviz.ui.core.FormItem
 import org.apache.isis.client.kroviz.utils.Point
 import io.kvision.form.text.Password
 import io.kvision.form.text.Text
+import org.apache.isis.client.kroviz.ui.core.RoDialog
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 class LoginPrompt : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/NotificationDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/NotificationDialog.kt
similarity index 86%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/NotificationDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/NotificationDialog.kt
index 8cfbce3..9ad3793 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/NotificationDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/NotificationDialog.kt
@@ -16,11 +16,12 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
-import org.apache.isis.client.kroviz.ui.kv.RoStatusBar
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
+import org.apache.isis.client.kroviz.ui.core.RoStatusBar
 
 class NotificationDialog(val message: String) : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SvgInline.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/SvgInline.kt
similarity index 91%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SvgInline.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/SvgInline.kt
index 733117c..beafdfe 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SvgInline.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/SvgInline.kt
@@ -17,16 +17,15 @@
  * under the License.
  */
 
-package org.apache.isis.client.kroviz.ui.samples
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.aggregator.SvgDispatcher
 import org.apache.isis.client.kroviz.core.event.RoXmlHttpRequest
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.Method
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.Command
-import org.apache.isis.client.kroviz.ui.FormItem
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 import org.apache.isis.client.kroviz.utils.UUID
 
 class SvgInline : Command() {
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/UndefinedDialog.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/UndefinedDialog.kt
similarity index 92%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/UndefinedDialog.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/UndefinedDialog.kt
index 3f8d9d6..d29c7ab 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/UndefinedDialog.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/dialog/UndefinedDialog.kt
@@ -16,11 +16,12 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.dialog
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.kv.RoDialog
+import org.apache.isis.client.kroviz.ui.core.FormItem
+import org.apache.isis.client.kroviz.ui.core.RoDialog
 
 class UndefinedDialog(val logEntry: LogEntry) : Command() {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoTabPanel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoTabPanel.kt
deleted file mode 100644
index 10f58dd..0000000
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoTabPanel.kt
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- *  Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *        http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- */
-package org.apache.isis.client.kroviz.ui.kv
-
-import io.kvision.core.CssSize
-import io.kvision.core.UNIT
-import io.kvision.panel.SimplePanel
-import io.kvision.panel.TabPanel
-import io.kvision.panel.VPanel
-import io.kvision.utils.perc
-
-class RoTabPanel : TabPanel() {
-
-    init {
-        width = 100.perc
-        marginTop = CssSize(40, UNIT.px)
-    }
-
-    override fun removeTab(index: Int): TabPanel {
-        val tab = getTabs().get(index)
-        RoView.removeTab(tab as SimplePanel)
-        return super.removeTab(index)
-    }
-
-    fun findTab(title: String): Int? {
-        getTabs().forEachIndexed { index, component ->
-            if ((component is VPanel) && (component.title == title)) {
-                return index
-            }
-        }
-        return null
-    }
-
-}
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoManagerBootstrap.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoManagerBootstrap.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoManagerBootstrap.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoManagerBootstrap.kt
index 0ee7389..853e1bc 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoManagerBootstrap.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoManagerBootstrap.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.kv.override
 
 /* (!) copied from kvision KVManagerBootstrap in order to make Dialogs transparent on move */
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoTab.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoTab.kt
new file mode 100644
index 0000000..967b3a9
--- /dev/null
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoTab.kt
@@ -0,0 +1,204 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *        http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.apache.isis.client.kroviz.ui.kv.override
+
+/**
+ * Copied from Tab in order to:
+ * * add IconMenu
+ * * recreate svg from LogEntry on focus
+ */
+
+import com.github.snabbdom.VNode
+import io.kvision.core.Component
+import io.kvision.core.ResString
+import io.kvision.core.onClick
+import io.kvision.html.Icon
+import io.kvision.html.Link
+import io.kvision.html.TAG
+import io.kvision.html.Tag
+import io.kvision.routing.RoutingManager
+import io.kvision.state.ObservableState
+import io.kvision.state.bind
+import io.kvision.utils.obj
+
+/**
+ * The single Tab component inside the TabPanel container.
+ *
+ * @constructor
+ * @param label label of the tab
+ * @param icon icon of the tab
+ * @param image image of the tab
+ * @param closable determines if this tab is closable
+ * @param route JavaScript route to activate given tab
+ * @param init an initializer extension function
+ */
+open class RoTab(
+        label: String? = null, icon: String? = null,
+        image: ResString? = null, closable: Boolean = false, val route: String? = null,
+        init: (RoTab.() -> Unit)? = null
+) : Tag(TAG.LI, classes = setOf("nav-item")) {
+
+    constructor(
+            label: String? = null,
+            child: Component,
+            icon: String? = null,
+            image: ResString? = null,
+            closable: Boolean = false,
+            route: String? = null,
+            init: (RoTab.() -> Unit)? = null
+    ) : this(label, icon, image, closable, route, init) {
+        @Suppress("LeakingThis")
+        add(child)
+    }
+
+    override fun focus() {
+        console.log("[RT.focus]")
+        if (getElementJQuery()?.attr("tabindex") == undefined) getElementJQuery()?.attr("tabindex", "-1")
+        super.focus()
+    }
+
+    /**
+     * The label of the tab.
+     */
+    var label
+        get() = link.label.ifBlank { null }
+        set(value) {
+            link.label = value ?: ""
+        }
+
+    /**
+     * The icon of the tab.
+     */
+    var icon
+        get() = link.icon
+        set(value) {
+            link.icon = value
+        }
+
+    /**
+     * The image of the tab.
+     */
+    var image
+        get() = link.image
+        set(value) {
+            link.image = value
+        }
+
+    /**
+     * Determines if this tab is closable.
+     */
+    var closable
+        get() = closeIcon.visible
+        set(value) {
+            closeIcon.visible = value
+        }
+
+    internal val closeIcon = Icon("fas fa-times").apply {
+        addCssClass("kv-tab-close")
+        visible = closable
+        setEventListener<Icon> {
+            click = { e ->
+                val tabPanel = (this@RoTab.parent as? RoTabPanelNav)?.tabPanel
+                val actIndex = tabPanel?.getTabIndex(this@RoTab) ?: -1
+                e.asDynamic().data = actIndex
+                @Suppress("UnsafeCastFromDynamic")
+                val event = org.w3c.dom.CustomEvent("tabClosing", obj { detail = e; cancelable = true })
+                if (tabPanel?.getElement()?.dispatchEvent(event) != false) {
+                    tabPanel?.removeTab(actIndex)
+                    @Suppress("UnsafeCastFromDynamic")
+                    val closed = org.w3c.dom.CustomEvent("tabClosed", obj { detail = e })
+                    tabPanel?.getElement()?.dispatchEvent(closed)
+                }
+                e.stopPropagation()
+            }
+        }
+    }
+
+    /**
+     * A link component within the tab.
+     */
+    val link = Link(label ?: "", "#", icon, image, classes = setOf("nav-link")).apply {
+        add(this@RoTab.closeIcon)
+    }
+
+    internal val tabId = counter++
+
+    protected val routingHandler = { _: Any ->
+        (this@RoTab.parent as? RoTabPanelNav)?.tabPanel?.activeTab = this
+    }
+
+    init {
+        addPrivate(link)
+        onClick { e ->
+            (this@RoTab.parent as? RoTabPanelNav)?.tabPanel?.activeTab = this
+            e.preventDefault()
+            if (route != null) {
+                RoutingManager.getRouter().kvNavigate(route)
+            }
+        }
+        if (route != null) RoutingManager.getRouter().kvOn(route, routingHandler)
+        @Suppress("LeakingThis")
+        init?.invoke(this)
+    }
+
+    override fun setDragDropData(format: String, data: String) {
+        link.setDragDropData(format, data)
+    }
+
+    override fun childrenVNodes(): Array<VNode> {
+        return (privateChildren).filter { it.visible }.map { it.renderVNode() }.toTypedArray()
+    }
+
+    override fun dispose() {
+        super.dispose()
+        if (route != null) RoutingManager.getRouter().kvOff(routingHandler)
+    }
+
+    companion object {
+        internal var counter = 0
+    }
+}
+
+/**
+ * DSL builder extension function.
+ *
+ * It takes the same parameters as the constructor of the built component.
+ */
+fun RoTabPanel.tab(
+        label: String? = null, icon: String? = null,
+        image: ResString? = null, closable: Boolean = false, route: String? = null,
+        init: (RoTab.() -> Unit)? = null
+): RoTab {
+    val tab = RoTab(label, icon, image, closable, route, init)
+    this.add(tab)
+    return tab
+}
+
+/**
+ * DSL builder extension function for observable state.
+ *
+ * It takes the same parameters as the constructor of the built component.
+ */
+fun <S> RoTabPanel.tab(
+        state: ObservableState<S>,
+        label: String? = null, icon: String? = null,
+        image: ResString? = null, closable: Boolean = false, route: String? = null,
+        init: (RoTab.(S) -> Unit)
+) = tab(label, icon, image, closable, route).bind(state, true, init)
+
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoTabPanel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoTabPanel.kt
new file mode 100644
index 0000000..4183743
--- /dev/null
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoTabPanel.kt
@@ -0,0 +1,437 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *        http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.apache.isis.client.kroviz.ui.kv.override
+
+/**
+ * Copied from TabPanel in order to:
+ * * add IconMenu to (Ro)Tab
+ * * recreate svg from LogEntry on focus
+ */
+
+import com.github.snabbdom.VNode
+import io.kvision.core.*
+import io.kvision.panel.SimplePanel
+import io.kvision.panel.VPanel
+import io.kvision.routing.RoutingManager
+import io.kvision.state.ObservableState
+import io.kvision.state.bind
+import io.kvision.utils.obj
+import io.kvision.utils.perc
+import io.kvision.utils.set
+import org.apache.isis.client.kroviz.ui.core.RoView
+
+/**
+ * Tab position.
+ */
+enum class TabPosition {
+    TOP,
+    LEFT,
+    RIGHT
+}
+
+/**
+ * Left or right tab size.
+ */
+enum class SideTabSize {
+    SIZE_1,
+    SIZE_2,
+    SIZE_3,
+    SIZE_4,
+    SIZE_5,
+    SIZE_6
+}
+
+/**
+ * The container rendering its children as tabs.
+ *
+ * It supports activating children by a JavaScript route.
+ *
+ * @constructor
+ * @param tabPosition tab position
+ * @param sideTabSize side tab size
+ * @param scrollableTabs determines if tabs are scrollable (default: false)
+ * @param draggableTabs determines if tabs are draggable (default: false)
+ * @param classes a set of CSS class names
+ * @param init an initializer extension function
+ */
+@Suppress("LeakingThis")
+open class RoTabPanel(
+        private val tabPosition: TabPosition = TabPosition.TOP,
+        private val sideTabSize: SideTabSize = SideTabSize.SIZE_3,
+        val scrollableTabs: Boolean = false,
+        val draggableTabs: Boolean = false,
+        classes: Set<String> = setOf(),
+        init: (RoTabPanel.() -> Unit)? = null
+) : SimplePanel(classes) {
+
+    private val navClasses = when (tabPosition) {
+        TabPosition.TOP -> if (scrollableTabs) setOf("nav", "nav-tabs", "tabs-top") else setOf("nav", "nav-tabs")
+        TabPosition.LEFT -> setOf("nav", "nav-tabs", "tabs-left", "flex-column")
+        TabPosition.RIGHT -> setOf("nav", "nav-tabs", "tabs-right", "flex-column")
+    }
+
+    internal val tabs = mutableListOf<RoTab>()
+
+    private val nav = RoTabPanelNav(this, navClasses)
+    private val content = RoTabPanelContent(this)
+
+    /**
+     * The index of the active tab.
+     */
+    var activeIndex: Int = -1
+        set(value) {
+            if (value >= -1 && value < tabs.size) {
+                field = value
+                tabs.forEach {
+                    it.link.removeCssClass("active")
+                }
+                tabs.getOrNull(value)?.link?.addCssClass("active")
+                @Suppress("UnsafeCastFromDynamic")
+                this.dispatchEvent("tabChange", obj { detail = obj { data = value } })
+            }
+        }
+
+    /**
+     * The active tab.
+     */
+    var activeTab: RoTab?
+        get() = tabs.getOrNull(activeIndex)
+        set(value) {
+            activeIndex = value?.let { tabs.indexOf(value) } ?: -1
+        }
+
+    init {
+        width = 100.perc
+        marginTop = CssSize(40, UNIT.px)
+        when (tabPosition) {
+            TabPosition.TOP -> {
+                this.addPrivate(nav)
+                this.addPrivate(content)
+            }
+            TabPosition.LEFT -> {
+                this.addSurroundingCssClass("container-fluid")
+                this.addCssClass("row")
+                val sizes = calculateSideClasses()
+                this.addPrivate(WidgetWrapper(nav, setOf(sizes.first, "pl-0", "pr-0")))
+                this.addPrivate(WidgetWrapper(content, setOf(sizes.second, "pl-0", "pr-0")))
+            }
+            TabPosition.RIGHT -> {
+                this.addSurroundingCssClass("container-fluid")
+                this.addCssClass("row")
+                val sizes = calculateSideClasses()
+                this.addPrivate(WidgetWrapper(content, setOf(sizes.second, "pl-0", "pr-0")))
+                this.addPrivate(WidgetWrapper(nav, setOf(sizes.first, "pl-0", "pr-0")))
+            }
+        }
+        init?.invoke(this)
+    }
+
+    private fun calculateSideClasses(): Pair<String, String> {
+        return when (sideTabSize) {
+            SideTabSize.SIZE_1 -> Pair("col-sm-1", "col-sm-11")
+            SideTabSize.SIZE_2 -> Pair("col-sm-2", "col-sm-10")
+            SideTabSize.SIZE_3 -> Pair("col-sm-3", "col-sm-9")
+            SideTabSize.SIZE_4 -> Pair("col-sm-4", "col-sm-8")
+            SideTabSize.SIZE_5 -> Pair("col-sm-5", "col-sm-7")
+            SideTabSize.SIZE_6 -> Pair("col-sm-6", "col-sm-6")
+        }
+    }
+
+    /**
+     * Returns the number of tabs.
+     */
+    open fun getSize(): Int {
+        return tabs.size
+    }
+
+    /**
+     * Returns the list of tabs.
+     */
+    open fun getTabs(): List<RoTab> {
+        return tabs
+    }
+
+    /**
+     * Get the Tab component by index.
+     * @param index the index of a Tab
+     */
+    open fun getTab(index: Int): RoTab? {
+        return tabs.getOrNull(index)
+    }
+
+    /**
+     * Get the index of the given tab.
+     * @param tab a Tab component
+     */
+    open fun getTabIndex(tab: RoTab): Int {
+        return tabs.indexOf(tab)
+    }
+
+    /**
+     * Removes tab at given index.
+     * @param index the index of the tab
+     */
+    open fun removeTab(index: Int): RoTabPanel {
+        val tab = getTabs().get(index)
+        RoView.removeTab(tab as SimplePanel)
+
+        getTab(index)?.let {
+            removeTab(it)
+            refresh()
+        }
+        return this
+    }
+
+    /**
+     * Find the tab which contains the given component.
+     * @param component a component
+     */
+    open fun findTabWithComponent(component: Component): RoTab? {
+        return tabs.find { it.getChildren().contains(component) }
+    }
+
+    /**
+     * Move the tab to a different position.
+     * @param fromIndex source tab index
+     * @param toIndex destination tab index
+     */
+    open fun moveTab(fromIndex: Int, toIndex: Int) {
+        tabs.getOrNull(fromIndex)?.let {
+            tabs.remove(it)
+            tabs.add(toIndex, it)
+            if (activeIndex == fromIndex) {
+                activeIndex = toIndex
+            } else if (activeIndex in (fromIndex + 1)..toIndex) {
+                activeIndex--
+            } else if (activeIndex in toIndex until fromIndex) {
+                activeIndex++
+            }
+            refresh()
+        }
+    }
+
+    /**
+     * Add new Tab component.
+     * @param tab a Tab component
+     * @param position tab position
+     */
+    protected open fun addTab(tab: RoTab, position: Int? = null) {
+        tab.parent = nav
+        if (position == null) {
+            tabs.add(tab)
+        } else {
+            tabs.add(position, tab)
+        }
+        if (tabs.size == 1) {
+            tab.link.addCssClass("active")
+            activeIndex = 0
+        }
+        if (draggableTabs) {
+            tab.setDragDropData("text/plain", tab.tabId.toString())
+            tab.setDropTargetData("text/plain") { data ->
+                val toIdx = getTabIndex(tab)
+                data?.toIntOrNull()?.let { tabId ->
+                    tabs.find { it.tabId == tabId }?.let {
+                        val fromIdx = getTabIndex(it)
+                        moveTab(fromIdx, toIdx)
+                    }
+                }
+            }
+        }
+        if (tab.route != null) {
+            RoutingManager.getRouter().kvResolve()
+        }
+    }
+
+    /**
+     * Add new child component.
+     * @param child a child component
+     * @param position tab position
+     */
+    protected open fun addChild(child: Component, position: Int? = null) {
+        if (child is RoTab) {
+            addTab(child, position)
+        } else {
+            addTab(RoTab("", child), position)
+        }
+    }
+
+    /**
+     * Delete the given Tab component.
+     * @param tab a Tab component
+     */
+    protected open fun removeTab(tab: RoTab) {
+        val index = tabs.indexOf(tab)
+        if (index >= 0) {
+            tabs.remove(tab)
+            tab.parent = null
+            if (activeIndex >= tabs.size) {
+                activeIndex = tabs.size - 1
+            } else if (activeIndex > index) {
+                activeIndex--
+            } else if (activeIndex == index) {
+                activeIndex = activeIndex
+            }
+        }
+    }
+
+    override fun add(child: Component): RoTabPanel {
+        addChild(child)
+        refresh()
+        return this
+    }
+
+    override fun add(position: Int, child: Component): RoTabPanel {
+        addChild(child, position)
+        refresh()
+        return this
+    }
+
+    /**
+     * Creates and adds new tab component.
+     * @param title title of the tab
+     * @param panel child component
+     * @param icon icon of the tab
+     * @param image image of the tab
+     * @param closable determines if this tab is closable
+     * @param route JavaScript route to activate given child
+     * @return current container
+     */
+    open fun addTab(
+            title: String, panel: Component, icon: String? = null,
+            image: ResString? = null, closable: Boolean = false, route: String? = null
+    ): RoTabPanel {
+        addTab(RoTab(title, panel, icon, image, closable, route))
+        refresh()
+        return this
+    }
+
+    override fun addAll(children: List<Component>): RoTabPanel {
+        children.forEach(::addChild)
+        refresh()
+        return this
+    }
+
+    override fun remove(child: Component): RoTabPanel {
+        if (child is RoTab) {
+            removeTab(child)
+            refresh()
+        } else {
+            findTabWithComponent(child)?.let {
+                removeTab(it)
+                refresh()
+            }
+        }
+        return this
+    }
+
+    override fun removeAt(position: Int): RoTabPanel {
+        if (position >= 0 && position < tabs.size) {
+            val tab = tabs.removeAt(position)
+            tab.parent = null
+            if (activeIndex >= tabs.size) {
+                activeIndex = tabs.size - 1
+            } else if (activeIndex > position) {
+                activeIndex--
+            } else if (activeIndex == position) {
+                activeIndex = activeIndex
+            }
+        }
+        return this
+    }
+
+    override fun removeAll(): RoTabPanel {
+        tabs.forEach { removeTab(it) }
+        return this
+    }
+
+    override fun disposeAll(): RoTabPanel {
+        tabs.forEach { it.dispose() }
+        removeAll()
+        return this
+    }
+
+    fun findTab(title: String): Int? {
+        getTabs().forEachIndexed { index, component ->
+            if ((component is VPanel) && (component.title == title)) {
+                return index
+            }
+        }
+        return null
+    }
+
+}
+
+/**
+ * DSL builder extension function.
+ *
+ * It takes the same parameters as the constructor of the built component.
+ */
+fun Container.tabPanel(
+        tabPosition: TabPosition = TabPosition.TOP,
+        sideTabSize: SideTabSize = SideTabSize.SIZE_3,
+        scrollableTabs: Boolean = false,
+        draggableTabs: Boolean = false,
+        classes: Set<String>? = null,
+        className: String? = null,
+        init: (RoTabPanel.() -> Unit)? = null
+): RoTabPanel {
+    val tabPanel = RoTabPanel(tabPosition, sideTabSize, scrollableTabs, draggableTabs, classes ?: className.set, init)
+    this.add(tabPanel)
+    return tabPanel
+}
+
+/**
+ * DSL builder extension function for observable state.
+ *
+ * It takes the same parameters as the constructor of the built component.
+ */
+fun <S> Container.tabPanel(
+        state: ObservableState<S>,
+        tabPosition: TabPosition = TabPosition.TOP,
+        sideTabSize: SideTabSize = SideTabSize.SIZE_3,
+        scrollableTabs: Boolean = false,
+        draggableTabs: Boolean = false,
+        classes: Set<String>? = null,
+        className: String? = null,
+        init: (RoTabPanel.(S) -> Unit)
+) = tabPanel(tabPosition, sideTabSize, scrollableTabs, draggableTabs, classes, className).bind(state, true, init)
+
+
+internal class RoTabPanelNav(internal val tabPanel: RoTabPanel, classes: Set<String>) : SimplePanel(classes) {
+
+    override fun render(): VNode {
+        return render("ul", childrenVNodes())
+    }
+
+    override fun childrenVNodes(): Array<VNode> {
+        return tabPanel.tabs.filter { it.visible }.map { it.renderVNode() }.toTypedArray()
+    }
+
+}
+
+internal class RoTabPanelContent(private val tabPanel: RoTabPanel) : SimplePanel() {
+
+    override fun childrenVNodes(): Array<VNode> {
+        return tabPanel.tabs.getOrNull(tabPanel.activeIndex)?.getChildren()?.map { it.renderVNode() }?.toTypedArray()
+                ?: emptyArray()
+    }
+
+}
+
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoWindow.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoWindow.kt
similarity index 91%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoWindow.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoWindow.kt
index f8d1ba8..5f5d1f1 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/RoWindow.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/override/RoWindow.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.kv.override
 
 /* (!) copied from io.kvision.window.Window in order to make
 * Dialogs transparent on move
@@ -26,7 +26,6 @@ package org.apache.isis.client.kroviz.ui.kv
 import com.github.snabbdom.VNode
 import io.kvision.core.*
 import io.kvision.dropdown.DropDown
-import io.kvision.dropdown.separator
 import io.kvision.html.*
 import io.kvision.modal.CloseIcon
 import io.kvision.panel.SimplePanel
@@ -36,6 +35,7 @@ import io.kvision.window.MaximizeIcon
 import io.kvision.window.MinimizeIcon
 import org.w3c.dom.events.Event
 import org.w3c.dom.events.MouseEvent
+import io.kvision.html.Link as KvisionHtmlLink
 
 internal const val DEFAULT_Z_INDEX = 900
 internal const val WINDOW_HEADER_HEIGHT = 40
@@ -68,6 +68,7 @@ open class RoWindow(
         minimizeButton: Boolean = true,
         icon: String? = null,
         classes: Set<String> = setOf(),
+        menu: List<KvisionHtmlLink>? = null,
         init: (RoWindow.() -> Unit)? = null
 ) :
         SimplePanel(classes + setOf("modal-content", "kv-window")) {
@@ -177,13 +178,14 @@ open class RoWindow(
     }
     private val iconsContainer = SimplePanel(setOf("kv-window-icons-container"))
 
-    /*    private val windowIcon = Icon(icon ?: "").apply {
-            addCssClass("window-icon")
-            visible = (icon != null && icon != "")
-        } */
-    private val windowIcon = DropDown(
+    private val windowIcon = Icon(icon ?: "").apply {
+        addCssClass("window-icon")
+        visible = (icon != null && icon != "")
+    }
+
+    private val windowButton = DropDown(
             text = "",
-            icon = icon,
+            icon = windowIcon.icon,
             style = ButtonStyle.LIGHT).apply {
         marginLeft = CssSize(-16, UNIT.px)
         marginTop = CssSize(-1, UNIT.px)
@@ -203,14 +205,29 @@ open class RoWindow(
         width = contentWidth
         @Suppress("LeakingThis")
         zIndex = ++zIndexCounter
-        amendMenu(windowIcon)
-        header.add(windowIcon)
-        windowIcon.setEventListener<Icon> {
-            click = { _ ->
-                console.log("[RoWindow.windowIcon.click]")
+        if (menu == null) {
+            header.add(windowIcon)
+        } else {
+            val windowButton = DropDown(
+                    text = "",
+                    icon = icon,
+                    style = ButtonStyle.LIGHT).apply {
+                marginLeft = CssSize(-16, UNIT.px)
+                marginTop = CssSize(-1, UNIT.px)
+//                background = Background(color = Color.name(Col.WHITE))
+                addBsBgColor(BsBgColor.TRANSPARENT)
             }
-            mousedown = { e ->
-                e.stopPropagation()
+            menu.forEach { m ->
+                windowButton.add(m)
+            }
+            header.add(windowButton)
+            windowButton.setEventListener<Icon> {
+                click = { _ ->
+                    console.log("[RoWindow.windowButton.click]")
+                }
+                mousedown = { e ->
+                    e.stopPropagation()
+                }
             }
         }
         header.add(captionTag)
@@ -328,7 +345,6 @@ open class RoWindow(
         )
     }
 
-
     private fun checkIsResizable() {
         checkResizablEventHandler()
         if (isResizable) {
@@ -443,22 +459,6 @@ open class RoWindow(
     open fun toggleMinimize() {
     }
 
-    //TODO pass in menu in constructor?
-    fun amendMenu(
-            dd: DropDown) {
-        dd.separator()
-
-//        val saveLink = tObject.links.first()
-        val saveAction = MenuFactory.buildActionLink(
-                label = "save",
-                menuTitle = "save")
-        saveAction.onClick {
-//            RoXmlHttpRequest().invoke(saveLink)
-        }
-        dd.add(saveAction)
-    }
-
-
     companion object {
         internal var counter = 0
         internal var zIndexCounter = DEFAULT_Z_INDEX
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/DropdownSearch.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/DropdownSearch.kt
similarity index 94%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/DropdownSearch.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/DropdownSearch.kt
index 6d14451..a933d42 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/DropdownSearch.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/DropdownSearch.kt
@@ -16,18 +16,16 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.panel
 
-import kotlinx.coroutines.delay
-import kotlinx.serialization.Serializable
 import io.kvision.form.formPanel
 import io.kvision.form.select.AjaxOptions
 import io.kvision.form.select.Select
-import io.kvision.utils.obj
-import io.kvision.utils.px
 import io.kvision.panel.SimplePanel
+import io.kvision.utils.obj
 import io.kvision.utils.pc
-import kotlin.js.Date
+import io.kvision.utils.px
+import kotlinx.serialization.Serializable
 
 @Serializable
 data class Form(
@@ -37,6 +35,7 @@ data class Form(
 
 class DropdownSearch() : SimplePanel() {
     val cachedValues = listOf("1" to "About", "2" to "Base", "3" to "Blog", "4" to "Contact", "5" to "Custom", "6" to "Support", "7" to "Tools")
+
     init {
         this.marginTop = 10.px
         this.marginLeft = 40.px
@@ -47,7 +46,8 @@ class DropdownSearch() : SimplePanel() {
                     options = cachedValues,
                     label = "Dropdown search with in-memory values"
             ).apply {
-                liveSearch = true}
+                liveSearch = true
+            }
             )
             add(Form::ajaxselect, Select(label = "Dropdown search on remote data source").apply {
                 emptyOption = true
@@ -67,4 +67,4 @@ class DropdownSearch() : SimplePanel() {
             })
         }
     }
-}
\ No newline at end of file
+}
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventChart.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventChart.kt
similarity index 96%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventChart.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventChart.kt
index 7a29a99..2865a9a 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventChart.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventChart.kt
@@ -16,13 +16,14 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.panel
 
 import io.kvision.chart.*
 import io.kvision.panel.SimplePanel
 import io.kvision.utils.obj
 import io.kvision.utils.px
 import io.kvision.utils.pc
+import org.apache.isis.client.kroviz.ui.chart.ChartModel
 
 //IMPROVE https://github.com/datavisyn/chartjs-chart-box-and-violin-plot
 class EventChart(model: ChartModel) : SimplePanel() {
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventLogTable.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventLogTable.kt
similarity index 96%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventLogTable.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventLogTable.kt
index da1945a..338c7e2 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventLogTable.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventLogTable.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.panel
 
 import io.kvision.core.*
 import io.kvision.html.Button
@@ -28,7 +28,8 @@ import io.kvision.utils.obj
 import io.kvision.utils.px
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.to.TObject
-import org.apache.isis.client.kroviz.ui.EventLogDetail
+import org.apache.isis.client.kroviz.ui.core.Constants
+import org.apache.isis.client.kroviz.ui.dialog.EventLogDetail
 
 class EventLogTable(val model: List<LogEntry>) : VPanel() {
     val tabulator: Tabulator<LogEntry>
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventLogTableMgr.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventLogTableMgr.kt
similarity index 86%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventLogTableMgr.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventLogTableMgr.kt
index 95cd5d7..46b7401 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/EventLogTableMgr.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/EventLogTableMgr.kt
@@ -17,12 +17,14 @@
  * under the License.
  */
 
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.panel
 
 import org.apache.isis.client.kroviz.core.event.EventStore
-import org.apache.isis.client.kroviz.ui.DiagramDialog
-import org.apache.isis.client.kroviz.ui.EventExportDialog
-import org.apache.isis.client.kroviz.ui.UmlDiagram
+import org.apache.isis.client.kroviz.ui.dialog.DiagramDialog
+import org.apache.isis.client.kroviz.ui.dialog.EventExportDialog
+import org.apache.isis.client.kroviz.ui.uml.UmlDiagram
+import org.apache.isis.client.kroviz.ui.chart.ChartFactory
+import org.apache.isis.client.kroviz.ui.core.UiManager
 import org.apache.isis.client.kroviz.utils.IconManager
 
 class EventLogTableMgr {
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/FormPanelFactory.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/FormPanelFactory.kt
similarity index 98%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/FormPanelFactory.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/FormPanelFactory.kt
index 4c5ef32..9d66407 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/FormPanelFactory.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/FormPanelFactory.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.panel
 
 import io.kvision.core.Component
 import io.kvision.core.Overflow
@@ -42,7 +42,7 @@ import io.kvision.utils.auto
 import io.kvision.utils.perc
 import io.kvision.utils.px
 import org.apache.isis.client.kroviz.to.ValueType
-import org.apache.isis.client.kroviz.ui.FormItem
+import org.apache.isis.client.kroviz.ui.core.FormItem
 import org.apache.isis.client.kroviz.utils.DateHelper
 import org.apache.isis.client.kroviz.utils.UUID
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/GeoMap.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/GeoMap.kt
similarity index 94%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/GeoMap.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/GeoMap.kt
index 64b7564..e92a122 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/GeoMap.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/GeoMap.kt
@@ -16,10 +16,10 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-package org.apache.isis.client.kroviz.ui.samples
+package org.apache.isis.client.kroviz.ui.panel
 
-import org.apache.isis.client.kroviz.ui.kv.Constants
-import org.apache.isis.client.kroviz.ui.kv.RoIconBar
+import org.apache.isis.client.kroviz.ui.core.Constants
+import org.apache.isis.client.kroviz.ui.core.RoIconBar
 import org.apache.isis.client.kroviz.utils.IconManager
 import io.kvision.core.CssSize
 import io.kvision.core.UNIT
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/PlantumlPanel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/PlantumlPanel.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/PlantumlPanel.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/PlantumlPanel.kt
index d54e486..65da659 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/PlantumlPanel.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/PlantumlPanel.kt
@@ -17,7 +17,7 @@
  * under the License.
  */
 
-package org.apache.isis.client.kroviz.ui.samples
+package org.apache.isis.client.kroviz.ui.panel
 
 import org.apache.isis.client.kroviz.utils.UmlUtils
 import io.kvision.core.CssSize
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SvgMap.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/SvgMap.kt
similarity index 99%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SvgMap.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/SvgMap.kt
index 9e53156..29a6f12 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/samples/SvgMap.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/SvgMap.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui.samples
+package org.apache.isis.client.kroviz.ui.panel
 
 import org.apache.isis.client.kroviz.utils.ScalableVectorGraphic
 import io.kvision.maps.*
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/SvgPanel.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/SvgPanel.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/SvgPanel.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/SvgPanel.kt
index a0612be..dd5564c 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/kv/SvgPanel.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/panel/SvgPanel.kt
@@ -17,7 +17,7 @@
  * under the License.
  */
 
-package org.apache.isis.client.kroviz.ui.kv
+package org.apache.isis.client.kroviz.ui.panel
 
 import org.apache.isis.client.kroviz.utils.ScalableVectorGraphic
 import io.kvision.maps.*
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilder.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/uml/PumlBuilder.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilder.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/uml/PumlBuilder.kt
index c619916..c83ae51 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilder.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/uml/PumlBuilder.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.uml
 
 import org.apache.isis.client.kroviz.core.event.EventStore
 import org.apache.isis.client.kroviz.core.event.LogEntry
@@ -27,7 +27,7 @@ import org.apache.isis.client.kroviz.to.DomainType
 import org.apache.isis.client.kroviz.to.HasLinks
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.Relation
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
 
 class PumlBuilder {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/UmlDiagram.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/uml/UmlDiagram.kt
similarity index 97%
rename from incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/UmlDiagram.kt
rename to incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/uml/UmlDiagram.kt
index 9a7b054..d172fa2 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/UmlDiagram.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/ui/uml/UmlDiagram.kt
@@ -16,7 +16,7 @@
  *  specific language governing permissions and limitations
  *  under the License.
  */
-package org.apache.isis.client.kroviz.ui
+package org.apache.isis.client.kroviz.ui.uml
 
 import org.apache.isis.client.kroviz.core.event.LogEntry
 import org.apache.isis.client.kroviz.core.model.DiagramDM
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/ScalableVectorGraphic.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/ScalableVectorGraphic.kt
index 9fd4931..e686613 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/ScalableVectorGraphic.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/ScalableVectorGraphic.kt
@@ -18,7 +18,7 @@
  */
 package org.apache.isis.client.kroviz.utils
 
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 import org.w3c.dom.Document
 import org.w3c.dom.Image
 import org.w3c.dom.parsing.DOMParser
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/UmlUtils.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/UmlUtils.kt
index c0283b5..6c83f37 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/UmlUtils.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/UmlUtils.kt
@@ -23,7 +23,7 @@ import org.apache.isis.client.kroviz.core.event.RoXmlHttpRequest
 import org.apache.isis.client.kroviz.to.Argument
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.Method
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 
 object UmlUtils {
 
diff --git a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/XmlHelper.kt b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/XmlHelper.kt
index 712c778..e22db8c 100644
--- a/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/XmlHelper.kt
+++ b/incubator/clients/kroviz/src/main/kotlin/org/apache/isis/client/kroviz/utils/XmlHelper.kt
@@ -18,7 +18,7 @@
  */
 package org.apache.isis.client.kroviz.utils
 
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 import org.w3c.dom.Document
 import org.w3c.dom.Node
 import org.w3c.dom.asList
diff --git a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/IntegrationTest.kt b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/IntegrationTest.kt
index 77383d5..8e15ff0 100644
--- a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/IntegrationTest.kt
+++ b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/IntegrationTest.kt
@@ -28,8 +28,8 @@ import org.apache.isis.client.kroviz.core.event.ResourceSpecification
 import org.apache.isis.client.kroviz.handler.ResponseHandler
 import org.apache.isis.client.kroviz.snapshots.Response
 import org.apache.isis.client.kroviz.to.Method
-import org.apache.isis.client.kroviz.ui.kv.Constants
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.Constants
+import org.apache.isis.client.kroviz.ui.core.UiManager
 import org.apache.isis.client.kroviz.utils.XmlHelper
 import org.w3c.xhr.XMLHttpRequest
 
diff --git a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/core/event/EventStoreTest.kt b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/core/event/EventStoreTest.kt
index 6a9b46e..ce5c914 100644
--- a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/core/event/EventStoreTest.kt
+++ b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/core/event/EventStoreTest.kt
@@ -23,7 +23,7 @@ import org.apache.isis.client.kroviz.core.aggregator.ListAggregator
 import org.apache.isis.client.kroviz.core.aggregator.ObjectAggregator
 import org.apache.isis.client.kroviz.snapshots.simpleapp1_16_0.*
 import org.apache.isis.client.kroviz.to.Method
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 import org.apache.isis.client.kroviz.utils.XmlHelper
 import io.kvision.panel.VPanel
 import kotlin.test.*
diff --git a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/ResponseRegressionTest.kt b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/ResponseRegressionTest.kt
index 1e36240..ad104b1 100644
--- a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/ResponseRegressionTest.kt
+++ b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/ResponseRegressionTest.kt
@@ -22,10 +22,8 @@ import kotlinx.coroutines.ExperimentalCoroutinesApi
 import org.apache.isis.client.kroviz.snapshots.demo2_0_0.Response2Handler
 import org.apache.isis.client.kroviz.to.Link
 import org.apache.isis.client.kroviz.to.Method
-import org.apache.isis.client.kroviz.ui.kv.UiManager
-import org.w3c.workers.Client
+import org.apache.isis.client.kroviz.ui.core.UiManager
 import kotlin.test.BeforeTest
-import kotlin.test.Test
 import kotlin.test.assertEquals
 import kotlin.test.assertTrue
 
diff --git a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/TestRequest.kt b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/TestRequest.kt
index 513671c..45303f1 100644
--- a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/TestRequest.kt
+++ b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/snapshots/TestRequest.kt
@@ -5,7 +5,7 @@ import kotlinx.coroutines.ExperimentalCoroutinesApi
 import kotlinx.coroutines.await
 import org.apache.isis.client.kroviz.IntegrationTest
 import org.apache.isis.client.kroviz.to.Link
-import org.apache.isis.client.kroviz.ui.kv.Constants
+import org.apache.isis.client.kroviz.ui.core.Constants
 import org.w3c.fetch.Response
 import kotlin.js.Promise
 
diff --git a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilderTest.kt b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilderTest.kt
index 9082886..cce28e2 100644
--- a/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilderTest.kt
+++ b/incubator/clients/kroviz/src/test/kotlin/org/apache/isis/client/kroviz/ui/PumlBuilderTest.kt
@@ -27,7 +27,8 @@ import org.apache.isis.client.kroviz.snapshots.Response
 import org.apache.isis.client.kroviz.snapshots.simpleapp1_16_0.*
 import org.apache.isis.client.kroviz.to.DomainType
 import org.apache.isis.client.kroviz.to.Method
-import org.apache.isis.client.kroviz.ui.kv.UiManager
+import org.apache.isis.client.kroviz.ui.core.UiManager
+import org.apache.isis.client.kroviz.ui.uml.PumlBuilder
 import kotlin.test.*
 
 class PumlBuilderTest {