どのようなプログラムであっても、コードの作成中に実行状況をテキスト表示してデバッグに役立てたいことがあります。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 にパラメータが正しく渡されているか、確認出来るようになります。

下記は、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

By Toshiaki Isezaki

You must be logged in to post a comment.