投稿者「araken」のアーカイブ

TDで、OPの名前を処理する方法

概要

Pythonで、OPの名前”base1″の数字やベース名を抽出したり、OPの名前を生成する方法。
OPの名前から数字(連番)をスクリプトから取得することで、繰り返し処理などが効率化できます。

サンプルファイル

https://github.com/arkwknsk/touchdesigner/tree/master/tips/op-name

OPの名前から連番を取得する方法

d = op('base1').digits
print(d) # 1

ここでは、digitsを使って、base1の連番を抽出しています。

OPの名前を生成する方法

TDF = op.TDModules.mod.TDFunctions
name = TDF.incrementStringDigits('foo',2)
print(name) #foo2

TDの標準ライブラリのincrementStringDigitsを使います。2個目の引数に、くっ付けたい数字を指定します。

OPの名前から連番前の文字列を取得する方法

b = op('base1').base
print(b) #base

baseを使って、連番前の文字列を抽出します。正規表現を書くより楽です。

TDで、スクリプトからConstant CHOPを書き換える方法

概要

Constant CHOPを参照するのと同じ形で値を変えようとするとエラーになるが、書き換えられる方法。

サンプルファイル

https://github.com/arkwknsk/touchdesigner/tree/master/tips/rewrite-upconstant-chop

Pythonコード

import random
op('constant1').par.value0 = random.uniform(0,100)

ここでは、1constant12text1のスクリプトから書き換えています。

chop_op.par.value0の形でアクセスすることで、値を書き換えられます。chop_op[0] = 1234 の形でアクセスするとエラーになります(Read Only)。

実行タイミング

最後に、このやり方で実行のタイミングはどうなるかを検証。結論は、同フレーム内で処理されるので安心です。

3text2のスクリプトから1constant1を書き換え、その変更で4chopexec1が実行されるサンプルを実行します。各実行タイミングでFrame数を出力しています。

import random
print( absTime.frame)
print( op('constant1')[0])
op('constant1').par.value0 = random.uniform(0,100)
print( op('constant1')[0])

4chopexec1で最後のFrame数を出力します。

def onValueChange(channel, sampleIndex, val, prev):
	print( absTime.frame)
	return

3text2のスクリプトから1constant1を書き換え、その変更で4chopexec1が実行されるサンプルを実行します。各実行タイミングでFrame数を出力しています。

実行結果は以下です。

python >>> 
29169
9.247329711914062
54.78358840942383
29169
python >>> 

2行目で、最初のFrame数を出力。3行目で、古い値が表示されています。4行目で書き換わった値を1constant1から参照して出力しています。ということは、同スクリプト内で書き換えた値を再び参照できるようです。最後に、4chopexec1の実行タイミングのFrame数を出力しています。最初のFrame数と同じなので、同フレーム内で実行されていることを検証できました。

余談

スクリプトの計算結果から、CHOPのノードで処理するときに便利です。また、スクリプトの計算結果を環境変数にして、各ノードの設定を決めるのにも便利です。

スクリプトから、Table DATを更新して、CHOPに流し込む方法もありますが、ノードの数が増えてしまいます。

TDで、複数プロセスのデータを共有する方法

概要

ローカルPC内もしくはネットワークに接続されたPC間で動くTouchDesignerの複数のプロセスでデータを共有する方法。

TDのプロセスは、シングルスレッドで動作し同期型のため、高負荷の処理に弱く、マルチコアのCPUの性能をフル活用することができません。大まかな機能ごとにプロセスを分けて、同時起動すると、マルチスレッド的で動作し、負荷分散を図ることができます。また、モジュール化を図ったり、複数人の共同作業の分割にお役立ち!

サンプルファイル

https://github.com/arkwknsk/touchdesigner/tree/master/tips/touchin

Touch In / Out

TDには、プロセス間でデータを共有できるノードがいくつか用意されています。

  • Touch In / Out CHOP
  • Touch in / Out DAT
  • Touch in / Out TOP

また、Pro/Commercialライセンスのみで使えるもっと高度なノードもあります。

送信側

今回は、数値・文字列データを送れるDATとCHOPを送受信

送信側に、1Touch Out DAT2Touch Out CHOPを追加します。今回は、absTime.frameの値を送ります。

毎フレームごとの値を連番(シークエンス)で送れるので、後ほど遅延時間を確認できます。

受信側

送信側のTDを起動した状態のままで、別のTDで受信側の.toeファイルを新規作成し、1Touch In DAT2Touch In CHOPを追加します。追加すると、早速、受信側のノードの数字が変わります。

もし、送受信ができない場合は、

  • Touch InのParametersのNetwork Addresslocalhostになっているかを確認
  • OSもしくはウィルスソフトのファイヤーウォールを一時的に全OFF

を試してみてください

遅延

