HN 日本語サマリー

← 一覧へ戻る
プログラミング

SQLによるレイトレーサー

Ray Tracer in SQL (github.com)

40 pointsby kbumsik11 コメント

要約

このプロジェクトは、ClickHouse SQLクエリのみを使用してレイトレーサーを実装しています。UDFや外部コードを使わず、単一のSELECT文で画像をPNG形式で出力します。Andrew KenslerのPixar名刺レイトレーサーに触発され、「ClickHouse」という単語をガラスやクロムの文字としてレンダリングし、手続き的に生成された風景の上に浮かべます。

全文翻訳

RayTracer — ClickHouse SQLによるレイトレーサー ClickHouse SQLクエリのみで完全に記述されたパストレーサーで、ClickHouseのPNG出力形式を介してPNGに直接レンダリングします。UDFも外部コードも使用せず、単一のSELECTで各ピクセルを計算します。これは、Andrew Kenslerの有名なPixar名刺レイトレーサーの精神に基づき、「ClickHouse」という単語をガラス質でクロムメッキの文字としてレンダリングし、上のシーンでは、手続き的に生成された風景の上に浮かべ、地形を反射し、丘に影を落とします。 関連項目: NoiSQL — SQLクエリで音楽を生成する SQL Mandelbrot Benchmark Click-V: ClickHouse SQLで構築されたRISC-Vエミュレーター DOOMHouseは、3Dグラフィックスを完全にClickHouse SQLでレンダリングする「Doomのような」ゲームエンジンです 仕組み レンダラー全体は1つのクエリに含まれています。 ピクセルは行です。numbers_mt(width * height * samples)は(ピクセル、サンプル)ごとに1行を生成します。サンプルはGROUP BY pixelで平均化され、出力列r, g, b ([0, 1]内) と明示的なx, y座標列 (pixel % width, intDiv(pixel, width)) がPNG出力形式に書き込まれます。明示的な座標により、ライターは各ピクセルをその位置によって配置できるため、行にORDER BYは不要で、重いピクセルごとの作業はすべてのコアで並列に実行されます。 タプルでの3D数学。ベクトルはTuple(Float64, Float64, Float64)です。dotProduct, L2Normalize, tuplePlus, tupleMultiplyByNumber, …が線形代数を実行し、短いラムダエイリアス (va, vs, vm, vd, vn, vc, vref) でラップされています。 バウンスループはarrayFoldです。各レイは、range(maxDepth)に対する各フォールドステップで正確に1回のミラーバウンスを進みます。これは各行内のループであるため、行は独立したままで、レンダリングはすべてのCPUコアで並列化されます。(最初のバージョンではWITH RECURSIVE CTEを使用していました — 下のクエリを参照してください。) arrayMapを介したletバインディング。ClickHouse WITHラムダはcall-by-nameであるため、値をパラメータとして渡すと式が再展開され、クエリツリーが膨れ上がります。そのため、中間値はarrayMap(x -> body, [expr])[1]という1要素配列の「let」で値によってバインドされます。 ジオメトリ (構成的ソリッドジオメトリ) シリンダー — 直線ストローク (l, i, k, H, u, eの横棒) 用の平らなキャップ付きの丸棒。 トーラス — 丸い文字 (C, c, o, u, s, e) は、符号付き距離フィールドを介してレイマーチされます。C/c/s/eの開口部は、リングから減算されたボックスです。 球 — iの点と、球から球を引いたクロムの「惑星」です。 指向性ボックス / 平行六面体 — 平らな面のストロークに利用できます。 したがって、このシーンでは、ボックス、シリンダー、トーラス、球が、CSGのユニオン、差分 (惑星と文字の開口部)、およびレイマーチされた距離フィールド (トーラス) で活用されています。 地形 高さフィールド z = amp · fBm(x, y) は、fBmがラティス値ノイズのいくつかのオクターブを合計したものです。カメラのレイはそれに対してレイマーチされます — マーチは空の空気 (レイが地形の最大高さに最初に落ちる場所から始まる) をスキップし、表面の交差を線形補間するため、高速でステップバンディングがありません。これは、高さカラーランプ (水 → 砂 → 草 → 岩 → 雪)、暖かい太陽と冷たい空のアンビエントモデル、マーチされた影 (地形の自己影と文字の落とす影)、そして空への距離フォグでシェーディングされます。 ギャラリー ClickBulb — 球体のみで作られたデスクランプが飛び跳ね、バナーの後ろに隠れ、文字の隙間から光を浴びせ、それから顔を出してあなたを覗き込みます。すべてのフレームは同じClickHouse SQLクエリをフレームごとに1回実行します (高品質ビデオ)。 Pixarへのオマージュ — 球プリミティブのユニオンとしての文字、チェッカーボード上のクロム。 CSGプリミティブ — シリンダー、トーラス、球から彫り出された文字。 Perlin地形 — スタンドアロンのレイマーチされた高さフィールド。 結合 — 地形上のClickHouse (上のヒーロー画像)。 実行 queries/内のすべてのファイルは完全で自己完結型であり、パラメータ化されています。画像サイズはClickHouseの画像出力設定 (SQLでgetSettingで読み取り) から、ピクセルあたりのサンプル数は{SAMPLES:UInt32}クエリパラメータから取得されます。1つのクエリで任意の解像度をレンダリングできます。次のようにレンダリングします。 ```sql clickhouse local --output_format_image_width 2560 --output_format_image_height 1200 \ --param_SAMPLES 8 --queries-file queries/clickhouse_terrain.sql > out.png ``` クエリ シーン 解像度 clickhouse_raytracer.sql Pixarへのオマージュ、WITH RECURSIVEバウンスループ 640 × 256 clickhouse_raytracer_loop.sql 同一シーン、arrayFoldループ (並列、高速) 640 × 256 clickhouse_raytracer_primitives.sql CSGプリミティブから彫り出された文字 1280 × 512 terrain.sql Perlinノイズ地形 896 × 504 clickhouse_terrain.sql 地形上のClickHouse (ヒーロー画像) 2560 × 1200 クエリはgenerators/内のPythonジェネレーターによって出力されます。シーンとバウンス深度は生成時に焼き付けられますが、画像サイズとピクセルあたりのサンプル数は、出力されるクエリの実行時パラメータとして保持されます。たとえば、ヒーロー画像を再作成するには: ```bash python3 generators/gen_combined.py 2560 1200 8 2 > scene.sql # depth 2; W/H/samples are runtime clickhouse local --output_format_image_width 2560 --output_format_image_height 1200 \ --param_SAMPLES 8 --queries-file scene.sql > scene.png ``` 任意のテキストのレンダリング 球体バナーのジェネレーター (gen.pyとより高速なgen_fold.py) は、オプションで5番目の引数としてレンダリングするテキストを受け取ります。これはgenerators/font.pyにある7行のビットマップフォント (大文字A–Z、数字、一般的な句読点; 元の大小文字混在の「ClickHouse」グリフは保持されるため、デフォルトのレンダリングは変更されません) からレイアウトされ、カメラ、ライト、クロム球はバナーの中心に自動的に再配置されます。 ```bash python3 generators/gen_fold.py 640 256 16 4 "HELLO SQL" > hello.sql clickhouse local --output_format_image_width 640 --output_format_image_height 256 \ --param_SAMPLES 16 --queries-file hello.sql > hello.png ``` レンダリングせずにバナーをASCIIアートとしてプレビューするには: ```bash python3 generators/font.py "HELLO SQL" ``` 他のデータベースでの試行 🐛 CedarDB: 動作するが、33倍遅く、バグがある: cedardb/issues#71 ☠️ DuckDB: 動作しない、配列と再帰CTEで複数試したが、最小解像度の画像でさえ処理できない。ベンチマークを参照。 クレジット Andrew Kenslerの名刺レイトレーサーとPaul Heckbertのミニマルなレイトレーサーに触発され、純粋なClickHouse SQLとして再考されました。 ライセンス Creative Commons Attribution-NonCommercial-ShareAlike 4.0、ClickBenchと同じライセンス。