daruma3940の日記

理解や文章に間違い等あればどんなことでもご指摘お願いします

「自分用」liltoonSDFについての備忘録

liltoonSDFについての備忘録

(前提)

・SDFとは

Signed Distance Fieldの略

もともとはフォントなどで使われていたらしい手法だが 最近になってToon調の3Dモデルの影にも使われるようになったようだ

それまではアニメ顔の影については『ギルティギア Xrd』などで使われていた、法線転写という技術を使うことである程度固定の影を出せる技術が確立されていました。

しかし法線を編集するよりもテクスチャーマッピングを利用する方が処理負荷的にもメモリ的にも効率がよく、 キャラごとの法線編集コストもないのでより安定した影を出せるんじゃないかというところから生まれたのではないかと勝手に予想をしています。

そこで効率の良い影を生成するためにSDFアルゴリズムを使って影情報を持った複数枚のテクスチャーから生成したテクスチャーをマスクに利用することで、 固定したアニメ顔影を生成できるので、ライト角度ごとに閾値を持った影のマスクを作って顔にアニメキャラらしいルックを得られるということになります。

[引用元]

UE5 SDF Face Shadowマッピングでアニメ顔用の影を作ろう - Let's Enjoy Unreal Engine

ちなみにSVGなどのベクター画像を綺麗に見せるための方法としてMSDF(Multi-channel signed distance field)なるものもあるらしい

UnityでMSDFを使ったShaderによるベクター画像の描画について #Unity - Qiita

(基本概念)

Toon調の影をつける際に 法線情報から陰影をつけるのではなくテクスチャから影をつけることが出来るようになりたい。

(これまでに見かけた実装方法)

①リッチな実装

影情報を含んだテクスチャを複数枚用意しライトの方向を基にそれらを補完して影をつける。

nagakagachi.hatenablog.com

cgworld.jp

②実用的な実装方法

①の方法(影情報を含んだテクスチャを複数枚用意しライトの方向を基にそれらを合成する)ではテクスチャサイズが大きくなってしまうので それらを最初から合成しておき一枚のテクスチャにしそれだけをモデルに持たせるようにすることで軽量化する。 ただこれだけでは影の情報不足なのでテクスチャだけではなくライトによる影と組み合わせることでうまくそれなりに見せる。

unrealengine.hatenablog.com

(liltoonにおける実装方法)

liltoonにおいては②の実装方法(実用的な実装方法)が用いられているようだ。

(lil_common_frag.hlslの949~962行目を参照(commit 2b3aca0635c29749f19708983e872bb73edc4aef)) github.com

手続きの概略(ミスがあるかもしれません)

① SDFテクスチャからの影(sdf)の計算
  1. ワールド座標における(Skinned Mesh RendererのRoot Boneから見た)右方向(x-が右かは要確認)のベクトルの取得

  2. ライトがRoot Boneから見て右にある場合はshadowStrengthMaskのREDを使用 そうでない場合はGREENを使用

②ライトによる影(lnSDF)の計算
  1. ワールド座標におけるRoot Boneから見た手前方向ベクトルの取得

  2. ライトの向きベクトルと手前方向ベクトルの内積を取り影の強度を計算

③ライトの向きからくる影(lnSDF)+テクスチャを用いた影(sdf)の合成

この記事の内容を見直してみるとliltoonのSDFの処理とほぼ同じであり、作者の方はこの記事を参考にSDFを実装したのだと考えられる。

テクスチャの作り方

このツイートでは「顔の法線調整は必須」と書いてあるがソースコードを見る限りでは顔の法線情報を取得していないように見えるので法線調整は必要ないように思う。

youtu.be Get PERFECT Anime Face Shadows (Easier Way) in Blender

この動画の概要欄にSDFツールのリンクがあるらしい(未検証情報)

ボクセルモデルの作成(自分用) MagicalVoxcel→Blender→Unity

いつも忘れるので備忘録。

 

  • 手順

1:マジカルボクセルでモデリングする。

今回はこんな感じ。これをPLYで出力する。

2:頂点カラーからテクスチャを作成する。

 

2-1:Blenderでplyファイルを読み込む。ファイル→インポート→Standard PLY

(読み込んだ時は色がついていないが別にOK)

 

2-2:全頂点を選択し、Island Marginを0.05にしてUV展開する。

UVEditorでテクスチャを新規作成する。

 

 

2-3:マテリアルを新規作成し、ベースカラーを先ほど作成したテクスチャに。

 

 