気になる遅延ですが、DATの方は、デフォルトの設定でローカルPC内で1 frame程度の遅延です。これは、PC自体の処理能力に依存すると思われます。

CHOPの方はデフォルトの設定だと、ローカルPC内でも5 framesのズレが発生します。これは、デフォルトの設定では、通信のドロップのエラー処理のため、キャッシュを貯めているの原因の様です。

CHOPの遅延回避

Touch In CHOPのparameterをこれぐらいにすると、ローカルPC内でも1 frameのズレ程度にできます。

OSCと比較

同じように、異なるプロセスやPCでデータを共有するのに、OSCが一般的に使われますが、Touch In/Outと比べると、

  • それぞれにノードを1つだけ置いて送受信でき、すぐに他のCHOPノードに送れるので開発が楽
  • チャンネルネームも送信できる

という利点があります。ただし、OSCの場合は、TD以外で開発されたアプリと通信ができるので、ここは大きく違います。あくまでも、TD同士での通信に有効と言えます。

使い道

このノード群を使うと、以下のようなことができます。

  • 重たいCHOP系の処理と描画系処理を別な.toeで制作して、マルチスレッドで実行する
  • 制御系toeから、複数のPCで稼働するtoeプロセスを制御して、複数画面同期コンテンツを動かす

その他のノード

Pro/Commercialライセンスだと、さらに共有できるノードが用意されています。こちらは、次回に。

Notchで、数値(テキスト)データを大量に表示する方法

Notch #madewithnotch Advent Calendar 2019」16日目の記事です。

概要

Notchで、ヴィジュアライゼーション的に、大量に数値や文字列を表示する方法を模索。

ClonerやParticleでTextを表示する場合、元になるTextの文字列が固定されてしまい、Particle毎に文字列を変え、異なる文字列を大量に表示することができない。

※本サンプルでは、NDIを使用しているのでTouchDesignerはCommercialライセンス以上が必要になります。ご了承ください。

そこで、TextureをSpriteアニメーションで切り替えるようにし、 Particle毎に表示を変え、疑似的に異なる文字列を表示するようにする。ただし、Notch内部では大量のテキストを処理するのは難しいので、TouchDesignerで数値を処理し、テクスチャーとしてNDIでNotchに送る。それをNotch側でParticleに貼り付けて、大量に表示するという流れ。

サンプルファイル

https://github.com/arkwknsk/notch/tree/master/20191216_many-text

TouchDesginerからNDIを送る

TouchDesignerのネットワーク

今回はランダム数値を16個、Notch側に流すことにする。ネットワーク左側でランダム数値を生成する。

次に、生成したランダム数値をText TOPで画像化し、Layout TOPで4 *4 のグリッドで貼り付ける。最終的に、Notch側でこの画像を16等分してTextureとして利用する。

Textureは、二乗の正方形がGPU的にやさしい。ここでは、1024*1024のResolutionにしている。

なぜか、Notch側でPoint RendererにImageとして貼り付けると、左右反転になってしまうので、TouchDesigner側で反転させ、NDI Out TOPで出力する。今回は、同じPC内でNDIを送る。

ここでは、ランダム数値を使っているが、大量のテキストデータやセンサーの数値データなどを送ったりして、演出できる。また、Top自体はどんな映像でも良いので、TouchDesigner側で様々なロジックを組みTextureを生成し、動的にNotch側で表示するという手法も考えられる。

Notch側でNDIを受け取る

新規のプロジェクトか、プロジェクトを開き、Menu->Devices->VideoIn/Camera/Kinect Setting…を選ぶ。

TouchDesignerからNDIが送信されている場合は、NDI -> Incomingの中に、リスト表示されているので、これを選択する。

こちらが今回のNotchのネットワーク。

1“Video NDI Source”で、NDIを受信します。これを、2PointRendererにTextureとして読み込ませます。

Point RendererのPropertiesの中ほどに、”Texture Animation”という項目があります。この中の”Num Frames X”と”Num Frames Y”をTouchDesignerで作成したTextureのGrid数に合わせます。この数値を基に画像が均等にスプライト分割されます。次に、その下の”Texture Start Frame Mode”をRandomに設定します。 分割されたスプライトからランダムに、画像がパーティクル毎に貼り付けられます。(はずです)

あとは、お好きなEmitterやAffectorで演出を付けていくことができます。

NDIのパフォーマンス次第になりますが、さらにパターン数の多いTextureを送り付けて、文字列のパターンを増やすこともできそうです。

gitであるファイルを元に戻す方法

元に戻したいファイルのログを表示

foo.txtのログ(変更履歴)を表示する

$ git log foo.txt

実行結果

commit 51ab9a2761dd5f506c8d7ce93f69512c873e1869
Author: Kensuke ARAKAWA <miyavi@ojarumaru.jp>
Date:   Mon Nov 11 17:23:07 2019 +0900

    feat: something

