Hogyan töltsünk be 3D modelleket a Python-ban
Aspose.3D FOSS for Python egyszerű API-t biztosít 3D fájlok megnyitásához natív függőségek nélkül. A fájl betöltése után egy Scene objektumba, bejárhatja a node hierarchiát, és nyers geometriai adatokat olvashat a scene minden mesh‑jéről.
Lépésről-lépésre útmutató
1. lépés: A csomag telepítése
Telepítse a Aspose.3D FOSS-t a PyPI‑ról. Nem szükséges további rendszerkönyvtárak.
pip install aspose-3d-fossTámogatott Python verziók: 3.7, 3.8, 3.9, 3.10, 3.11, 3.12.
2. lépés: A Scene osztály importálása
A Scene class a legfelső szintű tároló minden 3D adat számára. Importálja azt a szükséges load‑option class‑okkal együtt.
from aspose.threed import Scene
from aspose.threed.formats import ObjLoadOptionsMinden nyilvános classes a aspose.threed vagy annak sub‑packages (aspose.threed.entities, aspose.threed.formats, aspose.threed.utilities).
3. lépés: Fájl betöltése
Használja a static Scene.from_file() method bármely támogatott formátum megnyitásához. A library automatikusan felismeri a formátumot a fájl kiterjesztéséből.
##Automatic format detection
scene = Scene.from_file("model.obj")Alternatívaként hozzon létre egy Scene instance, és hívja meg a open(); hasznos, ha load options‑t szeretne átadni vagy hibákat explicit módon kezelni:
scene = Scene()
scene.open("model.obj")Mindkét módszer támogatja az OBJ, STL (bináris és ASCII), glTF 2.0 / GLB, COLLADA (DAE) és 3MF fájlokat.
4. lépés: A Scene csomópontok bejárása
A loaded scene egy fa a Node objects gyökere a scene.root_node. Iterate rekurzívan az összes node megtalálásához:
from aspose.threed import Scene, Node
scene = Scene.from_file("model.obj")
def walk(node: Node, depth: int = 0) -> None:
indent = " " * depth
print(f"{indent}Node: {node.name!r}")
for child in node.child_nodes:
walk(child, depth + 1)
walk(scene.root_node)Minden Node can nulla vagy több Entity objektumok (hálók, kamerák, fények). Ellenőrizze node.entities hogy lássa, mi van csatolva.
5. lépés: Csúcs és sokszög adatok elérése
Konvertálja egy csomópont entitását Mesh és olvassa el annak vezérlőpontjait (csúcspozíciók) és poligonjait (felületindex-listák):
from aspose.threed import Scene
from aspose.threed.entities import Mesh
scene = Scene.from_file("model.obj")
for node in scene.root_node.child_nodes:
for entity in node.entities:
if isinstance(entity, Mesh):
mesh: Mesh = entity
print(f"Mesh '{node.name}': "
f"{len(mesh.control_points)} vertices, "
f"{len(mesh.polygons)} polygons")
# First vertex position
if mesh.control_points:
v = mesh.control_points[0]
print(f" First vertex: ({v.x:.4f}, {v.y:.4f}, {v.z:.4f})")
# First polygon face (list of control-point indices)
if mesh.polygons:
print(f" First polygon: {mesh.polygons[0]}")mesh.control_points lista a Vector4 objektumok; x, y, z tartalmazzák a pozíciót és w a homogén koordináta (általában 1.0).
mesh.polygons egy listák listája egész számokból, ahol minden belső lista egy adott felülethez tartozó, rendezett vezérlőpont-indexek halmaza.
6. lépés: Formátum-specifikus betöltési beállítások alkalmazása
A finomhangolt vezérléshez, hogy egy OBJ fájlt hogyan értelmezzen, adjon át egy ObjLoadOptions példányt a scene.open():
from aspose.threed import Scene
from aspose.threed.formats import ObjLoadOptions
options = ObjLoadOptions()
options.flip_coordinate_system = True # Convert right-hand Y-up to Z-up
options.scale = 0.01 # Convert centimetres to metres
options.enable_materials = True # Load .mtl material file
options.normalize_normal = True # Normalize all normals to unit length
scene = Scene()
scene.open("model.obj", options)STL fájlok esetén az ekvivalens osztály StlLoadOptions. glTF esetén használja GltfLoadOptions. Lásd a API referencia a teljes listaért.
Gyakori problémák és megoldások
FileNotFoundError híváskor Scene.from_file()
Az elérési útnak abszolútnak vagy a futási időben a munkakönyvtárhoz képest helyesnek kell lennie. Használja pathlib.Path a megbízható utak felépítéséhez:
from pathlib import Path
from aspose.threed import Scene
path = Path(__file__).parent / "assets" / "model.obj"
scene = Scene.from_file(str(path))mesh.polygons üres egy STL fájl betöltése után
Az STL fájlok háromszögeket nyers felületekként tárolják, nem indexelt hálóként. Betöltés után a poligonok ezekből a felületekből szintetizálódnak. Ha polygons üresnek tűnik, ellenőrizze len(mesh.control_points); ha a szám háromszoros, a geometria index nélküli formában van tárolva, és minden egymást követő három csúcs egy háromszöget alkot.
Koordináta‑rendszer eltérés (a modell elfordítottnak vagy tükrözöttnek tűnik)
Különböző eszközök különböző konvenciókat használnak (Y-felfelé vs Z-felfelé, balkezes vs jobboldali). Állítsa be ObjLoadOptions.flip_coordinate_system = True vagy alkalmazzon egy forgatást a gyökércsomópont Transform betöltés után.
AttributeError: 'NoneType' object has no attribute 'polygons'
Egy csomópont entitáslistája tartalmazhat nem-háló entitásokat (kamerák, fények). Mindig ellenőrizze a isinstance(entity, Mesh) castolás előtt.
Gyakran Ismételt Kérdések (GYIK)
Milyen 3D formátumokat tudok betölteni?
OBJ (Wavefront), STL (bináris és ASCII), glTF 2.0 / GLB, COLLADA (DAE) és 3MF. Az FBX fájl tokenizálása részben támogatott, de a teljes elemzés még nem készült el.
Betölti-e egy OBJ fájl a .mtl materialt?
Igen, amikor ObjLoadOptions.enable_materials = True (az alapértelmezett). A könyvtár a .mtl fájlt ugyanabban a könyvtárban, mint a .obj fájl. Ha a .mtl hiányzik, a geometria továbbra is betöltődik, és egy figyelmeztetés kerül kiadásra.
Betölthetek fájlt bájtos áramlásból az útvonal helyett?
Igen. scene.open() elfogad bármilyen fájl-szerű objektumot egy .read() metódussal a fájlútvonal karakterlánc mellett. Adjon át egy nyitott bináris adatfolyamot (pl., io.BytesIO) közvetlenül. Scene.from_file() csak egy fájlútvonal karakterláncot fogad el.
Hogyan szerezhetem meg a felületi normálvektorokat?
Betöltés után ellenőrizze mesh.get_element(VertexElementType.NORMAL). Ez visszaad egy VertexElementNormal amelynek data lista egy normál vektort tartalmaz referenciaenként, a következő szerint leképezve mapping_mode és reference_mode.
from aspose.threed.entities import Mesh, VertexElementType
normals = mesh.get_element(VertexElementType.NORMAL)
if normals:
print(normals.data[0]) # First normal vectorA könyvtár szálbiztos a több fájl egyidejű betöltéséhez?
Minden Scene objektum független. Különálló fájlok betöltése különálló Scene példányokba különálló szálakról biztonságos, amíg nem oszt meg egyetlen Scene szálak között külső zárolás nélkül.