現在は頂点カラー情報しかもっていないため、テクスチャに頂点カラーをベイクする。

 

 

2-4:レンダーエンジンをCyclesにしベイクタイプをディフューズ、影響の寄与をカラーのみにする。

 

 

2-5:シェーダーエディターで以下のようにつないでから、

Image Textureが選択(外枠が白くなる)された状態で、プロパティのBakeボタンを押す。

 

2-6:ベイクが終われば以下のようにシェーダーエディターでベースカラーをつなぎ直す。

(ちなみにベイク結果はこんな感じになっている。)

 

3:頂点をマージする

現在は同じ座標に複数の頂点が重なってしまっている状態なので頂点を距離でマージする。

(ちなみに頂点をマージしないと、モデルを動かした際に裏面が見えてしまったりして酷いことになる)

(ちなみに1つ前の手順で頂点カラーをテクスチャにベイクせず頂点をマージしてしまうと頂点が色情報を持っているためマージで色がぐちゃぐちゃになっていた。)

4:Humanoidリグをつける

今回はこんな感じ

5:ウェイトを作成する

今回は自動ウェイトでテキトウにやってしまう

 

(一応ポーズモードでウェイトの確認はする)

6:Blenderでfbxとして書き出しUnityでHumanoidとして読み込む

(省略)

7:テクスチャのMipMapを無効化する

このままだとボクセルの境界線が見えて不格好なのでテクスチャのMipMapをOFFにすることで境界線を見えないようにする。

 

(ちなみにMipMapをGenerateしているとこんな感じ。(よくよく見るとボクセルの境界線が見える))

 

・以上。

ADDRESS1 開発後記

ADDRESS1 開発後記

公開してからだいぶ時間が経ってしまったが、開発を振り返ろうと思う。

”Address1”とかいうタイトル

前作が「天国の一丁目」だったので次は「一番地」だなと思い、 番地と言えばメモリのアドレスだし、次回作タイトルは「メモリの一番地」にするか~

というのがこの作品の全てであり、あとはこのタイトルに合うようにシナリオを書いたりしただけ。

開発期間

本格的な開発を始めたのはこのツイートを見るに"2019-10-27"で

開発開始
開発開始

steam版の初公開が"2023-05-01"で キャラデザや大まかなシナリオの作成は自分のツイートを見る限り"2019-02-06"なので

キャラデザ
キャラデザ
開発期間は大体4年ぐらいか。まあ開発をしていなかった期間や、steam公開後に英語版を作ったりしていたので 正確な開発期間となるともっと曖昧な数字になる。

開発前から開発期間は4年ぐらいにしようと設定していた。 なぜ4年なのかは後述

薄暗い気持ち

正直言って薄暗い気持ちで開発を始めた。 megabitconvention02というのが2019年08月25日に開催されて、無謀にもこれに一度出店をしたことがあって。 私の作ったゲームのクオリティがあまりにも低かったのと集客がヘタクソで誰からも遊んで貰えなくて。 両隣のブースは凄く人気があるのにその間の自分のゲームは誰にも遊んでもらえなくて。 みんな私のゲームをチラッと見ては見なかったことにして素通りしてゆく。 もうひたすらボーっと11:00~16:30までひたすら暇をしていただけで。それだけでかなり精神的にキてしまったんですが、このイベントのあと公開されたメガビットコンベンション02のシューティングゲーム一挙レポート!と銘打った記事にさえ辛うじてシューティングゲームである自分のゲームは紹介されていなかった事が追い打ちになって。 megabitSTG.png

(いいかユズ、ホントのクソゲーってのは酷評されるんじゃなくて無視されるんだぜ。むしろ酷評なんてちゃんと遊んでくれている上に、自分のターゲット層以外にまで自分のゲームが行き届いているというスゲー事だからな。)

こういう舞台に立ってみて初めて、「大学の発表の場」と「商品発表の場」の違いを理解しましたね。 大学の発表は「そもそも周囲の人間が自分の話を聞いてくれるという大前提」があって、 こういう商品発表の場では「そもそも皆自分に対して興味も無く自分の話を聞くつもりもないので、何とかして自分の話は聞く価値があると説得しなければならない所から始まる」ということにあまりにも無自覚だった。

このイベントで隣のブースになった魔神少女STGというゲームを開発した「ひつじさん」という方にどれぐらいの期間開発をされていたのかうかがったところ「4年」という回答が帰ってきたので「自分もそれぐらい頑張れば同じ土俵に立てるのかな」という思いでADDRESS1の開発期間を4年と見積もった。 魔神少女STG

