Design Automation API for 3ds Max:MAXScript からのログ出力

どのようなプログラムであっても、コードの作成中に実行状況をテキスト表示してデバッグに役立てたいことがあります。Design Automation API でも、GET workitems/:id endpoint や OnComplete コールバックからコアエンジンで実行された WorkItem 単位でログファイルをダウンロードして、アドイン(プラグイン/スクリプト)の実行状態を把握することが出来ます。

もし、Design Automation API for 3ds Max で MAXScript からログにテキストを表示させる場合、少し注意が必要です。MAXScript リスナーでのように print や format をコード中に挿入しても、ログに反映させることが出来ません。

MAXScript で Design Automation API のログにテキストを表示させるには、logsystem.logEntry を broadcast:true とともに使用してください。

また、コアエンジンに 3ds Max Batch(3dsmaxbatch.exe) を使用しているので、Activity 定義の CommandLine に、Autodesk Knowledge Network 記事 3ds Max Batch を使用する に記載の -v オプションで 5 ( デバッグ レベルのメッセージ)を指定する必要があります。

これによって、「羽根」の色や「葉っぱ」の有無、ビュー情報などが、クライアント(Web ブラウザ実装)から MAXScript にパラメータが正しく渡されているか、確認出来るようになります。

3D rendering interface featuring a tabletop fan, color selection options at the top, and a price display on the right side.

下記は、Design Automation API for 3ds Max:Forge Viewer ビューの反映 でご紹介した MAXScript に用意したログ主力を意識した Activity です。

    "id": 'TableFanConfiguratorRender',
    "commandLine": ['$(engine.path)\\3dsmaxbatch.exe -v 5 -sceneFile "$(args[InputMaxScene].path)" "$(args[MaxscriptToExecute].path)"'],
    "parameters": {
        "InputMaxScene": {
            "zip": false,
            "ondemand": false,
            "verb": "get",
            "description": "Input 3ds Max scene",
            "required": true,
            "localName": "Table Fan.max"
        },
        "Params": {
            "zip": false,
            "ondemand": false,
            "verb": "get",
            "description": "Input parameters to specify behavior",
            "required": true,
            "localName": "params.json"
        },
        "MaxscriptToExecute": {
            "zip": false,
            "verb": "get",
            "description": "MAXScript to render scene on 3dsmaxbatch.exe",
            "ondemand": false,
            "required": true,
            "localName": "myscript.ms"
        },
        "ImageOutput": {
            "zip": false,
            "ondemand": false,
            "verb": "put",
            "description": "output rendering image",
            "required": true,
            "localName": "result.jpg"
        }
    },
    "engine": 'Autodesk.3dsMax+2022',
    "appbundles": ['<your nicknme>.TableFanConfiguratorRender+dev'],
    "description": "Create rendering image"

また、ログ出力する MAXScript は次のようになります。

    logsystem.logEntry "************ myscript process start ************" info:true broadcast:true

    /* JSON 読み込み関数
     参照:https://forums.cgsociety.org/t/json-and-maxscript/1552038/11
    */
    fn getJsonFileAsString filePath=(
        local  jsonString = ""
        fs=openFile filePath
        while not eof fs do(
            jsonString += readchar fs
        )
        close fs
        return jsonString
    )

    /* JSON 読み込み */
    paramsFilePath = "params.json"
    jsonString = getJsonFileAsString paramsFilePath
    myJObject = dotNetObject "Newtonsoft.Json.Linq.JObject"
    myJObject = myJObject.parse jsonString

    /* パラメータ取得 */
    global col = myJObject.item["color"].value as integer
    global leaf = myJObject.item["leaf"].value as booleanClass
    global width = myJObject.item["width"].value as integer
    global height = myJObject.item["height"].value as integer
    global fov = myJObject.item["fov"].value as double
    global temp = myJObject.item["position"].value
    global pos = FilterString temp ","
    global temp = myJObject.item["rotation"].value
    global rot = FilterString temp ","
    logsystem.logEntry ("*** width, height = " + width as string + ", " + height as string) info:true broadcast:true

    /* ColorX 画層オフ */
    global lay
    for i = 1 to 6 do
    (
        if col != i then (
            lay = LayerManager.getLayerFromName ( "Color" + i as string )
            lay.on = false
            logsystem.logEntry ("*** trun off layer : " + lay.name) info:true broadcast:true
        )
    )

    /* Leaf 画層オン/オフ */
    lay = LayerManager.getLayerFromName ( "Leaf" )
    lay.on = leaf

    /* ART レンダラー設定 */
    global art = ART_Renderer()
    art.quality_db = 20
    art.render_method = 1
    art.anti_aliasing_filter_diameter = 2.0
    art.enable_noise_filter = true
    art.noise_filter_strength = 1
    renderers.current = art

    /* カメラ設定 */
    x = rot[1] as float
    y = rot[2] as float
    z = rot[3] as float
    w = rot[4] as float
    global cam = freecamera rotation:(quat x y z w) position:[pos[1] as float, pos[2] as float, pos[3] as float] fov:fov

    /* レンダリング & 生成画像保存 */
    fname = sysInfo.currentdir + "/result.jpg"
    undisplay ( render camera:cam outputwidth:width outputheight:height outputfile:fname )
    logsystem.logEntry "************ myscript process end ************" info:true broadcast:true
ログファイルのテキスト表示を含む3ds Maxのスクリプト実行状況を示すキャプチャ画像

By Toshiaki Isezaki

Discover more from Autodesk Developer Blog

Subscribe now to keep reading and get access to the full archive.

Continue reading