From b184c643961e3a0361835268b66aa5b440460c72 Mon Sep 17 00:00:00 2001 From: splidje Date: Tue, 19 May 2026 16:17:56 +0100 Subject: [PATCH 1/2] [opencue_requires_gpu] (it rhymes) Added checkbox to write node `requires_gpu` as a shortcut to setting the OpenCue publish attribute, so "Render On Farm" button picks it up. --- client/ayon_nuke/api/lib.py | 33 ++++++++++++++++++++++++++++++++ client/ayon_nuke/api/pipeline.py | 4 ++++ client/ayon_nuke/api/plugin.py | 10 ++++++++++ 3 files changed, 47 insertions(+) diff --git a/client/ayon_nuke/api/lib.py b/client/ayon_nuke/api/lib.py index f20d0d57aa..2bf13f7d71 100644 --- a/client/ayon_nuke/api/lib.py +++ b/client/ayon_nuke/api/lib.py @@ -48,6 +48,7 @@ from ayon_core.pipeline.colorspace import ( get_current_context_imageio_config_preset ) +from ayon_core.pipeline.create import CreateContext from ayon_core.resources import get_ayon_icon_filepath from .gizmo_menu import GizmoMenu @@ -1293,6 +1294,11 @@ def create_write_node( # adding clear rendered button add_button_clear_rendered(GN) + if data.get("render_on_farm", False): + requires_gpu_knob = nuke.Boolean_Knob("requires_gpu", "Requires GPU") + GN.addKnob(requires_gpu_knob) + requires_gpu_knob.setFlag(nuke.STARTLINE) + # set tile color tile_color = next( iter( @@ -1311,6 +1317,33 @@ def create_write_node( return GN +def group_node_knob_changed(): + requires_gpu_knob = nuke.thisKnob() + if requires_gpu_knob.name() != "requires_gpu": + return + + instance_id = get_node_data(nuke.thisNode(), INSTANCE_DATA_KNOB).get("instance_id") + if not instance_id: + return + + with nuke.Root(): + create_context = CreateContext(registered_host()) + instance = create_context.instances_by_id.get(instance_id) + if not instance: + return + + collect_opencue_layer_args = instance.publish_attributes.get("CollectOpenCueLayerArgs") + if not collect_opencue_layer_args: + return + + requires_gpu = requires_gpu_knob.value() + if collect_opencue_layer_args.get("requires_gpu") == requires_gpu: + return + + collect_opencue_layer_args["requires_gpu"] = requires_gpu + create_context.save_changes() + + def set_node_knobs_from_settings(node, knob_settings, **kwargs): """Overriding knob values from settings diff --git a/client/ayon_nuke/api/pipeline.py b/client/ayon_nuke/api/pipeline.py index dec42e71de..714024363d 100644 --- a/client/ayon_nuke/api/pipeline.py +++ b/client/ayon_nuke/api/pipeline.py @@ -58,6 +58,7 @@ dirmap_file_name_filter, add_scripts_menu, add_scripts_gizmo, + group_node_knob_changed, get_node_data, set_node_data, MENU_LABEL, @@ -196,6 +197,9 @@ def add_nuke_callbacks(project_settings: dict = None): # Add dirmap for file paths. nuke.addFilenameFilter(dirmap_file_name_filter) + # add callback for opencue requires gpu knob + nuke.addKnobChanged(group_node_knob_changed, nodeClass="Group") + log.info("Added Nuke callbacks ...") diff --git a/client/ayon_nuke/api/plugin.py b/client/ayon_nuke/api/plugin.py index c15b2ad88d..9e2ff88d68 100644 --- a/client/ayon_nuke/api/plugin.py +++ b/client/ayon_nuke/api/plugin.py @@ -405,6 +405,16 @@ def update_instances(self, update_list): # ensure was not deleted by super() if self.create_context.get_instance_by_id(created_inst.id): self._update_write_node_filepath(created_inst, changes) + requires_gpu = ( + "publish_attributes" in (changes.changed_keys - changes.removed_keys) + and changes.new_value.get( + "publish_attributes", {} + ).get("CollectOpenCueLayerArgs", {}).get("requires_gpu") + ) + # Approach to avoiding the infinite loop of this bi-directional + # relationship is just to only set if different. + if isinstance(requires_gpu, bool) and created_inst.transient_data["node"]["requires_gpu"].value() != requires_gpu: + created_inst.transient_data["node"]["requires_gpu"].setValue(requires_gpu) def _update_write_node_filepath(self, created_inst, changes): """Update instance node on context changes. From 408f2de24c66c91454a12daaa6b3eb69767e0362 Mon Sep 17 00:00:00 2001 From: splidje Date: Wed, 27 May 2026 12:47:20 +0100 Subject: [PATCH 2/2] [opencue_requires_gpu] more robust. handles the "requires_gpu" knob missing from the write node. --- client/ayon_nuke/api/plugin.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/client/ayon_nuke/api/plugin.py b/client/ayon_nuke/api/plugin.py index 9e2ff88d68..2337e05cb5 100644 --- a/client/ayon_nuke/api/plugin.py +++ b/client/ayon_nuke/api/plugin.py @@ -413,8 +413,9 @@ def update_instances(self, update_list): ) # Approach to avoiding the infinite loop of this bi-directional # relationship is just to only set if different. - if isinstance(requires_gpu, bool) and created_inst.transient_data["node"]["requires_gpu"].value() != requires_gpu: - created_inst.transient_data["node"]["requires_gpu"].setValue(requires_gpu) + requires_gpu_knob = created_inst.transient_data["node"].knob("requires_gpu") + if isinstance(requires_gpu, bool) and requires_gpu_knob and requires_gpu_knob.value() != requires_gpu: + requires_gpu_knob.setValue(requires_gpu) def _update_write_node_filepath(self, created_inst, changes): """Update instance node on context changes.