しかしこのイベント直後の時点では「もう2度とゲームなんて作りたくない」ぐらいの気持ちだった。

そのタイミングで「Hellsinker.」と出会ってもう一度だけ、開発をしてみようかなと思った。 しかしまあ、ADDRESS1の開発を始めたのはこのイベントで私を無下に扱った連中への復讐に近い思いからだった。

面白いゲームを作っている製作者のTwitterを見てみると人間性が最悪でガッカリしてしまうことが多いが ゲームや何かしらの作品を完成させるということは割と大変なことで何かしらの「拗らせ」や「悪意」や「名声欲」のような (いい意味でも悪い意味でも)強い感情が無いと難しいことではあるよなと今では思う。(異論は認められるものとする)

ゲームシステム

シューティングゲームにおける接近戦って楽しいしそれに重点を置いたSTGを作ろう!」ぐらいのアイディアで作った。

フリゲ2022得票作品

それをちゃんと理解してくれた人もいてとても嬉しい。

しかし、「上手くタイミングを見計らって接近戦をしかける」というゲームシステムを上手く機能させることが出来たのは「Stage1」だけで、 それ以外ではステージの内容を頭捻って考えるので精いっぱいで、「近接戦システムを上手く機能させよう」というところまでステージの内容を練り上げることが出来なかった。

スコア

当初は「最早スコアなんて不要だろ」と考えていて、要素として付けていなかったのだが、 知り合いにこのゲームを少し遊んでもらってみると「ただ敵の攻撃を避けながらショットを打ち続ければ良いタイプのSTGとはちょっと違うので、一体どういうプレイをすれば良いのか分からない」ようで、それを見てから考えを改め「初めてプレイする人にどのようなプレイが良いプレイなのか教える指標」、つまり「稼ぐもの」というよりは「機械学習エージェントに与える報酬」というスタンスでスコアを設計することにした。

参考作品

初期のゲームシステムを考えるうえで参考にした作品は「Hellsinker.」「らじおぞんで」「空飛ぶ赤いワイン樽」「神威」です。

どれも名作。

ヒトガタハッパ

Address1を作っている最中に「ヒトガタハッパ」というゲームと出会った。 自分は「シューティングゲームにおける接近戦って楽しいしそれに重点を置いたSTGを作ろう!」ぐらいのアイディアしか出なかったにも関わらず、 このゲームはあろうことか「自機を爆弾として敵にぶつけて攻撃する」というのが基本設計で。

しかもそのゲームコンセプトを活かすようなステージを最後まで練り上げることが出来ているし、なにより凄く面白い。 完全に負けたと思った。

このシステムは、「弾幕というものは接近を防ぐために張られるものであり、弾幕を避けきりなおかつ敵に直接打撃を入れてこそ、真に弾幕に勝利したと言える」という作者の主張を表現したものである。

(引用元: pixiv百科事典)

完敗としか言いようがない。

Penryn

元々狂ったようなゲームシステムにしようと思っていたのでキャラデザも狂った感じで。

ペンリン 2019年2月11日
ペンリン 2019年2月11日

Penryn 2019年11月27日
Penryn 2019年11月27日

脳みそがむき出しなのはなんでなのかはここを見てもらった方が早いと思う。(このゲームのシナリオには直接関わってこないことではあるけれど、主人公に「自分と同じコンプレックス」という呪いを与えて、その主人公が救われる物語を作ることで間接的に自分を救いたかった)

というかこういう考えなので、バッドエンドしかないゲームとか作れないんだよな。 どうしてここまで苦労して可愛がって作ったキャラクターに不幸な思いをさせることが出来ようかという気持ちになってしまう。

PenrynとMIA

「頑張って頑張っても目標に手が届かない」のと「頑張って頑張ってようやく目標に手が届いた瞬間にその目標の周囲を覆っていたメッキが剝げ落ち、”自分があれだけ追い求めていたものはこんなにも価値の無いものだったのか”」となるの、どちらが辛いんでしょうね。

ちなみにこのメッキですが、目標に向かって頑張り続けた期間が長ければ長いほどピカピカ輝きを増してゆくので剝がれた時の失望も目標に届かなかった時の失望も大きくなってしまうのが厄介な所だと思います。

PenrynとMerom

Merom 2023年6月15日
Merom 2023年6月15日
同じような生い立ちを持ち、同じ大切なものを持ち、それを(守るため|取り戻す為)に同じように身体改造を加えていった2人ですが それを(守るため|取り戻す為)に真逆の行動を取る2人。 2人の思考と肉体改造はどこか常軌を逸していて、きっと2人とも限界は近かったのでしょう。

