Repository: OpenAssetIO/OpenAssetIO-MediaCreation
Pull request #114: Add initial `ui` and `uiPolicy` traits
Author: login: feltech
Created: 2025-03-31T16:00:40Z | Merged: 2025-04-09T16:10:14Z

Part of OpenAssetIO/OpenAssetIO#1302.

Add initial tranche of traits that were found to be useful when prototyping UI delegation, and update some existing traits. In particular:

Add traits for sets of images. An image collection could be a manifest, directory, archive file, templated path, etc, containing one or more images. An image sequence specialises image collection with a frame range, implying the images in the collection are ordered. E.g. an image collection with a MIME type of "inode/directory" refers to a directory containing images.

Expand on MIME type usage in LocatableContent trait. In particular, support for multiple MIME types in a single field; and sources of common MIME types.


Diff:
diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml
index 1127b7b..244cd13 100644
--- a/.github/workflows/test.yml
+++ b/.github/workflows/test.yml
@@ -44,7 +44,7 @@ jobs:
           install-prefix: openassetio
 
       - name: Install Traitgen
-        run: python -m pip install openassetio-traitgen==1.0.0a10
+        run: python -m pip install openassetio-traitgen
 
       - name: Configure CMake build
         run: |
@@ -68,7 +68,7 @@ jobs:
       - uses: actions/checkout@v3
 
       - name: Install Traitgen
-        run: python -m pip install openassetio-traitgen==1.0.0a10
+        run: python -m pip install openassetio-traitgen
 
       - name: Configure CMake build
         run: >
@@ -97,7 +97,7 @@ jobs:
       - uses: actions/checkout@v3
 
       - name: Install Traitgen
-        run: python -m pip install openassetio-traitgen==1.0.0a10
+        run: python -m pip install openassetio-traitgen
 
       - name: Set Python Root Dir
         run: echo "Python_ROOT_DIR=$(python -c 'import sys; print(sys.prefix)')" >> $GITHUB_ENV
diff --git a/RELEASE_NOTES.md b/RELEASE_NOTES.md
index df816e6..b513594 100644
--- a/RELEASE_NOTES.md
+++ b/RELEASE_NOTES.md
@@ -1,6 +1,20 @@
 Release Notes
 =============
 
