Blender Python API in Houdini (Python 3)

Python 3 wird in Houdini 18.5 zu Production Builds

Houdini 18.5 - Python 3 wurde zu [Production Builds Items] hinzugefügt (https://www.sidefx.com/download/daily-builds/old-installer/#category-gold). Jetzt, da Sie Python3 verwenden können, sollten Sie Bibliotheken verwenden können, die nur in der Python3-Serie verfügbar sind! Also werde ich dieses Mal bpy (Blender Python), das in Python 3.7 verwendet werden kann, in Houdini einfügen.

Ich habe die folgende Windows-Version von Houdini verwendet. houdini-py3-18.5.351-win64-vc141.exe

Bpy bauen

Da bpy als Python-Modul derzeit nicht verteilt ist, muss es aus dem Quellcode erstellt werden, der sich auf Folgendes bezieht. Building Blender as a Python Module

Richten Sie eine Build-Umgebung ein

Sie können leicht einen japanischen Artikel über das Erstellen von Blender aus dem Quellcode finden. Wenn Sie also weitere Informationen benötigen, suchen Sie danach.

Vielleicht ist es okay, wenn der Bereich installiert ist ...?

Löschen Sie den Quellcode

Ich werde den Quellcode unter Bezugnahme auf https://developer.blender.org/diffusion/B/ löschen. Ich denke, Sie können es aus dem Spiegel auf Github ziehen.

Bauen

Wenn Sie den Quellcode erweitern, wird die Verzeichnisstruktur für Folgendes angezeigt. blender_build.PNG

Öffnen Sie eine Eingabeaufforderung in diesem Verzeichnis (wo sich make.bat befindet).

make bpy

Wenn Sie ausführen, werden andere zum Erstellen erforderliche Bibliotheken von Subversion gelöscht und erstellt. (Sobald Sie beginnen, werden Sie gefragt, ob Sie die anderen benötigten Bibliotheken löschen möchten. Drücken Sie also y, um fortzufahren.) Das erste Mal wird viel Zeit in Anspruch nehmen.

Ordne Build-Artefakte zum Lesen in Houdini an

Baue Artefakte (Blender-Quellcodeverzeichnis) \ .. \ build_windows_Bpy_x64_vc16_Release \ bin \ Release Es ist in.

bpy.pyd, libfftw3-3.dll Legen Sie diese beiden in Houdinis Python-lesbares Verzeichnis. Die erforderlichen DLLs können sich erhöhen oder verringern, wenn sich die Blender-Version ändert. Hier ist es unten angeordnet. C: \ Users \ (Benutzername) \ Documents \ houdini18.5 \ python3.7libs

37libs.PNG

Ordner 2.90 (Build Blender-Version)

Legen Sie diesen Ordner in das Verzeichnis, in dem sich die installierte Houdini-Exe befindet. Das Festlegen von Umgebungsvariablen kann an anderer Stelle hilfreich sein (nicht überprüft). Hier ist es unten angeordnet. C:\Program Files\Side Effects Software\Houdini 18.5.351\bin bin.PNG

Verwenden Sie die Blender Python-API

Bestätigen Sie den Import bpy

Es ist endlich einsatzbereit. Stellen Sie sicher, dass import bpy in Python Shell oder Python (SOP) fehlerfrei ausgeführt werden kann. Wenn es ein Problem mit dem Build-Artefakt oder dem Platzierungsort gibt, tritt ein Fehler auf oder Houdini stürzt ab.

python_shell.PNG

.Blend-Datei lesen

Erstellen Sie einen Prozess zum Lesen einer .blend-Datei mit Python (SOP).

Vorbereitung der Testdaten

Ich habe eine Mischung mit Würfeln und Susanne vorbereitet. Susanne wird in zwei Hälften geschnitten und die Modifikatoren Spiegel und Unterteilung werden gesetzt. test_data.PNG

Schreiben Sie Python-Code in Python (SOP)

Name im Attribut Primitive N, UV mit Vertex-Attributen Ich habe den Code zum Lesen geschrieben.

Die Parameter sind wie folgt.

Label Name Erläuterung
Blender File blend_file Lesen.Geben Sie die Mischung an
Object Name objects Angabe des zu lesenden Objekts
Apply Modifier apply_modifier Geben Sie an, ob der Modifikator angewendet werden soll

houdini.PNG

import os
import bpy
from bpy_extras.io_utils import axis_conversion

node = hou.pwd()
geo = node.geometry()

#Bereiten Sie die einzustellenden Attribute vor
name_attrib = geo.addAttrib(hou.attribType.Prim, 'name', '')
normal_attrib = geo.addAttrib(hou.attribType.Vertex, 'N', (0.0, 0.0, 0.0))
uv_attrib = geo.addAttrib(hou.attribType.Vertex, 'uv', (0.0, 0.0, 0.0))

#Parameter lesen
blend_file = node.parm('blend_file').evalAsString()
apply_modifier = node.parm('apply_modifier').evalAsInt()
object_names = [ s.strip() for s in node.parm('objects').evalAsString().split() ]

if len(blend_file)>0:
    # .Offene Mischung
    bpy.ops.wm.open_mainfile(filepath=blend_file)
    #Lesen Sie alle Objekte, wenn kein Name festgelegt ist
    if len(object_names)==0:
        object_names = bpy.data.objects.keys()
else:
    #Öffnen Sie die erste Datei des Mixers und löschen Sie Susanne
    bpy.ops.wm.read_homefile(app_template='')
    bpy.ops.mesh.primitive_monkey_add()
    object_names = ['Suzanne']

depsgraph = bpy.context.evaluated_depsgraph_get()
#Eine Matrix, die die Ausrichtung der Mixerachse in die Ausrichtung der Houdini-Achse umwandelt
axis_conv_mat = axis_conversion(
    from_forward='-Y', from_up='Z',  
    to_forward='Z', to_up='Y'
    ).to_4x4()
    
#Öffnet ein Objekt mit dem angegebenen Namen
for obj_name in object_names:
    obj = bpy.data.objects[obj_name]
    if obj.type!='MESH':
        continue
    
    #Wenden Sie bei Bedarf Modifikatoren an
    ob_for_convert = obj.evaluated_get(depsgraph) if apply_modifier else obj.original

    #Netz aus Objekt extrahieren
    try:
        me = ob_for_convert.to_mesh()
    except:
        me = None
    if me is None:
        continue
        
    #Wenden Sie die Achsentransformation und die Objekttransformation auf das Netz an
    me.transform( axis_conv_mat @ obj.matrix_world )
    
    #Was tun, wenn eine negative Skala angewendet wird?
    if obj.matrix_world.determinant() < 0.0:
        me.flip_normals()
    
    #Vertex Normal berechnen
    me.calc_normals_split()

    #Holen Sie sich UV-Daten
    uv_layer = me.uv_layers.active.data[:] if len(me.uv_layers) > 0 else None

    #Punkte erstellen
    points = [ hou.Vector3(v.co) for v in me.vertices ]
    pt_list = geo.createPoints(points)

    #Konvertieren Sie, da die Reihenfolge der Polygonscheitelpunkte zwischen Mixer und Houdini unterschiedlich ist
    loop_indices_list = list()
    for mpoly in me.polygons:
        count = len(mpoly.loop_indices)
        loop_indices_list.append( [ mpoly.loop_indices[(count-i)%count] for i in range(0, count) ] )

    for loop_indices in loop_indices_list:
        poly = geo.createPolygon()
        poly.setAttribValue(name_attrib, obj_name)
        for i in loop_indices:
            #Machen Sie ein Polygon
            v = poly.addVertex( pt_list[ me.loops[i].vertex_index ] )
            # N attribute 
            v.setAttribValue(normal_attrib,  me.loops[i].normal)
            # uv attribute 
            if uv_layer:
                uv = uv_layer[i].uv
                v.setAttribValue(uv_attrib, (uv[0], uv[1], 0.0))

Der Parameter Objektname kann jetzt wie unten gezeigt aus ▽ im Menüskript ausgewählt werden.

import os
import bpy

name_list = list()

node = hou.pwd()
blend_file = node.parm('blend_file').evalAsString()
#Überprüfung der Dateiexistenz
if not os.path.exists(blend_file):
    return name_list

#Zählen Sie die Namen der Mesh-Objekte auf
objects = bpy.data.objects
for obj in objects:
    if obj.type == 'MESH':
        name_list.extend( [obj.name]*2 )

return name_list

Ich schreibe einen Kommentar in den Code, daher werde ich ihn nicht im Detail erklären. Der Code zum Abrufen der Netzinformationen mit der Blender Python-API (Blender-Installationsverzeichnis) \ (Blender-Version) \ scripts \ addons Diejenigen, die unten mit io_ beginnen, sind Importer / Exporter-Add-Ons, daher ist dies hilfreich. Der obige Code wurde mit Bezug auf io_scene_obj geschrieben.

Andere

Das folgende Protokoll wird ausgegeben, wenn die .blend-Datei von bpy gelesen wird. Ich wusste nicht, wie ich das von außen stoppen sollte. houdini_console.png

Wenn dies im Weg ist, kommentieren Sie diesen Protokollausgabecode beim Erstellen von bpy aus und er wird nicht ausgegeben.

source\blender\blenkernel\intern\blendfile.c


int BKE_blendfile_read(bContext *C,
                       const char *filepath,
                       const struct BlendFileReadParams *params,
                       ReportList *reports)
{
  BlendFileData *bfd;
  bool success = false;

  /* Don't print startup file loading. */
  if (params->is_startup == false) {
    printf("Read blend: %s\n", filepath);
  }
  ...
}

Recommended Posts

Blender Python API in Houdini (Python 3)
Evernote-API in Python
Python-Dolmetscher in Maya, Houdini, Mixer, Nuke
C-API in Python 3
Hit Mastodons API in Python
Generieren Sie 8 * 8 (64) Cubes mit Blender Python
Zeichnen Sie Sinuswellen mit Blender Python
Abrufen der arXiv-API in Python
Klicken Sie in Python auf die Sesami-API
Erstellen Sie Google Mail in Python ohne Verwendung der API
Klicken Sie auf die Web-API in Python
Implementieren Sie die REST-API schnell in Python
Greifen Sie mit Python auf die Twitter-API zu
Beginnen Sie mit Python mit Blender
Quadtree in Python --2
Python in der Optimierung
CURL in Python
Mausbedienung mit Windows-API in Python
Metaprogrammierung mit Python
Python 3.3 mit Anaconda
Geokodierung in Python
SendKeys in Python
Versuchen Sie es mit der Wunderlist-API in Python
Metaanalyse in Python
Versuchen Sie, die Kraken-API mit Python zu verwenden
Unittest in Python
Epoche in Python
Zwietracht in Python
Blender 2.9 Python Extrude extrudieren
Holen Sie sich Google Fit API-Daten in Python
Deutsch in Python
DCI in Python
Quicksort in Python
nCr in Python
Holen Sie sich Youtube-Daten in Python mithilfe der Youtube-Daten-API
Plink in Python
Konstante in Python
Verweisen auf Umgebungsvariablen in Python in Blender
FizzBuzz in Python
SQLite in Python
Schritt AIC in Python
LINE-Bot [0] in Python
Reverse Assembler mit Python
Reflexion in Python
Konstante in Python
nCr in Python.
Format in Python
Scons in Python 3
Puyopuyo in Python
Python in Virtualenv
PPAP in Python
Quad-Tree in Python
Reflexion in Python
Chemie mit Python
Hashbar in Python
DirectLiNGAM in Python
LiNGAM in Python
In Python reduzieren