Meromをあれだけ過剰に大きくしたのは 「大切なものをこの手で守りたい」という気持ちが過剰なまでになってしまったというメタファー(?)

GameOver時のテキスト

一応テキストの主体がPenrynともMIAとも取れるように書いたはずだけれど、 どれか一つだけPenrynが主体としか取れない文章が存在した記憶がある。

別に主体を私として取っても良いです。

Stage4クリア後メニュー画面のテキストの日本語訳

Menu5

Menu5
Menu5

まるで 肉食動物のように
世界は私に牙を向ける

まるで その獲物であるように
抵抗せずそれを受け入れる
抗っても意味がないことぐらい分かっているから

この身に湧き上がる絶望と痛み
その中でも自身を終わらせることが出来ない私は
一体何をこの世界にまだ望んでいるのだろう

制限され義務付けられた休養の中で
即時的な快楽にすがり全てを見失ってしまう前に
この世界の全てにささやかな反逆を
自らの存在に福音を
かつて確かにそこにあった

自らの存在の意義を

「制限され義務付けられた休養の中で 即時的な快楽にすがり全てを見失ってしまう前に」 というのは、

休日や終業と銘打ちながら「自己研鑽」を強いてくるアレと、 アルコールなどでなんとか毎日騙し騙しやっていきながら自分を見失っている私についての記述です。

というかこの文章自体が私の会社勤めに対するフラストレーションを綴っていますが、まあ許してやって下さい。

BGM

  1. プログラムでステージを作る。
  2. そのあと下表のような形で何分何秒に何が始まるのかを記録する。
  3. この表の中の大事なタイミングで曲調が変わるように曲を作る。(この時点ではだいたいのタイミングでよい)
  4. もう一度プログラムに戻り、曲調が変るタイミングと、大事な事が起こるタイミングがキッチリ合うようにパラメーターを調整する。
Stage4 ms frame diff
敵登場 13.6 0分13.6秒 13600 816 0
WARNING_Start 32.116666 0分32.11秒 32116.666 1926.99996 1110.99996
Merom_人間形態戦闘開始 43.48333333 0分43.48秒 43483.33333 2609
Merom_ロボ変形開始 148.1333333 2分28.13秒 148133.3333 8888 8072
Merom_ロボ変形終了 165.6166667 2分45.61秒 165616.6667 9937
MEROM_ロボ飛び上がり 235.3 3分55.3秒 235300 14118 13302
MEROM_ロボ爆発開始 291.4666667 4分51.46秒 291466.6667 17488 16672
MEROM_上半身形態開始 297.6833333 4分57.68秒 297683.3333 17861 17045
MEROM_上半身形態爆発開始 320.3833333 5分20.38秒 320383.3333 19223 18407
MEROM_上半身形態爆発終了 324.133333 5分24.13秒 324133.333 19447.99998 18631.99998
Kubrick_前で静止 352.65 5分52.65秒 352650 21159 20343
STAGE4END 382.2666666 6分22.26秒 382266.6666 22936 22120

Stage2の道中はかなり音ハメを頑張った(というか音ハメがメインのステージだった)んだけど、 パラメーターを調整するのが面倒で中途半端に投げ出してしまった。

アニメーション制作の現場では、動画と音の同期に関して「動画は音より2フレーム前にすると仕上がりが良い」という「動画先行の原則」が語られてきた。

(引用:映像と音の同期―「動画先行の原則」の根拠と応用)

こういうこともこの時知った。

反省

もっと高級なゲームエンジンを用いて開発を時短すべきだった。

プログラミングパートのほとんどの部分は「アルゴリズムをプログラムで記述すること」ではなく 「パラメーターを適切に調整すること」にあり、それをデフォルトでサポートしてくれるような開発環境(例えばUnityで言うところのInspectorのような機能)を用いるべきだった。 というか最終的にDXライブラリのような環境で開発することにしたとしても 「このコンセプトは最終的に面白いゲームになりえるか」を素早く判断出来るようにするために、プロトタイプだけでも高級なゲームエンジンを用いて素早く作ることが出来るようになっておいた方が良い気がする。

BGMは自作にこだわらず素材を利用してもよかった

作曲が苦手過ぎた。もう本当に曲を作るのが辛かった。 たまたま一曲だけいい曲が作れるだけでは全然ダメで、色々な場面にキッチリと合った曲を作ることが出来なければならない。 きつすぎる。 作曲に関してはいい思い出無いです。