+v1.0.0-alpha.x
+---------------
+
+## New features
+
+- Added first tranche of UI-specific traits for common kinds of UI
+  delegation requests.
+  [OpenAssetIO#1302](https://github.com/OpenAssetIO/OpenAssetIO/issues/1302)
+ 
+- Added better support for file and image collections by expanding
+  allowed values in `LocatableContent.mimeType` and adding a new
+  `ImageCollection` trait and associated specifications.
+  [OpenAssetIO#1302](https://github.com/OpenAssetIO/OpenAssetIO/issues/1302)
+
 v1.0.0-alpha.11
 ---------------
 
diff --git a/pyproject.toml b/pyproject.toml
index 2b658dc..6ce236f 100644
--- a/pyproject.toml
+++ b/pyproject.toml
@@ -4,7 +4,7 @@
 [build-system]
 requires = [
     "setuptools>=65.5.0",
-    "openassetio-traitgen==1.0.0a11"
+    "openassetio-traitgen==1.0.0a12"
 ]
 build-backend = "setuptools.build_meta"
 
diff --git a/traits.yml b/traits.yml
index bcaa6e8..3e408b8 100644
--- a/traits.yml
+++ b/traits.yml
@@ -20,6 +20,12 @@ traits:
           entities.
         usage:
           - relationship
+      UI:
+        description: >
+          The trait set defines qualities of a user interface.
+        usage:
+          - ui
+
   color:
     description: Traits related to chromatic information in entity data.
     members:
@@ -67,9 +73,33 @@ traits:
             description: >
               The MIME type of the data referenced by the location
               property.
-
-
-              See https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/MIME_types/Common_types
+              
+              
+              A single MIME type may be insufficient. For example,
+              `isTemplated` is true and the MIME type may vary depending
+              on the substitution; or LocatableContent is used as a
+              filter predicate where multiple types are supported.
+              
+              
+              Multiple MIME types can be represented in two ways.
+              Firstly, a wildcard may be used in place of the subtype,
+              e.g. "image/*". Secondly, multiple MIME types may be
+              separated with a comma, e.g. "image/jpeg,image/png".
+              
+
+              Common references for MIME types are the IANA standard:
+              https://www.iana.org/assignments/media-types/media-types.xhtml
+              and the XDG standard (which adds e.g. "inode/directory"):
+              https://specifications.freedesktop.org/shared-mime-info-spec/latest/index.html
+              
+              
+              In addition There are several other non-standard MIME
+              types in use in the media creation industry. For example,
+              
+              
+              - "application/x-nuke" for Nuke scripts.             
+              - "application/vnd.aswf.opentimelineio" for OpenTimelineIO
+                ".otio" files.
           isTemplated:
             type: boolean
             description: >
@@ -328,6 +358,12 @@ traits:
           traits for any entity that holds two-dimensional data.
         usage:
           - entity
+      ImageCollection:
+        description: >
+          A family trait for any entity that is not an image itself but
+          is a collection of one or more images.
+        usage:
+          - entity
       PixelBased:
         description: >
           Entity data is encoded in a pixel grid of two dimensions.
@@ -587,6 +623,106 @@ traits:
         description: >
           Audio that is encoded in a series of discrete time samples,
           for some number of channels.
+
+  ui:
+    description: Traits related to UI delegation
+    members:
+      EntityProvider:
+        description: >
+          State updates from the UI element should include one or more
+          entity references.
+        usage:
+          - ui
+      MetadataProvider:
+        description: >
+          State updates from the UI element should include one or more
+          traits, with all appropriate properties filled.
+        usage:
+          - ui
+      EntityInfo:
+        description: >
+          The UI element should display relevant information about one
+          or more entities.
+          
+          
+          When choosing which information to display, take into account
+          
+          
+          - Context locale (e.g. any application-specific traits).
+          - Access mode (e.g. read vs. write).
+          - Available area (e.g. if Inline trait is also imbued).
+        usage:
+          - ui
+      Browser:
+        description: >
+          The UI element supports choosing a subset of resources from a
+          set of candidate resources.
+        usage:
+          - ui
+      Singular:
+        description: >
+          The UI element is associated with a single entity.
+        usage:
+          - ui
+      SingleUse:
+        description: >
+          The first state update from the UI element will be used by the
+          host and all subsequent updates will be ignored. The host may
+          destroy the UI element after this initial update.
+        usage:
+          - ui
+      InPlace:
+        description: >
+          The initial state provided to the UI delegate includes a 
+          container UI element that should be mutated by the delegate.
+        usage:
+          - ui
+      Detached:
+        description: >
+          A new UI element should be emitted in the state object, not
+          yet attached to the UI hierarchy. The host is responsible for
+          attaching the UI element.
+        usage:
+          - ui
+      Inline:
+        description: >
+          The UI element will be placed alongside other elements in a
+          layout of related elements. The UI element should be simple
+          and compact, assuming limited available screen space.
+        usage:
+          - ui
+      Tabbed:
+        description: >
+          The UI element should be a new tab in a tabbed panel.
+        usage:
+          - ui
+  uiPolicy:
+    description: Policy traits related to UI delegation
+    members:
+      Managed:
+        description: >
+          A trait indicating that a UI element can be delegated if it
+          matches the supplied traits, taking into account context and
+          access mode.
+        usage:
+          - uiPolicy
+        properties:
+          exclusive:
+            type: boolean
+            description: >
+              Determines if the manager exclusively handles data matching
+              the supplied trait set.
+
+
+              If True, then standard host controls should be disabled
+              in favour of manager delegated UI. For example, file system
+              browsers when determining where to load/save data.
+
+
+              If False, then standard host controls can be presented in
+              addition to any custom manager UI.
+
+
 specifications:
   audio:
     description: >
@@ -769,6 +905,39 @@ specifications:
             name: PixelBased
           - namespace: content
             name: LocatableContent
+      BitmapImageResourceCollection:
+        description: >
+          An entity that holds a collection of bitmap image resources
+          in some external resource.
+        usage:
+          - entity
+        traitSet:
+          - namespace: usage
+            name: Entity
+          - namespace: twoDimensional
+            name: ImageCollection
+          - namespace: twoDimensional
+            name: PixelBased
+          - namespace: content
+            name: LocatableContent
+      BitmapImageResourceSequence:
+        description: >
+          An entity that holds a collection of image resources, where
+          those image resources are ordered into a bounded list of 
+          frames.
+        usage:
+          - entity
+        traitSet:
+          - namespace: usage
+            name: Entity
+          - namespace: twoDimensional
+            name: ImageCollection
+          - namespace: twoDimensional
+            name: PixelBased
+          - namespace: timeDomain
+            name: FrameRanged
+          - namespace: content
+            name: LocatableContent
       PlanarBitmapImageResource:
         description: >
           Any entity that holds two-dimensional data as a pixel grid


Reviews:
user: login: hutchinson
state: APPROVED
author_association: NONE
submitted_at: 2025-04-01T10:28:12Z
user: login: feltech
state: COMMENTED
author_association: MEMBER
submitted_at: 2025-04-01T11:24:03Z
user: login: feltech
state: COMMENTED
author_association: MEMBER
submitted_at: 2025-04-01T11:24:14Z
user: login: hutchinson
state: COMMENTED
author_association: NONE
submitted_at: 2025-04-08T09:17:46Z
user: login: feltech
state: COMMENTED
author_association: MEMBER
submitted_at: 2025-04-08T10:38:10Z
user: login: hutchinson
state: APPROVED
author_association: NONE
submitted_at: 2025-04-09T09:58:52Z

Review comments:
diff_hunk: @@ -587,6 +623,106 @@ traits:
         description: >
           Audio that is encoded in a series of discrete time samples,
           for some number of channels.
+
+  ui:
+    description: Traits related to UI delegation
+    members:
+      EntityProvider:
+        description: >
+          State updates from the UI element should include one or more
+          entity references.
+        usage:
+          - ui
+      MetadataProvider:
+        description: >
+          State updates from the UI element should include one or more
+          traits, with all appropriate properties filled.
+        usage:
+          - ui
+      EntityInfo:
+        description: >
+          The UI element should display relevant information about one
+          or more entities.
+          
+          
+          When choosing which information to display, take into account
+          
+          
+          - Context locale (e.g. any application-specific traits).
+          - Access mode (e.g. read vs. write).
+          - Available area (e.g. if Inline trait is also imbued).
+        usage:
+          - ui
+      Browser:
+        description: >
+          The UI element supports choosing a subset of resources from a
+          set of candidate resources.
+        usage:
+          - ui
+      Singular:
+        description: >
+          The UI element is associated with a single entity.
+        usage:
+          - ui
+      OneShot:
+        description: >
+          The first state update from the UI element will be used by the
+          host and all subsequent updates will be ignored. The host may
+          destroy the UI element after this initial update.
+        usage:
+          - ui
path: traits.yml
user: login: feltech
body: [question] I'm rethinking the name here.  "OneShot" could be confusing in a media creation context, where "shot" has a specific meaning :thinking: 

* SingleUse
* OneOff
* ...?
created_at: 2025-04-01T11:24:03Z
author_association: MEMBER
diff_hunk: @@ -587,6 +623,106 @@ traits:
         description: >
           Audio that is encoded in a series of discrete time samples,
           for some number of channels.
+
+  ui:
+    description: Traits related to UI delegation
+    members:
+      EntityProvider:
+        description: >
+          State updates from the UI element should include one or more
+          entity references.
+        usage:
+          - ui
+      MetadataProvider:
+        description: >
+          State updates from the UI element should include one or more
+          traits, with all appropriate properties filled.
+        usage:
+          - ui
+      EntityInfo:
+        description: >
+          The UI element should display relevant information about one
+          or more entities.
+          
+          
+          When choosing which information to display, take into account
+          
+          
+          - Context locale (e.g. any application-specific traits).
+          - Access mode (e.g. read vs. write).
+          - Available area (e.g. if Inline trait is also imbued).
+        usage:
+          - ui
+      Browser:
+        description: >
+          The UI element supports choosing a subset of resources from a
+          set of candidate resources.
+        usage:
+          - ui
+      Singular:
+        description: >
+          The UI element is associated with a single entity.
+        usage:
+          - ui
+      OneShot:
+        description: >
+          The first state update from the UI element will be used by the
+          host and all subsequent updates will be ignored. The host may
+          destroy the UI element after this initial update.
+        usage:
+          - ui
path: traits.yml
user: login: feltech
body: @hutchinson any ideas?
created_at: 2025-04-01T11:24:14Z
author_association: MEMBER
diff_hunk: @@ -587,6 +623,106 @@ traits:
         description: >
           Audio that is encoded in a series of discrete time samples,
           for some number of channels.
+
+  ui:
+    description: Traits related to UI delegation
+    members:
+      EntityProvider:
+        description: >
+          State updates from the UI element should include one or more
+          entity references.
+        usage:
+          - ui
+      MetadataProvider:
+        description: >
+          State updates from the UI element should include one or more
+          traits, with all appropriate properties filled.
+        usage:
+          - ui
+      EntityInfo:
+        description: >
+          The UI element should display relevant information about one
+          or more entities.
+          
+          
+          When choosing which information to display, take into account
+          
+          
+          - Context locale (e.g. any application-specific traits).
+          - Access mode (e.g. read vs. write).
+          - Available area (e.g. if Inline trait is also imbued).
+        usage:
+          - ui
+      Browser:
+        description: >
+          The UI element supports choosing a subset of resources from a
+          set of candidate resources.
+        usage:
+          - ui
+      Singular:
+        description: >
+          The UI element is associated with a single entity.
+        usage:
+          - ui
+      OneShot:
+        description: >
+          The first state update from the UI element will be used by the
+          host and all subsequent updates will be ignored. The host may
+          destroy the UI element after this initial update.
+        usage:
+          - ui
path: traits.yml
user: login: hutchinson
body: Good point here @feltech . Mulling through ideas, `Constant` or `ReadOnly` seem somewhat misleading as that describes what their ultimate behaviour would appear to the user.... `OneTime`/`SingleUse`/`OneOff` (any of those feel right)
created_at: 2025-04-08T09:17:46Z
author_association: NONE
diff_hunk: @@ -587,6 +623,106 @@ traits:
         description: >
           Audio that is encoded in a series of discrete time samples,
           for some number of channels.
+
+  ui:
+    description: Traits related to UI delegation
+    members:
+      EntityProvider:
+        description: >
+          State updates from the UI element should include one or more
+          entity references.
+        usage:
+          - ui
+      MetadataProvider:
+        description: >
+          State updates from the UI element should include one or more
+          traits, with all appropriate properties filled.
+        usage:
+          - ui
+      EntityInfo:
+        description: >
+          The UI element should display relevant information about one
+          or more entities.
+          
+          
+          When choosing which information to display, take into account
+          
+          
+          - Context locale (e.g. any application-specific traits).
+          - Access mode (e.g. read vs. write).
+          - Available area (e.g. if Inline trait is also imbued).
+        usage:
+          - ui
+      Browser:
+        description: >
+          The UI element supports choosing a subset of resources from a
+          set of candidate resources.
+        usage:
+          - ui
+      Singular:
+        description: >
+          The UI element is associated with a single entity.
+        usage:
+          - ui
+      OneShot:
+        description: >
+          The first state update from the UI element will be used by the
+          host and all subsequent updates will be ignored. The host may
+          destroy the UI element after this initial update.
+        usage:
+          - ui
path: traits.yml
user: login: feltech
body: Renamed to SingleUse in 20b6854e
created_at: 2025-04-08T10:38:10Z
author_association: MEMBER

PR comments:
user: login: feltech
created_at: 2025-04-01T11:19:45Z
body: This PR requires OpenAssetIO-TraitGen to be released with support for `ui` as an allowed `usage` - i.e. https://github.com/OpenAssetIO/OpenAssetIO-TraitGen/pull/104
author_association: MEMBER
user: login: feltech
created_at: 2025-04-08T10:38:56Z
body: @hutchinson Added a few fixup commits with minor changes
author_association: MEMBER