Skip to content

Commit

Permalink
ocioview image and PySide6 updates (#1912)
Browse files Browse the repository at this point in the history
* Updates for PySide6 compatibility

Signed-off-by: Michael Dolan <[email protected]>

* Remove QT3D_RENDERER override

Signed-off-by: Michael Dolan <[email protected]>

* Message router name update

Signed-off-by: Michael Dolan <[email protected]>

---------

Signed-off-by: Michael Dolan <[email protected]>
Co-authored-by: Thomas Mansencal <[email protected]>
  • Loading branch information
michdolan and KelSolaar committed Apr 17, 2024
1 parent 67a26e4 commit 813785e
Show file tree
Hide file tree
Showing 16 changed files with 299 additions and 195 deletions.
2 changes: 1 addition & 1 deletion src/apps/ocioview/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
from pathlib import Path

import PyOpenColorIO as ocio
from PySide6 import QtCore, QtGui, QtWidgets, QtOpenGL
from PySide6 import QtCore, QtGui, QtWidgets

import ocioview.log_handlers # Import to initialize logging
from ocioview.main_window import OCIOView
Expand Down
2 changes: 1 addition & 1 deletion src/apps/ocioview/ocioview/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@

# Sizes
ICON_SIZE_ITEM = QtCore.QSize(20, 20)
ICON_SIZE_BUTTON = QtCore.QSize(24, 24)
ICON_SIZE_BUTTON = QtCore.QSize(20, 20)
ICON_SCALE_FACTOR = 1.15

MARGIN_WIDTH = 13 # Pixels
Expand Down
1 change: 1 addition & 0 deletions src/apps/ocioview/ocioview/inspect/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@
# Copyright Contributors to the OpenColorIO Project.

from .code_inspector import CodeInspector
from .curve_inspector import CurveInspector
from .log_inspector import LogInspector
4 changes: 3 additions & 1 deletion src/apps/ocioview/ocioview/inspect/code_inspector.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,9 @@ def __init__(self, parent: Optional[QtCore.QObject] = None):

html_css = HtmlFormatter(style="material").get_style_defs()
# Update line number colors to match palette
html_css = html_css.replace("#263238", palette.color(palette.ColorRole.Base).name())
html_css = html_css.replace(
"#263238", palette.color(palette.ColorRole.Base).name()
)
html_css = html_css.replace(
"#37474F", palette.color(palette.ColorRole.Text).darker(150).name()
)
Expand Down
10 changes: 5 additions & 5 deletions src/apps/ocioview/ocioview/inspect/curve_inspector.py
Original file line number Diff line number Diff line change
Expand Up @@ -249,21 +249,21 @@ def __init__(
# Initialize
self._update_x_samples()
msg_router = MessageRouter.get_instance()
msg_router.cpu_processor_ready.connect(self._on_cpu_processor_ready)
msg_router.processor_ready.connect(self._on_processor_ready)

def showEvent(self, event: QtGui.QShowEvent) -> None:
"""Start listening for processor updates, if visible."""
super().showEvent(event)

msg_router = MessageRouter.get_instance()
msg_router.set_cpu_processor_updates_allowed(True)
msg_router.set_processor_updates_allowed(True)

def hideEvent(self, event: QtGui.QHideEvent) -> None:
"""Stop listening for processor updates, if not visible."""
super().hideEvent(event)

msg_router = MessageRouter.get_instance()
msg_router.set_cpu_processor_updates_allowed(False)
msg_router.set_processor_updates_allowed(False)

def resizeEvent(self, event: QtGui.QResizeEvent) -> None:
"""Re-fit graph on resize, to always be centered."""
Expand Down Expand Up @@ -549,7 +549,7 @@ def _update_curves(self) -> None:
"""
self._update_x_samples()
if self._prev_cpu_proc is not None:
self._on_cpu_processor_ready(self._prev_cpu_proc)
self._on_processor_ready(self._prev_cpu_proc)

def _update_x_samples(self):
"""
Expand Down Expand Up @@ -603,7 +603,7 @@ def _fit(self) -> None:
self.update()

@QtCore.Slot(ocio.CPUProcessor)
def _on_cpu_processor_ready(self, cpu_proc: ocio.CPUProcessor) -> None:
def _on_processor_ready(self, cpu_proc: ocio.CPUProcessor) -> None:
"""
Update curves from sampled OCIO CPU processor.
Expand Down
3 changes: 1 addition & 2 deletions src/apps/ocioview/ocioview/inspect_dock.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,7 @@

from PySide6 import QtCore, QtWidgets

from .inspect.curve_inspector import CurveInspector
from .inspect import LogInspector, CodeInspector
from .inspect import CodeInspector, CurveInspector, LogInspector
from .utils import get_glyph_icon
from .widgets.structure import TabbedDockWidget

Expand Down
4 changes: 3 additions & 1 deletion src/apps/ocioview/ocioview/items/config_item_edit.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,9 @@ def __init__(self, parent: Optional[QtWidgets.QWidget] = None):

if self.__has_transforms__:
self.__has_tabs__ = True
no_tf_color = palette.color(palette.ColorGroup.Disabled, palette.ColorRole.Text)
no_tf_color = palette.color(
palette.ColorGroup.Disabled, palette.ColorRole.Text
)
self._from_ref_icon = get_glyph_icon("mdi6.layers-plus")
self._no_from_ref_icon = get_glyph_icon(
"mdi6.layers-plus", color=no_tf_color
Expand Down
85 changes: 58 additions & 27 deletions src/apps/ocioview/ocioview/message_router.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from typing import Any, Optional
from queue import Empty, SimpleQueue

import numpy as np
import PyOpenColorIO as ocio
from PySide6 import QtCore, QtGui, QtWidgets

Expand All @@ -30,9 +31,10 @@ class MessageRunner(QtCore.QObject):
error_logged = QtCore.Signal(str)
debug_logged = QtCore.Signal(str)

cpu_processor_ready = QtCore.Signal(ocio.CPUProcessor)
config_html_ready = QtCore.Signal(str)
ctf_html_ready = QtCore.Signal(str, ocio.GroupTransform)
image_ready = QtCore.Signal(np.ndarray)
processor_ready = QtCore.Signal(ocio.CPUProcessor)
shader_html_ready = QtCore.Signal(str, ocio.GPUProcessor)

LOOP_INTERVAL = 0.5 # In seconds
Expand Down Expand Up @@ -64,21 +66,23 @@ def __init__(self, parent: Optional[QtCore.QObject] = None):
self._gpu_language = ocio.GPU_LANGUAGE_GLSL_4_0

self._prev_config = None
self._prev_proc = None
self._prev_cpu_proc = None
self._prev_image_array = None

self._cpu_processor_updates_allowed = False
self._config_updates_allowed = False
self._ctf_updates_allowed = False
self._image_updates_allowed = False
self._processor_updates_allowed = False
self._shader_updates_allowed = False

def get_gpu_language(self) -> ocio.GpuLanguage:
return self._gpu_language

def set_gpu_language(self, gpu_language: ocio.GpuLanguage) -> None:
self._gpu_language = gpu_language
if self._shader_updates_allowed and self._prev_proc is not None:
if self._shader_updates_allowed and self._prev_cpu_proc is not None:
# Rebroadcast last processor record
message_queue.put_nowait(self._prev_proc)
message_queue.put_nowait(self._prev_cpu_proc)

def config_updates_allowed(self) -> bool:
return self._config_updates_allowed
Expand All @@ -89,32 +93,41 @@ def set_config_updates_allowed(self, allowed: bool) -> None:
# Rebroadcast last config record
message_queue.put_nowait(self._prev_config)

def cpu_processor_updates_allowed(self) -> bool:
return self._cpu_processor_updates_allowed

def set_cpu_processor_updates_allowed(self, allowed: bool) -> None:
self._cpu_processor_updates_allowed = allowed
if allowed and self._prev_config is not None:
# Rebroadcast last config record
message_queue.put_nowait(self._prev_config)

def ctf_updates_allowed(self) -> bool:
return self._ctf_updates_allowed

def set_ctf_updates_allowed(self, allowed: bool) -> None:
self._ctf_updates_allowed = allowed
if allowed and self._prev_proc is not None:
if allowed and self._prev_cpu_proc is not None:
# Rebroadcast last processor record
message_queue.put_nowait(self._prev_proc)
message_queue.put_nowait(self._prev_cpu_proc)

def image_updates_allowed(self) -> bool:
return self._image_updates_allowed

def set_image_updates_allowed(self, allowed: bool) -> None:
self._image_updates_allowed = allowed
if allowed and self._prev_image_array is not None:
# Rebroadcast last image record
message_queue.put_nowait(self._prev_image_array)

def processor_updates_allowed(self) -> bool:
return self._processor_updates_allowed

def set_processor_updates_allowed(self, allowed: bool) -> None:
self._processor_updates_allowed = allowed
if allowed and self._prev_config is not None:
# Rebroadcast last config record
message_queue.put_nowait(self._prev_config)

def shader_updates_allowed(self) -> bool:
return self._shader_updates_allowed

def set_shader_updates_allowed(self, allowed: bool) -> None:
self._shader_updates_allowed = allowed
if allowed and self._prev_proc is not None:
if allowed and self._prev_cpu_proc is not None:
# Rebroadcast last processor record
message_queue.put_nowait(self._prev_proc)
message_queue.put_nowait(self._prev_cpu_proc)

def is_routing(self) -> bool:
"""Whether runner is routing messages."""
Expand Down Expand Up @@ -144,14 +157,20 @@ def start_routing(self) -> None:

# OCIO processor
elif isinstance(msg_raw, ocio.Processor):
self._prev_proc = msg_raw
self._prev_cpu_proc = msg_raw
if (
self._cpu_processor_updates_allowed
self._processor_updates_allowed
or self._ctf_updates_allowed
or self._shader_updates_allowed
):
self._handle_processor_message(msg_raw)

# Image array
elif isinstance(msg_raw, np.ndarray):
self._prev_image_array = msg_raw
if self._image_updates_allowed:
self._handle_image_message(msg_raw)

# Python or OCIO log record
else:
self._handle_log_message(msg_raw)
Expand All @@ -162,7 +181,7 @@ def _handle_config_message(self, config: ocio.Config) -> None:
"""
Handle OCIO config received in the message queue.
:config: OCIO config instance
:param config: OCIO config instance
"""
try:
config_html_data = config_to_html(config)
Expand All @@ -171,22 +190,22 @@ def _handle_config_message(self, config: ocio.Config) -> None:
# Pass error to log
self._handle_log_message(str(e), force_level=self.LOG_LEVEL_WARNING)

def _handle_processor_message(self, processor: ocio.Processor) -> None:
def _handle_processor_message(self, cpu_proc: ocio.Processor) -> None:
"""
Handle OCIO processor received in the message queue.
:config: OCIO processor instance
:param cpu_proc: OCIO processor instance
"""
try:
if self._cpu_processor_updates_allowed:
self.cpu_processor_ready.emit(processor.getDefaultCPUProcessor())
if self._processor_updates_allowed:
self.processor_ready.emit(cpu_proc.getDefaultCPUProcessor())

if self._ctf_updates_allowed:
ctf_html_data, group_tf = processor_to_ctf_html(processor)
ctf_html_data, group_tf = processor_to_ctf_html(cpu_proc)
self.ctf_html_ready.emit(ctf_html_data, group_tf)

if self._shader_updates_allowed:
gpu_proc = processor.getDefaultGPUProcessor()
gpu_proc = cpu_proc.getDefaultGPUProcessor()
shader_html_data = processor_to_shader_html(
gpu_proc, self._gpu_language
)
Expand All @@ -196,6 +215,18 @@ def _handle_processor_message(self, processor: ocio.Processor) -> None:
# Pass error to log
self._handle_log_message(str(e), force_level=self.LOG_LEVEL_WARNING)

def _handle_image_message(self, image_array: np.ndarray) -> None:
"""
Handle image buffer received in the message queue.
:param image_array: Image array
"""
try:
self.image_ready.emit(image_array)
except Exception as e:
# Pass error to log
self._handle_log_message(str(e), force_level=self.LOG_LEVEL_WARNING)

def _handle_log_message(
self, log_record: str, force_level: Optional[str] = None
) -> None:
Expand Down
10 changes: 10 additions & 0 deletions src/apps/ocioview/ocioview/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -242,3 +242,13 @@ def increase_html_lineno_padding(html: str) -> str:
r"\1\2&nbsp;&nbsp;\3",
html,
)


def float_to_uint8(value: float) -> int:
"""
Convert float value to an 8-bit clamped unsigned integer value.
:param value: Float value
:return: Integer value
"""
return max(0, min(255, int(value * 255)))
1 change: 1 addition & 0 deletions src/apps/ocioview/ocioview/viewer/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,4 @@
# Copyright Contributors to the OpenColorIO Project.

from .image_viewer import ViewerChannels, ImageViewer
from .utils import load_image
Loading

0 comments on commit 813785e

Please sign in to comment.