自作にこだわったところで全体としてのクオリティが上がるわけでもないし。

ゲームの進行に合わせて変化するメニュー画面それぞれにBGMをつけたかった。

作曲難しい。

音ハメをもっと丁寧にしたかった。

IKUSAAAN!」とか「Hellsinker.のSegment8」の音ハメすごいよね。 いや~すごいわ。あそこまでやるだけの気力がない。

「敵に上手く近づいて接近戦をしかけるスタイル」を徹底すべきだった。

ステージの内容を頭捻って考えるので精いっぱいで、「近接戦システムを上手く機能させよう」というところまでステージの内容を練り上げることが出来なかった。

結局みんな「過去に遊んだどのゲームに似てるか」ぐらいにしか着目していなかった。

まあそりゃそうか。そりゃそうだよな。 何も知らないゲームの紹介なら「グラフィックが綺麗か」「過去に遊んだゲームの中でどれに似てるか」ぐらいにしか目がいかないよな。

開発者の思っている本質とユーザーの考える本質の間に差があった。

Steamでゲームを公開してから、ありがたいことにレビューやコミュニティハブ等で色々と反応が付いた。好意的な反応はもちろん、手痛い反応でさえもしっかりとプレイしてみた上での感想という感じでとても嬉しいものだった。

私は手痛い反応から「開発者の思っている本質とユーザーの考える本質の間に差がある」ということを教えられた。

ステージの冒頭にあるムービーが長すぎるというのは(開発者はこのゲームに慣れきっており一度でクリアできてしまい同じステージを何度も繰り返すことが無かったので)気が付くことが出来なかったし、開発者からしてみれば「冒頭のムービーのアイディアを考え、ちゃんと実装し上映できること」こそが本質で「ムービーのスキップ機能をつけること」はおまけのような非本質だと考えていたが、これをスキップできる機能はユーザーからしてみれば本質で。

チュートリアルが読みにくいというのも開発者からしてみれば「チュートリアルの内容を考え、それの英訳を作成し、正しくゲーム画面上で再生できること」こそが本質だと考えていたが、「チュートリアルが十分読み終えることが出来る分量&適切な文字送りのスピードか」というのはユーザーからしてみれば本質で。

でもそういうのって作ってる間はなかなか意識が向かないんだよなぁ。(私だけかもしれないが) アイディアを出すことやアイディアがバグを出さずに動いているかとか、そういった方面にばかり気がいってしまう。

一度開発者であることを捨て、全力でユーザーになってみなければ分からないことはとても多いと感じる。 (しかし開発者であることを捨てるのはなかなか難しいものだと痛感する。) (できれば他の誰かにプレイテストをしてもらうのが良いのだろうけど、人望の無い私にはそういう知り合いが居ないので...) (それにもし誰かにプレイテストをしてもらったとしても、そこでの手痛いフィードバックを素直に受け止めることが出来るだけの寛容さが私にあるとも思えない...)

周囲の反応集

フリゲ20XX得票

コンセプトを理解したうえで楽しんでくれて ここまで丁寧に遊んでもらえるとは思わなかったのでとても嬉しい。

merom686氏

https://merom686.hatenablog.com/entry/2023/05/27/152138

とても嬉しい。

MQ 7145氏

紹介中に別のゲームの話をされていたり、Hellsinker.にこういう武器使ってるキャラいたよねぐらいの紹介で無下にされている感は否めない。

discord

知らない外国人(しかも私の書いた絵がアイコン)からフレンド申請が来てて、「怖いなぁ」と思いつつとりあえず承認してみたら、 「I wante to tell you that i like your game」 というメッセージが届いて嬉しくなった。 (英語対応しておいて良かった)

総括

いろいろ嬉しい反応もありましたが、「これでmegabitconvention02の雪辱を晴らすことが出来たか」と問われると「駄目だったよ」というのが正直な所かもしれない。

4年かけて頑張ってみても結局私はこの程度だったということです。

逆に自分がどの程度なのかしっかり知ることが出来たのは良かったのかもしれない。

「Penrynに世界を用意してあげることが出来た。」 「物語を完成させることでPenrynを救うことが出来た。」 それでいいんだ。私程度の人間はそれで”足るを知る”べきなんだ。

今後

このゲームのキャッチコピーは

大切なあの記憶 もう一度だけ この体でもまだ そう思えるのなら

ですが,もはや私は

もう一度だけ なんてもう 思えない...

