three实现动态三维字母融合变形倒影动画效果代码
代码语言:html
所属分类:动画
代码描述:three实现动态三维字母融合变形倒影动画效果代码
代码标签: three 动态 三维 字母 融合 变形 倒影 动画
下面为部分代码预览,完整代码请点击下载或在bfwstudio webide中打开
<!DOCTYPE html> <html lang="en" > <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width,initial-scale=1,minimal-ui,shrink-to-fit=no,viewport-fit=cover"> <meta name="apple-mobile-web-app-capable" content="yes"> <meta name="mobile-web-app-capable" content="yes"> <meta name="description" content="Dynamic liquid letters with reflections"> <link rel='stylesheet' href='https://fonts.googleapis.com'> <link rel='stylesheet' href='https://fonts.gstatic.com'> <link rel='stylesheet' href='https://fonts.googleapis.com/css2?family=Cal+Sans&display=swap'> <style> *, *::after, *::before { box-sizing: border-box; } :root { font-size: 12px; --color-text: #000; --color-bg: #52a0b2; --color-link: #000; --color-link-hover: #000; --page-padding: 1.5rem; } @font-face Cal Sans { font-family: "Cal Sans", sans-serif; font-weight: 400; font-style: normal; } body { margin: 0; color: var(--color-text); background-color: var(--color-bg); font-family: sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; height: 100dvh; overflow: clip; } canvas { display: block; /* make the canvas act like a block */ width: 100%; /* make the canvas fill its container */ height: 100%; } .warning-message { position: absolute; top: 50%; left: 50%; transform: translate(-50%, -50%); background: rgba(0, 0, 0, 0.8); color: white; padding: 20px; border-radius: 10px; font-weight: bold; text-align: center; z-index: 1000; display: none; } .content { padding: var(--page-padding); display: flex; flex-direction: column; width: 100vw; position: relative; @media screen and (min-width: 53em) { min-height: 100dvh; justify-content: center; align-items: center; } } </style> </head> <body translate="no"> <canvas style="cursor: -webkit-grabbing;"></canvas> <div id="webgpu-warning" class="warning-message"> WebGPU is not supported in your browser. Please try using the latest version of Chrome or Edge. </div> <script type="module"> import * as THREE from "//unpkg.com/three?module"; var Gr = Object.defineProperty; var Rr = (n, e, t) => e in n ? Gr(n, e, { enumerable: !0, configurable: !0, writable: !0, value: t }) : (n[e] = t); var Pn = (n, e, t) => Rr(n, typeof e != "symbol" ? e + "" : e, t); (function () { const e = document.createElement("link").relList; if (e && e.supports && e.supports("modulepreload")) return; for (const r of document.querySelectorAll('link[rel="modulepreload"]')) i(r); new MutationObserver((r) => { for (const o of r) if (o.type === "childList") for (const a of o.addedNodes) a.tagName === "LINK" && a.rel === "modulepreload" && i(a); }).observe(document, { childList: !0, subtree: !0 }); function t(r) { const o = {}; return ( r.integrity && (o.integrity = r.integrity), r.referrerPolicy && (o.referrerPolicy = r.referrerPolicy), r.crossOrigin === "use-credentials" ? (o.credentials = "include") : r.crossOrigin === "anonymous" ? (o.credentials = "omit") : (o.credentials = "same-origin"), o ); } function i(r) { if (r.ep) return; r.ep = !0; const o = t(r); fetch(r.href, o); } })(); function nr(n, e) { n = n.split(";"); let t = []; const i = /group\(([^)]+)\)/, r = /binding\(([^)]+)\)/; return ( n.forEach((o, a) => { if (o.includes("@group")) { const s = Number(i.exec(o)[1]), u = Number(r.exec(o)[1]); if ( (t[s] == null && (t[s] = []), o.includes("uniform") || o.includes("storage")) ) { let c = ""; o.includes("storage") && (c = o.includes("read_write") ? "storage" : "read-only-storage"), o.includes("uniform") && (c = "uniform"), (t[s][u] = { binding: u, visibility: e, buffer: { type: c } }); } if (o.includes("texture_")) { let c = "2d"; if ( (o.includes("_3d") && (c = "3d"), o.includes("_1d") && (c = "1d"), o.includes("_2d") && o.includes("array") && (c = "2d-array"), o.includes("texture_storage")) ) t[s][u] = { binding: u, visibility: e, storageTexture: { format: o.includes("unorm") ? "rgba8unorm" : "rgba32float", viewDimension: c } }; else { let m = "float", p = "2d"; o.includes("texture_3d") && (p = "3d"), o.includes("texture_1d") && (p = "1d"), o.includes("_2d") && o.includes("array") && (p = "2d-array"), (t[s][u] = { binding: u, visibility: e, texture: { sampleType: m, viewDimension: p } }); } } o.includes("sampler") && (t[s][u] = { binding: u, visibility: e, sampler: { type: "filtering" } }); } }), t ); } Promise.create = function () { const n = new Promise((e, t) => { (this.temp_resolve = e), (this.temp_reject = t); }); return ( (n.resolve = this.temp_resolve), (n.reject = this.temp_reject), delete this.temp_resolve, delete this.temp_reject, n ); }; var G = null; let kr = async (n) => { var t; const e = await ((t = navigator.gpu) == null ? void 0 : t.requestAdapter()); return ( (G = await (e == null ? void 0 : e.requestDevice({ requiredFeatures: ["float32-filterable"] }))), G || (console.log("error finding device"), null) ); }, rr = async (n) => { try { return await (await fetch(n)).text(); } catch { return n; } }, Oe = async (n) => { const e = await rr(n), t = G.createShaderModule({ label: `${n} module`, code: e }), r = nr(e, GPUShaderStage.COMPUTE).map((s) => G.createBindGroupLayout({ entries: s }) ), o = G.createPipelineLayout({ bindGroupLayouts: r }); return { pipeline: G.createComputePipeline({ label: `${n} pipeline`, layout: o, compute: { module: t, entryPoint: "main" } }) }; }; class ir { constructor() { Pn(this, "setBindGroup", (e) => { this.bindGroup = G.createBindGroup({ label: `${this.label} bind group`, layout: this.pipeline.getBindGroupLayout(0), entries: e }); }); (this.label = null), (this.passDescriptor = null), (this.pipeline = null), (this.bindGroup = null), (this.uniformsData = null), (this.uniformsBuffer = null); } } async function gn(n, e, t = 1, i, r = !0) { let o = new ir(); const a = await rr(e), s = G.createShaderModule({ label: `${n} module`, code: a }), c = nr(a, GPUShaderStage.VERTEX | GPUShaderStage.FRAGMENT).map((h) => G.createBindGroupLayout({ entries: h }) ), m = G.createPipelineLayout({ bindGroupLayouts: c }); let p = { label: `${n} pipeline`, layout: m, vertex: { module: s, entryPoint: "vs" }, fragment: { module: s, entryPoint: "fs", targets: i }, primitive: { topology: "triangle-list", cullMode: "none" }, multisample: { count: t } }; const d = { label: `${n} rendering pass descriptor`, colorAttachments: [] }; r && ((p.depthStencil = { depthWriteEnabled: !0, depthCompare: "less", format: "depth32float" }), (d.depthStencilAttachment = { depthClearValue: 1, depthStoreOp: "store" })); const g = G.createRenderPipeline(p); return ( i.map((h) => { d.colorAttachments.push({ clearValue: [0, 0, 0, 0], storeOp: "store" }); }), (o.label = n), (o.pipeline = g), (o.passDescriptor = d), o ); } async function re(n, e, t = null, i = null) { let r = new ir(), o = Promise.create(); if ( (Oe(e).then((a) => { (r.pipeline = a.pipeline), o.resolve(); }), await o, (r.label = n), t && ((r.uniformsData = new Float32Array(t)), (r.uniformsBuffer = G.createBuffer({ label: `${n} uniforms buffer`, size: r.uniformsData.byteLength, usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST })), G.queue.writeBuffer(r.uniformsBuffer, 0, r.uniformsData)), i) ) { let a = i.map((s, u) => ({ binding: u, resource: { buffer: s == "uniforms" ? r.uniformsBuffer : s } })); r.bindGroup = G.createBindGroup({ label: `${n} bind group`, layout: r.pipeline.getBindGroupLayout(0), entries: a }); } return console.log(`${n} ready`), r; } var Lr = `struct Uniforms { axis: vec3f, steps: f32 } @group(0) @binding(0) var textureRead: texture_3d<f32>; @group(0) @binding(1) var textureSave: texture_storage_3d<rgba32float, write>; @group(0) @binding(2) var<uniform> uniforms: Uniforms; @compute @workgroup_size(1) fn main( @builtin(global_invocation_id) ud: vec3<u32> ) { var tSize = vec3f(textureDimensions(textureRead)); var id = ud + vec3u( u32(tSize.x * 0.2), 0, 0); var blend = vec4f(0.); var blend2 = vec4f(0.); var sum = 1.; var sum2 = 0.; var m = 1.; var n = uniforms.steps; for(var i = 0.; i < uniforms.steps; i += 1.) { var j = i - 0.5 * uniforms.steps; var tRead = textureLoad(textureRead, vec3<i32>(id) + vec3<i32>(j * uniforms.axis), 0); blend += m * tRead; blend2 += tRead; m *= (n - i) / (i + 1.); sum += m; sum2 += 1.; } blend /= sum; blend2 /= sum2; var mixer = 1.; blend = mixer * blend + (1. - mixer) * blend2; textureStore(textureSave, id, blend ); }`; let Sn = !1, kt, Kt = []; const zr = (n) => { let e = [ [1, 0, 0, 1], [0, 0, 1, 1], [0, 1, 0, 1] ]; for (let t = 0; t < 3; t++) { let i = new Float32Array(e[t]), r = n.createBuffer({ label: "uniforms buffer", size: i.byteLength, usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST }); n.queue.writeBuffer(r, 0, i), Kt.push(r); } }; async function Mr(n, e, t) { let i = G; if (!Sn) { zr(i); let d = Promise.create(); Oe(Lr).then((g) => { (kt = g.pipeline), d.resolve(); }), await d, (Sn = !0); } let r = t * 2, o = [ [1, 0, 0, r], [0, 0, 1, r], [0, 1, 0, r] ]; for (let d = 0; d < 3; d++) { let g = new Float32Array(o[d]); i.queue.writeBuffer(Kt[d], 0, g); } const a = i.createCommandEncoder({ label: "encoder" }), s = a.beginComputePass({ label: "blur3D pass" }); s.setPipeline(kt); let u = n.width, c, m; for (let d = 0; d < 3; d++) { let g = d % 2 == 0; (c = g ? n : e), (m = g ? e : n); const h = i.createBindGroup({ label: "bind group for blur3D", layout: kt.getBindGroupLayout(0), entries: [ { binding: 0, resource: c.createView({ baseMipLevel: 0, mipLevelCount: 1 }) }, { binding: 1, resource: m.createView({ baseMipLevel: 0, mipLevelCount: 1 }) }, { binding: 2, resource: { buffer: Kt[d] } } ] }); s.setBindGroup(0, h), s.dispatchWorkgroups(u * 0.6, u, u); } s.end(); const p = a.finish(); i.queue.submit([p]); } var at = typeof Float32Array < "u" ? Float32Array : Array; Math.hypot || (Math.hypot = function () { for (var n = 0, e = arguments.length; e--; ) n += arguments[e] * arguments[e]; return Math.sqrt(n); }); function $() { var n = new at(16); return ( at != Float32Array && ((n[1] = 0), (n[2] = 0), (n[3] = 0), (n[4] = 0), (n[6] = 0), (n[7] = 0), (n[8] = 0), (n[9] = 0), (n[11] = 0), (n[12] = 0), (n[13] = 0), (n[14] = 0)), (n[0] = 1), (n[5] = 1), (n[10] = 1), (n[15] = 1), n ); } function Cn(n, e) { var t = e[0], i = e[1], r = e[2], o = e[3], a = e[4], s = e[5], u = e[6], c = e[7], m = e[8], p = e[9], d = e[10], g = e[11], h = e[12], v = e[13], w = e[14], E = e[15], L = t * s - i * a, b = t * u - r * a, x = t * c - o * a, y = i * u - r * s, S = i * c - o * s, Le = r * c - o * u, ze = m * v - p * h, Me = m * w - d * h, Ie = m * E - g * h, Ne = p * w - d * v, Fe = p * E - g * v, Ve = d * E - g * w, O = L * Ve - b * Fe + x * Ne + y * Ie - S * Me + Le * ze; return O ? ((O = 1 / O), (n[0] = (s * Ve - u * Fe + c * Ne) * O), (n[1] = (r * Fe - i * Ve - o * Ne) * O), (n[2] = (v * Le - w * S + E * y) * O), (n[3] = (d * S - p * Le - g * y) * O), (n[4] = (u * Ie - a * Ve - c * Me) * O), (n[5] = (t * Ve - r * Ie + o * Me) * O), (n[6] = (w * x - h * Le - E * b) * O), (n[7] = (m * Le - d * x + g * b) * O), (n[8] = (a * Fe - s * Ie + c * ze) * O), (n[9] = (i * Ie - t * Fe - o * ze) * O), (n[10] = (h * S - v * x + E * L) * O), (n[11] = (p * x - m * S - g * L) * O), (n[12] = (s * Me - a * Ne - u * ze) * O), (n[13] = (t * Ne - i * Me + r * ze) * O), (n[14] = (v * b - h * y - w * L) * O), (n[15] = (m * y - p * b + d * L) * O), n) : null; } function Jt(n, e, t) { var i = e[0], r = e[1], o = e[2], a = e[3], s = e[4], u = e[5], c = e[6], m = e[7], p = e[8], d = e[9], g = e[10], h = e[11], v = e[12], w = e[13], E = e[14], L = e[15], b = t[0], x = t[1], y = t[2], S = t[3]; return ( (n[0] = b * i + x * s + y * p + S * v), (n[1] = b * r + x * u + y * d + S * w), (n[2] = b * o + x * c + y * g + S * E), (n[3] = b * a + x * m + y * h + S * L), (b = t[4]), (x = t[5]), (y = t[6]), (S = t[7]), (n[4] = b * i + x * s + y * p + S * v), (n[5] = b * r + x * u + y * d + S * w), (n[6] = b * o + x * c + y * g + S * E), (n[7] = b * a + x * m + y * h + S * L), (b = t[8]), (x = t[9]), (y = t[10]), (S = t[11]), (n[8] = b * i + x * s + y * p + S * v), (n[9] = b * r + x * u + y * d + S * w), (n[10] = b * o + x * c + y * g + S * E), (n[11] = b * a + x * m + y * h + S * L), (b = t[12]), (x = t[13]), (y = t[14]), (S = t[15]), (n[12] = b * i + x * s + y * p + S * v), (n[13] = b * r + x * u + y * d + S * w), (n[14] = b * o + x * c + y * g + S * E), (n[15] = b * a + x * m + y * h + S * L), n ); } function Ir(n, e, t, i, r) { var o = 1 / Math.tan(e / 2), a; return ( (n[0] = o / t), (n[1] = 0), (n[2] = 0), (n[3] = 0), (n[4] = 0), (n[5] = o), (n[6] = 0), (n[7] = 0), (n[8] = 0), (n[9] = 0), (n[11] = -1), (n[12] = 0), (n[13] = 0), (n[15] = 0), r != null && r !== 1 / 0 ? ((a = 1 / (i - r)), (n[10] = (r + i) * a), (n[14] = 2 * r * i * a)) : ((n[10] = -1), (n[14] = -2 * i)), n ); } var Nr = Ir; function U() { var n = new at(3); return at != Float32Array && ((n[0] = 0), (n[1] = 0), (n[2] = 0)), n; } function ae(n, e, t) { var i = new at(3); return (i[0] = n), (i[1] = e), (i[2] = t), i; } function Zt(n, e, t) { return (n[0] = e[0] + t[0]), (n[1] = e[1] + t[1]), (n[2] = e[2] + t[2]), n; } function $e(n, e, t) { return (n[0] = e[0] - t[0]), (n[1] = e[1] - t[1]), (n[2] = e[2] - t[2]), n; } function _e(n, e, t) { return (n[0] = e[0] * t), (n[1] = e[1] * t), (n[2] = e[2] * t), n; } function Tn(n, e) { return (n[0] = -e[0]), (n[1] = -e[1]), (n[2] = -e[2]), n; } function Xe(n, e) { var t = e[0], i = e[1], r = e[2], o = t * t + i * i + r * r; return ( o > 0 && (o = 1 / Math.sqrt(o)), (n[0] = e[0] * o), (n[1] = e[1] * o), (n[2] = e[2] * o), n ); } function I(n, e) { return n[0] * e[0] + n[1] * e[1] + n[2] * e[2]; } function En(n, e, t) { var i = e[0], r = e[1], o = e[2], a = t[0], s = t[1], u = t[2]; return ( (n[0] = r * u - o * s), (n[1] = o * a - i * u), (n[2] = i * s - r * a), n ); } function lt(n, e, t) { var i = e[0], r = e[1], o = e[2], a = t[3] * i + t[7] * r + t[11] * o + t[15]; return ( (a = a || 1), (n[0] = (t[0] * i + t[4] * r + t[8] * o + t[12]) / a), (n[1] = (t[1] * i + t[5] * r + t[9] * o + t[13]) / a), (n[2] = (t[2] * i + t[6] * r + t[10] * o + t[14]) / a), n ); } var be = $e; (function () { var n = U(); return function (e, t, i, r, o, a) { var s, u; for ( t || (t = 3), i || (i = 0), r ? (u = Math.min(r * t + i, e.length)) : (u = e.length), s = i; s < u; s += t ) (n[0] = e[s]), (n[1] = e[s + 1]), (n[2] = e[s + 2]), o(n, n, a), (e[s] = n[0]), (e[s + 1] = n[1]), (e[s + 2] = n[2]); return e; }; })(); class Fr { constructor(e) { (this.block = !1), (this.position = U()), (this.down = !1), (this.prevMouseX = 0), (this.prevMouseY = 0), (this.currentMouseX = 0), (this.currentMouseY = 0), (this.alpha = Math.PI * 0.5), (this.beta = -Math.PI * 0.5), (this._alpha = this.alpha), (this._beta = this.beta), (this._alpha2 = this.alpha), (this._beta2 = this.beta), (this.gaze = !0), (this.ratio = 1), (this.init = !0), (this.target = [0.5, 0.35, 0.5]), (this.lerp = 0.1), (this.lerp2 = 0.1), (this.perspectiveMatrix = $()), (this.cameraTransformMatrix = $()), (this.orientationMatrix = $()), (this.transformMatrix = $()), (this.transformMatrixReflection = $()), (e.style.cursor = "-moz-grab"), (e.style.cursor = " -webkit-grab"), document.addEventListener( "mousemove", (t) => { (this.currentMouseX = t.clientX), (this.currentMouseY = t.clientY); }, !1 ), document.addEventListener( "mousedown", (t) => { (e.style.cursor = "-moz-grabbing"), (e.style.cursor = " -webkit-grabbing"), (this.down = !0); }, !1 ), document.addEventListener( "mouseup", (t) => { (e.style.cursor = "-moz-grab"), (e.style.cursor = " -webkit-grab"), (this.down = !1); }, !1 ); } updateCamera(e, t, i) { if ( ((this.ratio = i), Nr(this.perspectiveMatrix, (e * Math.PI) / 180, t, 0.01, 1e3), this.block || (this.down && ((this.alpha -= (0.1 * (this.currentMouseY - this.prevMouseY) * Math.PI) / 180), (this.beta += (0.1 * (this.currentMouseX - this.prevMouseX) * Math.PI) / 180)), this.alpha <= 0.3 * Math.PI && (this.alpha = 0.3 * Math.PI), this.alpha >= 0.52 * Math.PI && (this.alpha = 0.52 * Math.PI), this.beta > -0.1 * Math.PI && (this.beta = -0.1 * Math.PI), this.beta < -0.9 * Math.PI && (this.beta = -0.9 * Math.PI)), (this.lerp = this.down ? 0.2 : 0.05), (this.lerp2 += (this.lerp - this.lerp2) * 0.15), this._alpha != this.alpha || this._beta != this.beta || this.init) ) { (this._alpha += (this.alpha - this._alpha) * this.lerp2), (this._beta += (this.beta - this._beta) * this.lerp2), (this._alpha2 += (this._alpha - this._alpha2) * this.lerp2), (this._beta2 += (this._beta - this._beta2) * this.lerp2), (this.position[0] = this.ratio * Math.sin(this._alpha2) * Math.sin(this._beta2) + this.target[0]), (this.position[1] = this.ratio * Math.cos(this._alpha2) + this.target[1]), (this.position[2] = this.ratio * Math.sin(this._alpha2) * Math.cos(this._beta2) + this.target[2]), (this.cameraTransformMatrix = this.defineTransformMatrix( this.position, this.target, [0, 1, 0] )); for (let r = 0; r < 16; r++) this.orientationMatrix[r] = this.cameraTransformMatrix[r]; (this.orientationMatrix[12] = 0), (this.orientationMatrix[13] = 0), (this.orientationMatrix[14] = 0); } (this.prevMouseX = this.currentMouseX), (this.prevMouseY = this.currentMouseY), Jt(this.transformMatrix, this.perspectiveMatrix, this.cameraTransformMatrix); } calculateReflection(e, t) { let i = ae(e[0], e[1], e[2]); be(i, i, this.position); let r = U(); _e(r, t, 2 * I(i, t)), be(i, i, r), Tn(i, i), Zt(i, i, e); let o = ae(e[0], e[1], e[2]); be(o, o, this.target), _e(r, t, 2 * I(o, t)), be(o, o, r), Tn(o, o), Zt(o, o, e); let a = ae(0, -1, 0); (this.reflectionPosition = i), (this.cameraReflectionMatrix = this.defineTransformMatrix2(i, o, a)), Jt( this.transformMatrixReflection, this.perspectiveMatrix, this.cameraReflectionMatrix ); } defineTransformMatrix(e, t, i) { let r = $(), o = U(), a = U(), s = U(), u = U(), c = U(); (c[0] = i[0]), (c[1] = i[1]), (c[2] = i[2]), $e(o, e, t), Xe(a, o); let m = I(a, c), p = U(); return ( _e(p, a, m), $e(s, c, p), Xe(s, s), En(u, a, s), (r[0] = u[0]), (r[1] = s[0]), (r[2] = a[0]), (r[3] = 0), (r[4] = u[1]), (r[5] = s[1]), (r[6] = a[1]), (r[7] = 0), (r[8] = u[2]), (r[9] = s[2]), (r[10] = a[2]), (r[11] = 0), (r[12] = -I(e, u)), (r[13] = -I(e, s)), (r[14] = -I(e, a)), (r[15] = 1), r ); } defineTransformMatrix2(e, t, i) { let r = $(), o = U(), a = U(), s = U(), u = U(), c = U(); (c[0] = i[0]), (c[1] = i[1]), (c[2] = i[2]), $e(o, e, t), Xe(a, o); let m = I(a, c), p = U(); return ( _e(p, a, m), $e(s, c, p), Xe(s, s), En(u, s, a), (r[0] = u[0]), (r[1] = s[0]), (r[2] = a[0]), (r[3] = 0), (r[4] = u[1]), (r[5] = s[1]), (r[6] = a[1]), (r[7] = 0), (r[8] = u[2]), (r[9] = s[2]), (r[10] = a[2]), (r[11] = 0), (r[12] = -I(e, u)), (r[13] = -I(e, s)), (r[14] = -I(e, a)), (r[15] = 1), r ); } } var J = document.createElement("canvas"), ie = J.getContext("2d", { willReadFrequently: !0 }); J.style.position = "absolute"; J.style.top = "0px"; function Vr(n, e, t, i = 0.56, r = null) { return ( (J.width = t), (J.height = t), (J.style.width = `${t}px`), (J.style.height = `${t}px`), r == null ? ((ie.fillStyle = "black"), ie.fillRect(0, 0, J.width, J.height), (ie.fillStyle = "white"), (ie.textAlign = "center"), (ie.font = `${e}px Cal Sans, sans-serif`), (ie.crossOrigin = `anonymous`), ie.fillText(n, t * 0.5, t * 0.5 + e * i)) : ie.drawImage(r, 0, 0), ie.getImageData(0, 0, t, t).data ); } var Hr = `struct Uniforms { cameraOrientation: mat4x4f, acceleration: vec3f, deltaTime: f32, mousePosition: vec3f, gridResolution: f32, mouseDirection: vec3f, currentFrame: f32, transition: f32, totalParticles: f32 } @group(0) @binding(0) var<storage, read_write> resetBuffer: array<vec4f>; @group(0) @binding(1) var<storage, read_write> positionBuffer: array<vec4f>; @group(0) @binding(2) var<storage, read> velocityBuffer: array<vec4f>; @group(0) @binding(3) var<storage, read_write> counterBuffer: array<atomic<u32>>; @group(0) @binding(4) var<storage, read_write> indicesBuffer: array<u32>; @group(0) @binding(5) var<uniform> uniforms: Uniforms; fn t1() -> f32 { return uniforms.currentFrame * 10.5432895; } fn t2() -> f32 { return uniforms.currentFrame * 20.5432895; } fn t3() -> f32 { return uniforms.currentFrame * 5.535463; } fn t4() -> f32 { return -uniforms.currentFrame * 13.534534; } fn t5() -> f32 { return uniforms.currentFrame * 54.42345; } fn t6() -> f32 { return - uniforms.currentFrame * 23.53450; } fn t7() -> f32 { return - uniforms.currentFrame * 45.5345354313; } fn t8() -> f32 { return uniforms.currentFrame * 23.4234521243; } fn dP3dY( v: vec3<f32>) -> f32 { var noise = 0.0; noise += 3. * cos(v.z * 1.8 + v.y * 3. - 194.58 + t1() ) + 4.5 * cos(v.z * 4.8 + v.y * 4.5 - 83.13 + t2() ) + 1.2 * cos(v.z * -7.0 + v.y * 1.2 -845.2 + t3() ) + 2.13 * cos(v.z * -5.0 + v.y * 2.13 - 762.185 + t4() ); noise += 5.4 * cos(v.x * -0.48 + v.y * 5.4 - 707.916 + t5() ) + 5.4 * cos(v.x * 2.56 + v.y * 5.4 + -482.348 + t6() ) + 2.4 * cos(v.x * 4.16 + v.y * 2.4 + 9.872 + t7() ) + 1.35 * cos(v.x * -4.16 + v.y * 1.35 - 476.747 + t8() ); return noise; } fn dP2dZ( v: vec3<f32>) -> f32 { return -0.48 * cos(v.z * -0.48 + v.x * 5.4 -125.796 + t5() ) + 2.56 * cos(v.z * 2.56 + v.x * 5.4 + 17.692 + t6() ) + 4.16 * cos(v.z * 4.16 + v.x * 2.4 + 150.512 + t7() ) -4.16 * cos(v.z * -4.16 + v.x * 1.35 - 222.137 + t8() ); } fn dP1dZ( v: vec3<f32>) -> f32 { var noise = 0.0; noise += 3. * cos(v.x * 1.8 + v.z * 3. + t1() ) + 4.5 * cos(v.x * 4.8 + v.z * 4.5 + t2() ) + 1.2 * cos(v.x * -7.0 + v.z * 1.2 + t3() ) + 2.13 * cos(v.x * -5.0 + v.z * 2.13 + t4() ); noise += 5.4 * cos(v.y * -0.48 + v.z * 5.4 + t5() ) + 5.4 * cos(v.y * 2.56 + v.z * 5.4 + t6() ) + 2.4 * cos(v.y * 4.16 + v.z * 2.4 + t7() ) + 1.35 * cos(v.y * -4.16 + v.z * 1.35 + t8() ); return noise; } fn dP3dX( v: vec3<f32>) -> f32 { return -0.48 * cos(v.x * -0.48 + v.y * 5.4 - 707.916 + t5() ) + 2.56 * cos(v.x * 2.56 + v.y * 5.4 + -482.348 + t6() ) + 4.16 * cos(v.x * 4.16 + v.y * 2.4 + 9.872 + t7() ) -4.16 * cos(v.x * -4.16 + v.y * 1.35 - 476.747 + t8() ); } fn dP2dX( v: vec3<f32>) -> f32 { var noise = 0.0; noise += 3. * cos(v.y * 1.8 + v.x * 3. - 2.82 + t1() ) + 4.5 * cos(v.y * 4.8 + v.x * 4.5 + 74.37 + t2() ) + 1.2 * cos(v.y * -7.0 + v.x * 1.2 - 256.72 + t3() ) + 2.13 * cos(v.y * -5.0 + v.x * 2.13 - 207.683 + t4() ); noise += 5.4 * cos(v.z * -0.48 + v.x * 5.4 -125.796 + t5() ) + 5.4 * cos(v.z * 2.56 + v.x * 5.4 + 17.692 + t6() ) + 2.4 * cos(v.z * 4.16 + v.x * 2.4 + 150.512 + t7() ) + 1.35 * cos(v.z * -4.16 + v.x * 1.35 - 222.137 + t8() ); return noise; } fn dP1dY( v: vec3<f32>) -> f32 { return -0.48 * cos(v.y * -0.48 + v.z * 5.4 + t5() ) + 2.56 * cos(v.y * 2.56 + v.z * 5.4 + t6() ) + 4.16 * cos(v.y * 4.16 + v.z * 2.4 + t7() ) -4.16 * cos(v.y * -4.16 + v.z * 1.35 + t8()); } fn curlNoise(p : vec3<f32> ) -> vec3<f32> { let x = dP3dY(p) - dP2dZ(p); let y = dP1dZ(p) - dP3dX(p); let z = dP2dX(p) - dP1dY(p); return normalize(vec3<f32>(x, y, z)); } @compute @workgroup_size(256) fn main( @builtin(global_invocation_id) id: vec3<u32> ) { let i = id.x; var ii = id.x; let tt = u32(uniforms.totalParticles); if(ii >= tt) { ii = tt - i % tt; } var planeIndex = positionBuffer[i].a; var position = positionBuffer[i].rgb; var velocity = velocityBuffer[i].rgb; var origin = resetBuffer[ii].rgb; var dt = uniforms.deltaTime; var acceleration = vec3f(0.); var noiseAcceleration = uniforms.acceleration; var transition = uniforms.transition * 3.; var delta = 1.; var amp = 150.; var freq = .01; for(var k = 0; k < 2; k ++) { var c = curlNoise(freq * position ); noiseAcceleration += amp * c; amp /= 2.; freq *= 2.; } var resetAcceleration = 20. * (origin - position); if(transition < 1.) { acceleration = noiseAcceleration; } else { var transitionIndex = min(max(transition - planeIndex / uniforms.gridResolution - 1., 0.), 1.); acceleration = mix(noiseAcceleration, resetAcceleration + noiseAcceleration * (1. - transitionIndex), vec3f(transitionIndex)); } var p1 = uniforms.cameraOrientation * vec4f(position, 1.); var p2 = uniforms.cameraOrientation * vec4f(uniforms.mousePosition, 1.); var intensity = 1. - length(p2.xy - p1.xy) / (5. + 10. * clamp(length(uniforms.mouseDirection), 0, 1) ); intensity = clamp(intensity, 0., 1.); acceleration += 0.1 * uniforms.mouseDirection * intensity / (dt * dt); position = position + dt * (velocity + dt * acceleration); positionBuffer[i] = vec4f(position, planeIndex); let textureSize = u32(uniforms.gridResolution); let voxelPosition = vec3<u32>( floor(position) ); let index1D = voxelPosition.x + textureSize * voxelPosition.y + textureSize * textureSize * voxelPosition.z; let amountOfParticlesInVoxel = atomicAdd(&counterBuffer[index1D], 1); if(amountOfParticlesInVoxel < 4) { indicesBuffer[ u32( u32(4 * index1D) + u32(amountOfParticlesInVoxel) )] = i; } }`, Yr = `struct Uniforms { uResolution: f32, uSearchRadius: f32, separation: f32 } var<private> deltaPosition: vec3<f32> = vec3f(0.); var<private> h2: f32 = 0.; @group(0) @binding(0) var<storage, read> positionBufferIN: array<vec4f>; @group(0) @binding(1) var<storage, read_write> positionBufferOUT: array<vec4f>; @group(0) @binding(2) var<storage, read> indicesBuffer: array<vec4<u32>>; @group(0) @binding(3) var<uniform> uniforms: Uniforms; fn addToSum(particlePosition: vec3f, nParticlePosition: vec3f) { let distance = (particlePosition - nParticlePosition) ; let r = length(distance); let separation = 1. + uniforms.separation; if(r > 0. && r < separation) { deltaPosition -= 0.5 * (r - separation) * normalize(distance) ; } } @compute @workgroup_size(256) fn main( @builtin(global_invocation_id) id: vec3<u32> ) { var index1D = id.x; h2 = uniforms.uSearchRadius * uniforms.uSearchRadius; let particlePosition = positionBufferIN[index1D].rgb; let lambdaPressure = positionBufferIN[index1D].a; let gridPosition = vec3<i32>(floor(particlePosition)); let resolution = i32(uniforms.uResolution); var neighborsVoxel = gridPosition ; var voxelIndex = neighborsVoxel.x + neighborsVoxel.y * resolution + neighborsVoxel.z * resolution * resolution; var indices = indicesBuffer[u32(voxelIndex)]; if(indices.x > 0) {addToSum(particlePosition, positionBufferIN[indices.x].rgb);} if(indices.y > 0) {addToSum(particlePosition, positionBufferIN[indices.y].rgb);} if(indices.z > 0) {addToSum(particlePosition, positionBufferIN[indices.z].rgb);} if(indices.w > 0) {addToSum(particlePosition, positionBufferIN[indices.w].rgb);} var offsets = array<vec3<i32>, 26>(); offsets[0] = vec3<i32>(0, 0, 1); offsets[1] = vec3<i32>(0, 0, -1); offsets[2] = vec3<i32>(0, 1, 0); offsets[3] = vec3<i32>(0, -1, 0); offsets[4] = vec3<i32>(1, 0, 0); offsets[5] = vec3<i32>(-1, 0, 0); offsets[6] = vec3<i32>(0, 1, 1); offsets[7] = vec3<i32>(1, 0, 1); offsets[8] = vec3<i32>(1, 1, 0); offsets[9] = vec3<i32>(0, 1, -1); offsets[10] = vec3<i32>(1, 0, -1); offsets[11] = vec3<i32>(1, -1, 0); offsets[12] = vec3<i32>(0, -1, 1); offsets[13] = vec3<i32>(-1, 0, 1); offsets[14] = vec3<i32>(-1, 1, 0); offsets[15] = vec3<i32>(0, -1, -1); offsets[16] = vec3<i32>(-1, 0, -1); offsets[17] = vec3<i32>(-1, -1, 0); offsets[18] = vec3<i32>(1, 1, 1); offsets[19] = vec3<i32>(1, 1, -1); offsets[20] = vec3<i32>(1, -1, 1); offsets[21] = vec3<i32>(-1, 1, 1); offsets[22] = vec3<i32>(1, -1, -1); offsets[23] = vec3<i32>(-1, -1, 1); offsets[24] = vec3<i32>(-1, 1, -1); offsets[25] = vec3<i32>(-1, -1, -1); for(var i = 0; i < 26; i ++) { var average = vec3f(0); var counter = 0.; let neighborsVoxel = gridPosition + offsets[i]; let voxelIndex = neighborsVoxel.x + neighborsVoxel.y * resolution + neighborsVoxel.z * resolution * resolution; let indices = indicesBuffer[u32(voxelIndex)]; if(indices.x > 0) {addToSum(particlePosition, positionBufferIN[indices.x].rgb);} .........完整代码请登录后点击上方下载按钮下载查看
网友评论0