import type { Class_DrawingArea } from './DrawingArea'; import type { Type_JSON } from './Utils'; export declare const MASTER_VIEW_ID = "sankey_maitre"; /** * Entrée d'une vue OSP telle que stockée dans `views_dict`. Une vue porte un snapshot * gzip de sa DA (`json`) plus le concept unifié vue ⊕ viewtag : * - `tag_selection` : sélection de visibilité { [view_tagg_id]: selected_label_id } ; * - `is_light` : vue « light » (pas d'override géométrie propre, réutilise le maître) ; * - `generated_from_group_id` : id du groupe de view tags dont la vue est auto-générée ; * - `labels` : sa#396 — LABELS DE VUES, étiquettes libres posées par l'auteur pour * SÉLECTIONNER des vues (publication, constructeur de sites). À ne JAMAIS confondre * avec les view tags (`viewTags` / tag_selection ci-dessus), qui sont la dimension de * GÉNÉRATION des vues par combinaison : un label n'a aucun effet sur la génération. */ export type Type_ViewEntry = { name: string; json: Uint8Array; tag_selection?: { [view_tagg_id: string]: string; }; is_light?: boolean; generated_from_group_id?: string; labels?: string[]; }; /** * Surface minimale (état de vues, en lecture) dont dépend la logique pure. Une interface * étroite plutôt que la classe `ApplicationDataOSP` entière : le service est ainsi testable * avec un mock léger, sans construire une app réelle ni tirer d3/chakra. */ export interface ViewsQueryHost { readonly views_dict: { [id: string]: Type_ViewEntry; }; readonly views_order: string[]; readonly current_view_id: string; readonly master_view_name: string; readonly show_master_in_views: boolean; readonly master_drawing_area: Class_DrawingArea | undefined; readonly drawing_area: Class_DrawingArea; readonly publish_view_label_filter?: string | null; } /** * Logique PURE de vues (#244) : résolution d'une sélection vers un id de vue, lecture des * champs unifiés, requêtes de navigation et manipulation de l'ordre. Aucun effet de bord sur * la DA, aucune dépendance runtime OS → testable en isolation. `ViewsManager` la compose et * y ajoute le cluster switch/persistance (qui, lui, opère la DA). */ export declare class ViewsQuery { protected readonly host: ViewsQueryHost; constructor(host: ViewsQueryHost); /** * Résout une valeur de sélection (nom OU id d'une vue) vers un id de vue. Fusion vue ⊕ * viewtag : une vue se sélectionne par identité, indifféremment de son type (light/heavy), * comme le sélecteur de vue de la topbar. Ordre : id exact dans `views`, puis nom de vue, * puis maître (id réservé `MASTER_VIEW_ID` ou son libellé `master_view_name`). * `null` si rien ne correspond. */ resolveViewIdFromSelection(selection: string): string | null; /** * Résout un `view_tag_selection` de publication `{ groupe : tag }` (id OU nom) vers l'id * d'une VRAIE vue (heavy) si l'un des couples (groupe, tag) en désigne une. Deux stratégies : * 1) id déterministe des vues générées/promues depuis un groupe de view tags : `vt____`. * 2) fallback : n'importe quelle vue heavy dont la `tag_selection` contient (group.id → tag.id). * Ne renvoie qu'une vue non-light. `null` si aucune vue heavy ne correspond. */ resolveHeavyViewIdFromViewTagSelection(selection: Record): string | null; /** * Lit les champs du concept unifié (tag_selection / is_light / generated_from_group_id) * depuis le JSON d'une vue et les pose sur l'entrée `views` correspondante. */ parseViewExtraFields(view_id: string, view_json: Type_JSON): void; /** Tous les labels utilisés dans le document (ordre de première apparition, dédoublonnés). */ get all_view_labels(): string[]; /** Ids des vues portant ce label, dans l'ordre des vues. Vide si aucun. */ viewIdsWithLabel(label: string): string[]; /** Multi-vues actif : au moins une vue est enregistrée (le maître ne compte pas). */ get has_views(): boolean; /** * Vue courante = maître (identité LOGIQUE, pas l'id du Sankey de la DA : une vue light * réutilise la DA maître mais n'EST pas le maître). */ get is_view_master(): boolean; /** Vue courante = vue light (visibilité seule, géométrie héritée du maître). */ get is_current_view_light(): boolean; /** * Ordre de navigation (flèches Préc./Suiv. + sélecteur) : le maître y figure en tête * UNIQUEMENT si show_master_in_views est actif (sinon atteignable via setCurrentViewToMaster). * sa#397 — si la page publiée impose un label de vue (publish_view_label_filter), l'ordre est * RESTREINT aux vues portant ce label (le maître, qui n'est pas une vue labellisable, est * exclu). Garde-fou : un filtre qui ne matche plus rien est ignoré (jamais de sélecteur vide). */ get views_navigation_order(): string[]; get has_master_sankey(): boolean; get master_view(): Class_DrawingArea | undefined; get has_view_before(): boolean; get has_view_after(): boolean; /** Sources de mise en page disponibles (maître + vues nommées), pour les sélecteurs UI. */ get layout_view_sources(): Array<{ id: string; name: string; }>; /** * Pousse (ou re-pousse) un id en fin d'ordre. Dédoublonne d'abord : un id déjà présent * est retiré puis remis en queue (les doublons cassent la navigation). */ pushViewIdInViewOrder(id: string): void; /** Remonte une vue d'un cran dans l'ordre (le maître, position 0, est immuable). */ moveViewUpInOrder(id: string): void; /** Descend une vue d'un cran dans l'ordre. */ moveViewDownInOrder(id: string): void; }