2013-06-13 111 views
2

我正在尝试将某些对象从搅拌器导出为专有格式。我希望我写的脚本能够从文件下拉菜单和命令行中将搅拌机中的对象导出。我在ubuntu 12.04 LTS上使用搅拌机2.66。下面是我目前正在尝试运行的文件。如何让Blender导出脚本从命令行运行?

# Required Blender information. 
bl_info = { 
      "name": "My Exporter", 
      "author": "", 
      "version": (1, 0), 
      "blender": (2, 65, 0), 
      "location": "File > Export > Test (.tst)", 
      "description": "", 
      "warning": "", 
      "wiki_url": "", 
      "tracker_url": "", 
      "category": "Import-Export" 
      } 

# Import the Blender required namespaces. 
import bpy 
from bpy_extras.io_utils import ExportHelper 


# The main exporter class. 
class MyExporter(bpy.types.Operator, ExportHelper): 
    bl_idname  = "test.tst"; 
    bl_label  = "My Exporter"; 
    bl_options  = {'PRESET'}; 

    filename_ext = ".tst"; 

    object_count = 0; 

    def __init__(self): 
     pass 

    def execute(self, context): 
     print("Execute was called."); 

     # Parse all the objects in the scene. 
     return {'FINISHED'}; 

    def export_object(self, gameObject): 
     if (gameObject.type != "MESH"): 
     print("Object was not of type mesh."); 
     else: 
     object_count += 1; 

     return; 


# Define a function to create the menu option for exporting. 
def create_menu(self, context): 
    self.layout.operator(MyExporter.bl_idname,text="test (.tst)"); 

# Define the Blender required registration functions. 
def register(): 
    """ 
    Handles the registration of the Blender Addon. 
    """ 
    bpy.utils.register_module(__name__); 
    bpy.types.INFO_MT_file_export.append(create_menu); 

def unregister(): 
    """ 
    Handles the unregistering of this Blender Addon. 
    """ 
    bpy.utils.unregister_module(__name__); 
    bpy.types.INFO_MT_file_export.remove(create_menu); 

# Handle running the script from Blender's text editor. 
if (__name__ == "__main__"): 
    print("Registering."); 
    register(); 

    print("Executing."); 

    # I have tried with these lines uncommented to force it to run 
    # the execute function, but I get an error saying: 
    # exporter = MyExporter(); 
    # TypeError: bpy_struct.__new__(type): expected a single argument 

    #exporter = MyExporter(); 
    #exporter.execute(bpy.context.scene); 

我曾尝试下面的命令:

blender model.blend --background --python myexporter.py 

从中我得到以下的输出:

Note: No (valid) '~/.config/blender/2.66/config/startup.blend' found, 
     fall back to built-in default. 

Read new prefs: ~/.config/blender/2.66/config/userpref.blend 
found bundled python: ~/blender/2.66/python 
read blend: ~/model.blend 
Registering. 
Executing. 

Blender quit 

从MyExporter类执行功能似乎永远不会被调用。我甚至尝试过直接调用execute函数,但是,如果你阅读了该区域的注释,我似乎也错过了那里的一些东西。

当脚本作为加载项添加到搅拌器时,一切正常。它完美地调用执行。所以至少我有一半工作。

非常感谢您提供的任何帮助。如果我犯了一个愚蠢的错误,我很抱歉,我在写这个脚本的同时学习了python。

回答

10

我终于明白了这一点,并认为回来分享答案是个好主意。首先这里是可用的文件。

# Required Blender information. 
bl_info = { 
      "name": "My Exporter", 
      "author": "", 
      "version": (1, 0), 
      "blender": (2, 65, 0), 
      "location": "File > Export > Test (.tst)", 
      "description": "", 
      "warning": "", 
      "wiki_url": "", 
      "tracker_url": "", 
      "category": "Import-Export" 
      } 

# Import the Blender required namespaces. 
import sys, getopt 

import bpy 
from bpy_extras.io_utils import ExportHelper 