ので「もうゲーム作ることも無いかな」という気持ちです。 疲れ果てました。お疲れ様でした。

ネタバレ含 映画AWAKEの感想

awake-film.com

note.com

俺もやるか

感想

COM将面のツッコミどころ

まあ俺もAWAKE以後の人間なので細かいところは分かっていないんだけど....

  1. 駒が動くようになる前にalpha-beta実装するか?
  2. Bonanzaソースコード公開以前にKKPを用いたソースコード書いてませんでした?
  3. 「評価関数を作成して機械学習しよう」(KKP使ってただろ)
  4. LazySMPって当時あったっけ?(WCSC27ぐらいからだった気がするんだが)
  5. UIに流れるソースコード

作品としての感想

物語から作者の意図を読み取るなんて俺が一番苦手とするところだよ

低レベル読解力なので間違ってると思うがまあ思ったところを書くか

最後清田が浅川の甥っ子に将棋のアドバイス(?)をしてるシーンは (まあ清田は人間なんだけどコンピューター将棋代表みたいなものとして) 人間とコンピュータが敵同士ではなくて協力してより良い将棋を作り上げてほしいという意図と もっとプロとコンピューターが気軽に対局出来るようになってほしいみたいな意図があったのかなぁと思ったりした(しらんけど)

「2017年 佐藤 VS PONANZA 以降 コンピューターとの公式戦は行われていない」 で締めるのは攻めてるなぁと思った(しらんけど)

埴輪さんの相手を尊重する意味で投了というのは私には読み解けなくてなるほどと思った 確かに28角のシーンでの早すぎる投了と比べてみるとあそこはそういうことだよな。なるほど。

開発環境

良く使っているものに関して製作環境のメモを取っておこうと思う

------------3D
blender 2.8.0 2.7.9
https://www.blender.org/


------------DTM


FL Studio 20
https://www.image-line.com/fl-studio-download/

Studio One 5 Prime
https://www.mi7.co.jp/products/presonus/studioone/prime/


------------外部音源

(FT Studioから見たインストールされたVST一覧)

f:id:daruma3940:20201018132243p:plain



SGM-V2.01(サウンドフォント)
http://www.mediafire.com/file/zo8l3dgf2989266/SGM-V2.01.7z/file

Standard Guitar(サウンドフォント)
キースイッチでアーティキュレーションをつけることが出来、便利
https://unreal-instruments.wixsite.com/unreal-instruments/standard-guitar

TAL Dub Delay (VST 64bit)
(Dubみたいな感じのエコーをかけることが出来る)
https://tal-software.com/products/tal-dub

Ample Bass P Lite II(VST 32+64bit)
(ベース音源 無料音源なのでアーティキュレーションはほとんど使えないが、いい感じのエレキベース音が出る)
http://www.amplesound.net/en/download.asp

Nanotron(32bitVST)
(メロトロン音源)
https://vst4free.com/plugin/288/

sforzando(VST 32+64bit)
(サウンドフォントプレイヤー)
https://unreal-instruments.wixsite.com/unreal-instruments/installation-guide

Dexed (64bitVST)
(シンセ プリセットでいい感じのが入ってる)
https://asb2m10.github.io/dexed/

Synth1VST

https://daichilab.sakura.ne.jp/softsynth/

(Synth1VSTのプリセット)

f:id:daruma3940:20201018132230p:plain



------------フォント
Curves
https://www.dafont.com/curves.font

Marske
https://www.1001fonts.com/marske-font.html

アプリ明朝
https://flopdesign.com/blog/font/5852/


------------絵
Clip Studio Paint
https://www.clipstudio.net/

UIレイアウト
入門教室のおススメ
コンテンツID:1721631
https://assets.clip-studio.com/ja-jp/detail?id=1721631

 

・Aseprite

(ドット絵を描く用途(だいたい下書きはこれでして色塗りはClipStudioでしている))

・Paint.net

(ちょこちょこっと画像を弄る用途)
------------エフェクト作成
Effekseer
(ver150からUIが変更されかなり使いやすくなった)
https://effekseer.github.io/jp/download.html

 

------------プログラミング
Visual Studio 2019  
https://visualstudio.microsoft.com/ja/downloads/

DXライブラリ Ver3.21 
https://dxlib.xsrv.jp/

VSCode
https://azure.microsoft.com/ja-jp/products/visual-studio-code/

 

「自分用」DXライブラリでHLSLシェーダー

