-
Notifications
You must be signed in to change notification settings - Fork 0
exposing the setView, getView, and listSavedViews api [NOT FOR MERGE YET] #177
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,101 @@ | ||||||||||||||||||||||||||
| /*--------------------------------------------------------------------------------------------- | ||||||||||||||||||||||||||
| * Copyright (c) Bentley Systems, Incorporated. All rights reserved. | ||||||||||||||||||||||||||
| * See LICENSE.md in the project root for license terms and full copyright notice. | ||||||||||||||||||||||||||
| *--------------------------------------------------------------------------------------------*/ | ||||||||||||||||||||||||||
| import type { ViewStateProps } from "@itwin/core-common"; | ||||||||||||||||||||||||||
| import { | ||||||||||||||||||||||||||
| DrawingViewState, | ||||||||||||||||||||||||||
| IModelApp, | ||||||||||||||||||||||||||
| SheetViewState, | ||||||||||||||||||||||||||
| SpatialViewState, | ||||||||||||||||||||||||||
| type ScreenViewport, | ||||||||||||||||||||||||||
| } from "@itwin/core-frontend"; | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| import { applySavedView } from "./applySavedView.js"; | ||||||||||||||||||||||||||
| import type { SavedViewData } from "./SavedView.js"; | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| /** Minimal client interface required for {@link setView} when passing a saved view ID. */ | ||||||||||||||||||||||||||
| export interface ViewOperationsClient { | ||||||||||||||||||||||||||
| getSavedViewDataById: (args: { savedViewId: string }) => Promise<SavedViewData>; | ||||||||||||||||||||||||||
| /** Optional: list all saved views as `{ id, displayName }` pairs for name-based lookup. */ | ||||||||||||||||||||||||||
| listSavedViews?: () => Promise<{ id: string; displayName: string }[]>; | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| let _client: ViewOperationsClient | undefined; | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||
| * Initialize view operations with a client for ID-based {@link setView} calls. | ||||||||||||||||||||||||||
| * This is optional — {@link getActiveView} and {@link setView} with {@link ViewStateProps} | ||||||||||||||||||||||||||
| * work without initialization. | ||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||
| export function initViewOperations(client: ViewOperationsClient): void { | ||||||||||||||||||||||||||
| _client = client; | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| function getActiveViewport(): ScreenViewport | undefined { | ||||||||||||||||||||||||||
| return IModelApp.viewManager.selectedView; | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||
| * Returns the active viewport's current view state as {@link ViewStateProps}. | ||||||||||||||||||||||||||
| * Returns `undefined` if there is no active viewport. | ||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||
| export function getActiveView(): ViewStateProps | undefined { | ||||||||||||||||||||||||||
| return getActiveViewport()?.view.toProps(); | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||
| * Lists all saved views accessible via the client supplied to {@link initViewOperations}. | ||||||||||||||||||||||||||
| * Returns an array of `{ id, displayName }` objects, or an empty array if no client is set. | ||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||
| export async function listSavedViews(): Promise<{ id: string; displayName: string }[]> { | ||||||||||||||||||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I believe See We only need to query the frontend when we want the current state of the viewport, but the saved views are stored in the iModel, which is on the backend. The way it's done now: backend calls frontend -> frontend calls backend -> backend receives backend value
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. There are 2 types of "views" that are used in applications:
Using IModelDb.Views only would result in the first one. |
||||||||||||||||||||||||||
| return _client?.listSavedViews?.() ?? []; | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
Comment on lines
+47
to
+53
|
||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| /** | ||||||||||||||||||||||||||
| * Sets the active viewport's view. | ||||||||||||||||||||||||||
| * - When passed a **saved view ID** (string), fetches the saved view data via the | ||||||||||||||||||||||||||
| * client supplied to {@link initViewOperations} and applies it. | ||||||||||||||||||||||||||
| * - When passed **{@link ViewStateProps}**, constructs a `ViewState` from the props | ||||||||||||||||||||||||||
| * and applies it directly — no client required. | ||||||||||||||||||||||||||
| * @returns `true` on success, `false` on any failure. | ||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||
| export async function setView(viewIdOrProps: string | ViewStateProps): Promise<boolean> { | ||||||||||||||||||||||||||
| const vp = getActiveViewport(); | ||||||||||||||||||||||||||
| if (!vp) | ||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
|
Comment on lines
+63
to
+67
|
||||||||||||||||||||||||||
| if (typeof viewIdOrProps === "string") { | ||||||||||||||||||||||||||
| if (!_client) | ||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| try { | ||||||||||||||||||||||||||
| const savedViewData = await _client.getSavedViewDataById({ savedViewId: viewIdOrProps }); | ||||||||||||||||||||||||||
| await applySavedView(vp.iModel, vp, savedViewData); | ||||||||||||||||||||||||||
| return true; | ||||||||||||||||||||||||||
| } catch { | ||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| try { | ||||||||||||||||||||||||||
| const viewState = createViewStateFromViewStateProps(viewIdOrProps, vp); | ||||||||||||||||||||||||||
| await viewState.load(); | ||||||||||||||||||||||||||
| vp.changeView(viewState); | ||||||||||||||||||||||||||
| return true; | ||||||||||||||||||||||||||
| } catch { | ||||||||||||||||||||||||||
| return false; | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||
| function createViewStateFromViewStateProps( | ||||||||||||||||||||||||||
| props: ViewStateProps, | ||||||||||||||||||||||||||
| vp: ScreenViewport, | ||||||||||||||||||||||||||
| ) { | ||||||||||||||||||||||||||
| const className = props.viewDefinitionProps.classFullName.toLowerCase(); | ||||||||||||||||||||||||||
| if (className.includes("drawing")) | ||||||||||||||||||||||||||
| return DrawingViewState.createFromProps(props, vp.iModel); | ||||||||||||||||||||||||||
| if (className.includes("sheet")) | ||||||||||||||||||||||||||
| return SheetViewState.createFromProps(props, vp.iModel); | ||||||||||||||||||||||||||
|
Comment on lines
+95
to
+99
|
||||||||||||||||||||||||||
| const className = props.viewDefinitionProps.classFullName.toLowerCase(); | |
| if (className.includes("drawing")) | |
| return DrawingViewState.createFromProps(props, vp.iModel); | |
| if (className.includes("sheet")) | |
| return SheetViewState.createFromProps(props, vp.iModel); | |
| const className = props.viewDefinitionProps.classFullName; | |
| if (className === DrawingViewState.classFullName) | |
| return DrawingViewState.createFromProps(props, vp.iModel); | |
| if (className === SheetViewState.classFullName) | |
| return SheetViewState.createFromProps(props, vp.iModel); | |
| if (className === SpatialViewState.classFullName) | |
| return SpatialViewState.createFromProps(props, vp.iModel); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
listSavedViewsreturns{ id, displayName }, but this package consistently usessavedViewId(seeSavedView.savedViewId). This inconsistency forces consumers to special-case this API and increases the chance of mixing up different kinds of ids. Consider returning{ savedViewId, displayName }(e.g.,Pick<SavedView, "savedViewId" | "displayName">[]) and update the JSDoc to match.