commit 1f5f1d153407402e3a6c45d0d0a27a7b7af46746
Author: Kensuke ARAKAWA <miyavi@ojarumaru.jp>
Date:   Fri Nov 8 19:01:08 2019 +0900

    feat: something

commit 45eeb1882ac48110ac87bd6a6b4b23b6da27be95
Author: Kensuke ARAKAWA <miyavi@ojarumaru.jp>
Date:   Tue Nov 5 18:06:51 2019 +0900

    feat: something

元に戻す

例えば、commit 1f5f1d153407402e3a6c45d0d0a27a7b7af46746 に戻す場合は、

$ git checkout 1f5f1d153407402e3a6c45d0d0a27a7b7af46746 foo.txt
$ git checkout [commit] [filepath]

Webpackで静的なファイルをコピーする方法

CopyWebpackPluginを使って、build時に、JSONファイルなどをバンドルせずに、単体でコピーする方法。

インストール方法

$ npm i -S copy-webpack-plugin write-file-webpack-plugin

file-webpack-pluginを入れることで、debug時に、実際のdistディレクトリにも書き出されるようになります。

webpack.config.js

importを追加

const CopyFilePlugin = require("copy-webpack-plugin");
const WriteFilePlugin = require("write-file-webpack-plugin");

pluginの項目に追加

new CopyFilePlugin(
    [
        {
            context: "src",
            from: "**/*.json",
            to: path.resolve(__dirname, "dist")
        }
    ],
    { copyUnmodified: true }
),
new WriteFilePlugin()

src以下のJSONファイルをdist以下にコピーするという設定。contextで、対象となるディレクトリ/ファイルの親ディレクトリを指定。

参考にしたサイト

https://qiita.com/pepoipod/items/e41105e8f3afd47dc01c
https://codeday.me/jp/qa/20190515/828253.html

TouchDesigner 黙々会2019 #01の成果物

10/23に開催されたTouchDesignerの黙々会の成果物をアップします。

つくったもの

先日、 cyclo. (Ryoji Ikeda, Alva Noto)のLiveを観てきまして、Line Art系のAudio/VisualなものをTouchDesignerで作れないかなと。

成果物

https://github.com/arkwknsk/touchdesigner/tree/master/mokumoku/20191023
MIT Licenseで公開
かなり、ネットワークが汚いですが、お許しを。

サウンド解析

  • ネットワーク左側に、Audio Device In CHOPを配置。別途、サウンドドライバを入れて、PC内部でループさせてYouTubeの音を拾ってきた
  • サウンド解析は、Paletteに入ってるaudioAnalysisを使用。ここから、CHOPでごにょごにょと、音から拾ってきた数字をいじる
  • 閾値の調整や数値のスケールで、かなり映像が変化するので、実際の調整はきりがない。
  • Audio File In CHOPに、手元のMP3ファイルなどを指定して音を鳴らすことも可能

ラインアート

ラインアートを大量に出す方法は、比嘉さんのブログで解説されています
http://satoruhiga.com/TDWS2019/day10/

  • Circle SOPで、四角や円をつくり、Geometory COMPでインスタンシング。位置やサイズに、音解析のデータを加えて、A/V感を。
  • インスタンシングする際に、ベースとなる位置は、ネットワーク真ん中上部のSOPで決めます。形状を複数個つくり、これをスイッチングして、バキッバキッと演出
  • カメラは、視点にNullを指定して、常に中心部分を見るようにし、Projectionは、Orthographicにして、2D感を。

インスタンシングでの位置やスケールを変えれば、いろいろとoFっぽい演出が、TDでもできそうな感じ。

Post Processing

  • フラッシュ効果は、Level TOPのInvertで反転して演出。反転するタイミングも、音解析から持ってくる。
  • その他、色を変えたり、ノイズを載せたり

TypeScriptでlog4jsを使う方法

インストール

$ npm i -S log4js @types/log4js

使い方

コンソールとファイルに、ログを同時出力。

import { configure, getLogger } from "log4js";

configure({
  appenders: {
    console: {
      type: "console"
    },
    logfile: { type: "file", filename: "log/app.log" }
  },
  categories: { default: { appenders: ["console", "logfile"], level: "error" } }
});

const logger = getLogger();

logger.level = "debug";
logger.debug("Some debug messages");
logger.error("aha!");

出力結果

[2019-10-20T10:58:43.835] [DEBUG] default - Some debug messages
[2019-10-20T10:58:43.839] [ERROR] default - aha!

設定を変えると、ログレベルごとに出力先を変えたり、ログの出力のテンプレート(レイアウト)を変更できたりする。

log4jsのドキュメント
https://log4js-node.github.io/log4js-node/

日付の形式について
https://www.npmjs.com/package/date-format