# The main exporter class. 
class MyExporter(bpy.types.Operator, ExportHelper): 
    bl_idname  = "export_scene.my_exporter"; 
    bl_label  = "My Exporter"; 
    bl_options  = {'PRESET'}; 

    filename_ext = ".tst"; 

    object_count = 0; 

    def __init__(self): 
     pass 

    def execute(self, context): 
     print("Execute was called."); 

     self.parse_command_line_options(); 

     if (self.filepath == ""): 
     print("No sutable filename was provided to save to."); 
     return {'FINISHED'}; 

     # Get all the mesh objects in the scene. 
     objList = [object for object in bpy.context.scene.objects if object.type == 'MESH']; 

     # Now process all the objects that we found. 
     for gameObject in objList: 
     self.export_object(gameObject); 

     # Parse all the objects in the scene. 
     return {'FINISHED'}; 


    def export_object(self, gameObject): 
     if (gameObject.type != "MESH"): 
     print("Object was not of type mesh."); 
     else: 
     self.object_count += 1; 

     return; 


    def parse_command_line_options(self): 
     modelFile = ""; 
     myArgs = []; 
     argsStartPos = 0; 

     if (("--" in sys.argv) == False): 
     return; 

     argsStartPos = sys.argv.index("--"); 
     argsStartPos += 1; 
     myArgs = sys.argv[argsStartPos:]; 

     try: 
     opts, args = getopt.getopt(myArgs, 'hm:', ["help", "model-file="]); 
     except getOpt.GetoptError: 
     print("Opt Error."); 
     return; 

     for opt, arg in opts: 
     if (opt in ("-h", "--help")): 
      print("Run this as the following blender command."); 
      print("\tblender <blend file> --background --python <script file> -- -m <output file>"); 
     elif (opt in ("-m", "--model-file")): 
      modelFile = arg; 

     if (modelFile != ""): 
     self.filepath = modelFile; 



# Define a function to create the menu option for exporting. 
def create_menu(self, context): 
    self.layout.operator(MyExporter.bl_idname,text="test (.tst)"); 

# Define the Blender required registration functions. 
def register(): 
    """ 
    Handles the registration of the Blender Addon. 
    """ 
    bpy.utils.register_module(__name__); 
    bpy.types.INFO_MT_file_export.append(create_menu); 

def unregister(): 
    """ 
    Handles the unregistering of this Blender Addon. 
    """ 
    bpy.utils.unregister_module(__name__); 
    bpy.types.INFO_MT_file_export.remove(create_menu); 


# Handle running the script from Blender's text editor. 
if (__name__ == "__main__"): 
    print("Registering."); 
    register(); 

    print("Executing."); 
    bpy.ops.export_scene.my_exporter(); 

,我失踪了错误,然后设置为我出口类bl_idname)bpy.ops.export_scene.my_exporter的调用(关键的东西;

什么我搞砸了可以在这里找到

的更多信息:http://www.blender.org/documentation/blender_python_api_2_66_release/bpy.ops.html

现在,因为我也想这从命令行运行,而不仅仅是文件下拉菜单中,我添加了一个解析函数来解析命令行选项发送到Blender。 Blender有一个开关' - ',它定义了搅拌器参数输入的结束,所以如果检测到该开关,我会抓住任何参数并将其解析为我的脚本参数。到目前为止,这似乎完美地工作。

目前,模型文件支持-h打印一些帮助信息,-m指定保存转换数据的文件。

那么,我希望这些信息可以帮助别人。祝你好运。

更新:如果在运行脚本时在命令行上看到一条或多条消息,请使用此question的答案来解决该问题。

skipping driver 'alpha * auto', automatic scripts are disabled 
+0

Hi @Jason Smith,这真的是一个伟大的工作,我们希望将这个脚本放在搅拌机中,我们该如何运行它? –

+0

嗯,我是从命令行运行的,因为标题说明了,所以我使用了类似这样的东西: 搅拌器 --background --python Exporter.py –

+0

如果您想从blender中作为add - 这也是可能的。为此,我把你介绍到这里。 http://wiki.blender.org/index.php/Doc:2.6/Manual/Extensions/Python/Add-Ons –