新しい記事がQiitaに出ていて、そちらの方が洗練されているので以下記事を参考にした方がいい。
(IKUSAAAAAAAN!の作者さんによる記事だし)
qiita.com

ーーーーーーーーーーーーーーーーーーーーーーーーーーーーーーー
「DXライブラリでピクセルシェーダを使う その1-Quita」を参考にした。
情報がまとまってるページだけど死んでしまっているので「このページを参考にしました!」だけじゃなくてちゃんとどんなことをしたのか書いておこうと思う。






hoge.fx がHLSLシェーダーのソースコード
DXライブラリをダウンロードしたときについてくるShaderCompilier.exeを使ってコンパイルするとhoge.psoというのが作成される。

ShaderCompiler.exe /Tps_2_0 hoge.fx

ここで /Tps_2_0 はピクセルシェーダ2.0を使うということ。
これは32のテクスチャ命令と64の算術命令までしか実行できないので、/Tps_3_0にした方が良いのかもしれない。

DxLib_Init()を呼ぶ前に

SetUseDirect3DVersion(DX_DIRECT3D_9EX);

を呼ぶ必要がある。(これはピクセルシェーダーのバージョンによるかもしれない。)


以下はコードの必要そうな部分を抜き出してきたつぎはぎ(ちゃんと動かないかもしれない)
ーーCPPーーー

#include "DxLib.h"
typedef int ImageHandle;
typedef int ShaderHandle;

ShaderHandle  barreldistort;
ImageHandle imh;
const std::string BarrelDistortshaderpath = "./shader/ShaderCompiler/barreldistort.pso";

int ShaderScreen;
//頂点の設定
VERTEX2DSHADER vertex[4];

void initVertex() {
	for (int i = 0; i < 4; i++)
	{
		vertex[i].pos = VGet((i % 2) * 640.0f, (i / 2) * 640.0f, 0);
		vertex[i].rhw = 1.0f;
		vertex[i].dif = GetColorU8(255, 255, 255, 255);
		vertex[i].spc = GetColorU8(0, 0, 0, 0);
		vertex[i].u = vertex[i].su = (float)(i % 2);
		vertex[i].v = vertex[i].sv = (float)(i / 2);
	}
}


void TestBarrelShader() {
	float mousex = float(MyMouse::posx) / 640.0f;
	float mousey =float(MyMouse::posy) / 640.0f;
	

	SetDrawScreen(ShaderScreen);

	
	DrawModiGraph(0, 0, 640, 0, 640, 480, 0, 480, imh, TRUE);

	SetDrawScreen(DX_SCREEN_BACK); 
   //定数渡し
	SetUseTextureToShader(0, ShaderScreen);//0なのでs0
	SetPSConstSF(0, 1.30f);//0なのでc0
	SetPSConstSF(1, 2.0f);//0なのでc1

	SetPSConstSF(2, mousex);//0なのでc2
	SetPSConstSF(3, mousey);//0なのでc3

  //シェーダーを適用
	SetUsePixelShader(barreldistort);
	DrawPrimitive2DToShader(vertex, 4, DX_PRIMTYPE_TRIANGLESTRIP);


}

int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance,
						 LPSTR lpCmdLine, int nCmdShow )
{
	SetUseDirect3DVersion(DX_DIRECT3D_9EX);//これを入れないとシェーダーが使えない

	ChangeWindowMode(TRUE);
	if( DxLib_Init() == -1 )	// DXライブラリ初期化処理
	{
		 return -1;				// エラーが起きたら直ちに終了
	}
       imh = (ImageHandle)LoadGraph("BG.png");
      const std::string BarrelDistortshaderpath = "./shader/barreldistort.pso";

      barreldistort = LoadPixelShader(BarrelDistortshaderpath.c_str());


       ShaderScreen = MakeScreen(640, 480);
	initVertex();
	while (!ProcessMessage() && !ClearDrawScreen() && !Key[KEY_INPUT_ESCAPE])
	{

		SetDrawScreen(DX_SCREEN_BACK);
		// 画面をクリア

		ClearDrawScreen();
		
		
		//画面の更新処理
		{
	
			TestBarrelShader();
		
		}
		MousePos();

	
		ScreenFlip();
	
	
		if (ProcessMessage() != 0) break;

	}

	
	DxLib_End() ;				// DXライブラリ使用の終了処理

	return 0 ;					// ソフトの終了
}

