Last active
May 10, 2024 12:50
-
-
Save paulwinex/c3eebeb11f1bbe2a55110fcbfe3c8ab5 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import hou | |
class Connector: | |
container_node_type = "" | |
input_node_type = "" | |
input_connector_name = "" | |
def __init__(self, out_node): | |
self.out_node = out_node | |
def get_input_node(self): | |
container = self.out_node.parent() | |
input_node = next((n for n in container.allSubChildren() if n.type().name() == self.input_node_type), None) | |
if not input_node: | |
raise Exception("Output node not Found") | |
return input_node | |
def get_input_index(self): | |
output_node_input_index = self.get_input_node().inputIndex(self.input_connector_name) | |
if output_node_input_index < 0: | |
output_node_input_index = 0 | |
print(f'Wrong input name "{self.input_node_type}": {self.input_connector_name}') | |
return output_node_input_index | |
def is_already_connected(self, input_node): | |
if input_node in self.out_node.outputs(): | |
return input_node | |
def get_output_index(self): | |
input_node = self.get_input_node() | |
next_index = 0 | |
connected_input_node = self.is_already_connected(input_node) | |
if connected_input_node: | |
for con in self.out_node.outputConnectors(): | |
if con and any([c.outputNode() == connected_input_node for c in con]): | |
next_index = con[0].outputIndex() + 1 | |
break | |
if next_index is None: | |
raise Exception("Index error") | |
else: | |
if next_index >= len(self.out_node.outputNames()): | |
next_index = 0 | |
return next_index | |
def output_data_type(self, index=None): | |
index = index or self.get_output_index() | |
return self.out_node.outputDataTypes()[index] | |
def get_indexes_and_input_node(self): | |
input_node = self.get_input_node() | |
input_index = self.get_input_index() | |
output_index = self.get_output_index() | |
return input_node, input_index, output_index | |
def connect(self): | |
input_node, input_index, output_index = self.get_indexes_and_input_node() | |
# print(f"{self.out_node.name()}.{output_index} -> {input_node.name()}.{input_index}") | |
input_node.setInput(input_index, self.out_node, output_index) | |
@classmethod | |
def from_node(cls, hou_node): | |
current_container_type = hou_node.parent().type().name() | |
for engine in cls.__subclasses__(): | |
if engine.container_node_type == current_container_type: | |
return engine(hou_node) | |
@classmethod | |
def connect_selected(cls): | |
sel = hou.selectedNodes() | |
if sel: | |
connector = Connector.from_node(sel[0]) | |
connector.connect() | |
class KarmaConnector(Connector): | |
container_node_type = "subnet" | |
input_node_type = "suboutput" | |
input_connector_name = "surface" | |
preview_node_name = "shader_preview" | |
def is_already_connected(self, input_node): | |
node = super().is_already_connected(input_node) | |
if not node: | |
prev_node = self.out_node.parent().node(self.preview_node_name) | |
if prev_node in self.out_node.outputs(): | |
return prev_node | |
def get_indexes_and_input_node(self): | |
input_node, input_index, output_index = super().get_indexes_and_input_node() | |
data_type = self.output_data_type(output_index) | |
if data_type == "surface": | |
return input_node, input_index, output_index | |
else: | |
input_node, input_index = self.create_intermediate_node(input_node, input_index) | |
return input_node, input_index, output_index | |
def create_intermediate_node(self, input_node, input_index): | |
node = input_node.parent().node(self.preview_node_name) | |
if not node: | |
node = self.out_node.parent().createNode("usdpreviewsurface") | |
node.setName(self.preview_node_name) | |
node.setParms({"diffuseColor": (0, 0, 0), "roughness": 1}) | |
for name in node.inputNames(): | |
node.setIsInputVisible(name, 0) | |
node.setPosition(input_node.position() - hou.Vector2(0, 2)) | |
input_node.setInput(input_index, node, 0) | |
return node, 1 | |
class HtoaConnector(Connector): | |
container_node_type = "arnold_materialbuilder" | |
input_node_type = "arnold_material" | |
input_connector_name = "surface" | |
def main(): | |
Connector.connect_selected() | |
if __name__ == "builtins": | |
main() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment