174 lines
5.7 KiB
Python
174 lines
5.7 KiB
Python
#!/usr/bin/env python
|
||
# -*- coding: utf-8 -*-
|
||
|
||
import os
|
||
import sys
|
||
import maya.cmds as cmds
|
||
import maya.mel as mel
|
||
from config import data
|
||
|
||
# 根据Maya和Python版本获取正确的DNA模块路径
|
||
MAYA_VERSION = cmds.about(version=True)
|
||
SYSTEM_OS = "win64" if cmds.about(os=True) == "Windows" else "linux"
|
||
PYTHON_VERSION = sys.version_info
|
||
|
||
def load_dna_plugin():
|
||
"""加载DNA插件"""
|
||
try:
|
||
# 加载DNA校准插件
|
||
dna_plugin = os.path.join(data.PLUGIN_PATH, "dnacalib.py")
|
||
if not cmds.pluginInfo(dna_plugin, query=True, loaded=True):
|
||
cmds.loadPlugin(dna_plugin)
|
||
|
||
# 加载嵌入式插件
|
||
embedded_plugin = os.path.join(data.PLUGIN_PATH, "embeddedRL4.mll")
|
||
if not cmds.pluginInfo(embedded_plugin, query=True, loaded=True):
|
||
cmds.loadPlugin(embedded_plugin)
|
||
|
||
# 加载RBF插件
|
||
rbf_plugin = os.path.join(data.PLUGIN_PATH, f"MayaUERBFPlugin.mll")
|
||
if not cmds.pluginInfo(rbf_plugin, query=True, loaded=True):
|
||
cmds.loadPlugin(rbf_plugin)
|
||
|
||
return True
|
||
except Exception as e:
|
||
cmds.warning(f"加载DNA插件失败: {str(e)}")
|
||
return False
|
||
|
||
def setup_dna_path():
|
||
"""设置DNA模块路径"""
|
||
# 获取DNA插件路径
|
||
if data.PLUGIN_PATH not in sys.path:
|
||
sys.path.append(data.PLUGIN_PATH)
|
||
|
||
# 获取PyDNA路径
|
||
if data.PYDNA_PATH not in sys.path:
|
||
sys.path.append(data.PYDNA_PATH)
|
||
|
||
# 添加DLL搜索路径
|
||
if SYSTEM_OS == "win64":
|
||
os.environ["PATH"] = f"{data.PYDNA_PATH};{os.environ['PATH']}"
|
||
|
||
# 设置路径并加载插件
|
||
setup_dna_path()
|
||
if not load_dna_plugin():
|
||
cmds.warning("DNA插件加载失败,某些功能可能无法使用")
|
||
|
||
try:
|
||
import dna
|
||
import dnacalib
|
||
except ImportError as e:
|
||
cmds.warning(f"无法导入DNA模块: {str(e)}")
|
||
cmds.warning(f"Python路径: {sys.path}")
|
||
cmds.warning(f"插件路径: {data.PLUGIN_PATH}")
|
||
cmds.warning(f"PyDNA路径: {data.PYDNA_PATH}")
|
||
# 不抛出异常,让界面仍然可以加载
|
||
dna = None
|
||
dnacalib = None
|
||
|
||
class DNAManager:
|
||
def __init__(self):
|
||
self.current_dna = None
|
||
self.reader = None
|
||
self.writer = None
|
||
|
||
def load_dna(self, file_path):
|
||
"""载入DNA文件"""
|
||
try:
|
||
if dna is None:
|
||
raise ImportError("DNA模块未正确加载")
|
||
|
||
# 创建DNA读取器
|
||
self.reader = dna.DNAReader()
|
||
self.reader.read(file_path)
|
||
self.current_dna = self.reader.get_dna()
|
||
return True
|
||
except Exception as e:
|
||
cmds.warning(f"DNA文件加载失败: {str(e)}")
|
||
return False
|
||
|
||
def save_dna(self, file_path):
|
||
"""保存DNA文件"""
|
||
try:
|
||
if not self.current_dna:
|
||
raise ValueError("没有DNA数据可保存")
|
||
|
||
# 创建DNA写入器
|
||
self.writer = DNAWriter()
|
||
self.writer.set_dna(self.current_dna)
|
||
self.writer.write(file_path)
|
||
return True
|
||
except Exception as e:
|
||
cmds.warning(f"DNA文件保存失败: {str(e)}")
|
||
return False
|
||
|
||
def calibrate_joints(self):
|
||
"""校准骨骼位置"""
|
||
try:
|
||
if not self.current_dna:
|
||
raise ValueError("请先加载DNA文件")
|
||
|
||
# 获取骨骼定义
|
||
joints = self.current_dna.get_joints()
|
||
|
||
# 校准每个骨骼
|
||
for joint in joints:
|
||
# 获取骨骼名称和位置
|
||
joint_name = joint.get_name()
|
||
neutral_position = joint.get_neutral_position()
|
||
|
||
# 如果Maya场景中存在该骨骼
|
||
if cmds.objExists(joint_name):
|
||
# 设置骨骼位置
|
||
cmds.xform(joint_name,
|
||
worldSpace=True,
|
||
translation=neutral_position)
|
||
|
||
return True
|
||
except Exception as e:
|
||
cmds.warning(f"骨骼校准失败: {str(e)}")
|
||
return False
|
||
|
||
def export_fbx(self, file_path):
|
||
"""导出FBX文件"""
|
||
try:
|
||
# 选择所有需要导出的对象
|
||
all_objects = self.get_export_objects()
|
||
cmds.select(all_objects)
|
||
|
||
# 设置FBX导出选项
|
||
mel.eval('FBXExportInputConnections -v true')
|
||
mel.eval('FBXExportIncludeChildren -v true')
|
||
|
||
# 导出FBX
|
||
cmds.file(file_path,
|
||
force=True,
|
||
options="v=0",
|
||
type="FBX export",
|
||
preserveReferences=True,
|
||
exportSelected=True)
|
||
return True
|
||
except Exception as e:
|
||
cmds.warning(f"FBX导出失败: {str(e)}")
|
||
return False
|
||
|
||
def get_export_objects(self):
|
||
"""获取需要导出的对象列表"""
|
||
# 获取模型、骨骼等对象
|
||
objects = []
|
||
if self.current_dna:
|
||
# 添加骨骼
|
||
joints = self.current_dna.get_joints()
|
||
for joint in joints:
|
||
joint_name = joint.get_name()
|
||
if cmds.objExists(joint_name):
|
||
objects.append(joint_name)
|
||
|
||
# 添加蒙皮模型
|
||
meshes = self.current_dna.get_meshes()
|
||
for mesh in meshes:
|
||
mesh_name = mesh.get_name()
|
||
if cmds.objExists(mesh_name):
|
||
objects.append(mesh_name)
|
||
|
||
return objects |