ーーHLSLーー
これBarrelDistortのプログラム。
t!=1.0にしたときの境界があんまりきれいにならないので上手い処理の方法があれば教えてください
PSいい感じになりました(注意)無理矢理画像の縦幅と横幅を640:640にしているので元のInput画像が縦に拡大されてしまっています)
https://www.geeks3d.com/20140213/glsl-shader-library-fish-eye-and-dome-and-barrel-distortion-post-processing-filters/2/

struct PS_INPUT
{
    float4 DiffuseColor       : COLOR0 ;
    float4 SpecularColor      : COLOR1 ;
    float2 TextureCoord0      : TEXCOORD0 ;
    float2 TextureCoord1      : TEXCOORD1 ;
} ;

// ピクセルシェーダーの出力
struct PS_OUTPUT
{
    float4 Output             : COLOR0 ;
} ;


sampler Texture : register( s0 ) ;

float BarrelPower : register( c0 );
float t : register( c1 );

float mousex : register( c2 );
float mousey : register( c3 );

PS_OUTPUT main( PS_INPUT PSInput )
{
    PS_OUTPUT PSOutput ;

    float2 xy=2.0*PSInput.TextureCoord0.xy-1.0;
    float2 mouse;
    mouse.x=mousex;
    mouse.y=mousey;
    mouse=2.0*mouse.xy-1.0;
    
    float2 xy2=t*(xy-mouse);
    float dist=length(xy2);
    float2 CalcPos;
    float4 TextureColor;

    if(dist>=1.0){
        CalcPos=PSInput.TextureCoord0.xy;
        TextureColor = tex2D( Texture , CalcPos );
    }
    else
    {
        float theta=atan2(xy2.y,xy2.x);
        float dist2=pow(dist,BarrelPower);
        //float dist2=dist*t;

        CalcPos.x=dist2*cos(theta);
        CalcPos.y=dist2*sin(theta);
        CalcPos*=1.0/t;
        CalcPos+=mouse;
        CalcPos=0.5*(CalcPos+1.0);
        TextureColor = tex2D( Texture , CalcPos );
        TextureColor.rgb  -= clamp(0.3*(1.0-dist),0.0,0.8);
    }
     
    PSOutput.Output = TextureColor;
    return PSOutput;
}

こんな感じになる

https://twitter.com/daruma3940/status/1199724459499802624?s=20

Magma Live 行ってきた

アンコール含めて2時間3曲。
まあ1曲はメドレーなので3曲とカウントしてよいかは怪しい。

1,Kohntarkorz
メンバーが舞台に上がってきてハーヴ・アクニンによる「ハマタイ」の掛け声から唐突に始まる。
こういったライブではまず最初にメンバーによる挨拶とかがあるんだろうなと勝手に思っていて「ハマタイ」からメンバーによる挨拶が始まるんだろうと思っていたが、
ハマタイ」の後楽器がジャーンと鳴り始めてここでようやくKohntarkorzが始まったことに気が付いた。

緊張していて何があったのかあまり覚えていない。

2,Theusz hamtaahk Trirogy Medley

(ちゃんと覚えているわけではないが)
Makawelekaahmが終わったらZeuhl wortzまで飛ぶ。
Slibendi deh theuszも飛ばされていた。
Zortsungをし、そこから唐突にWurdah ItahのWainsahtへ。

Wurdah Itahはあんまり聞いていないのでどこを飛ばしていたかは分からない。
多分そこから先はほとんどフルでやっていたように思う。

そこからMDKのDa Zeuhl wortz mekanik, Nebehr gudahtt,MKで終了。

Medleyでは中途半端になってしまうのでTheusz hamtaahkかMDKを一曲やってほしかった感があるが。
2時間という時間の制限でうまくやろうとした結果なのかもしれない、
Nebehr gudahttはヴァンデが歌っていたが苦しそうだった。

3,De Futura
ブゾネのベースがすごかった。というかこの曲に限らずこのバンドやはりベースがすごい。
ベースをずっと見ていたい気持ちになるがハーヴ・アクニンがベースの前にかぶってきたりしてほげほげした。
ベースが遊びを入れてもいいようなところであんまり遊びを入れてないような気がしたが腕が痛そうにしていたので仕方ないのかもしれない。
ビブラフォンが音板と音板の間にバチを歯間ブラシを歯と歯の間に通すようにこすりつけて音を出していたりしてそんなこともできるのかと思った。


感想

非日常的な空間すぎてどういう感情を抱くべきなのか分からなかった。
多分すごかったんだとおもう。たぶん。しかしそれと同時にまあこんなもんなのかという気持ちにもなった。
私の今の感受性の問題かもしれない。