WaveTerrain
threecn/wave-terrainFreeComponent
An undulating wireframe terrain in perspective, drawn with --primary.
Install it
npx shadcn@latest add https://threecn.dev/r/wave-terrain.jsonSource
1"use client"23import * as React from "react"4import { useFrame } from "@react-three/fiber"5import * as THREE from "three"67import {8 SceneContainer,9 type SceneContainerProps,10} from "@/components/threecn/scene-container"11import {12 useShadcnTheme,13 type ThemeMode,14} from "@/components/hooks/use-shadcn-theme"1516function Terrain({17 amplitude,18 speed,19 density,20 theme,21}: {22 amplitude: number23 speed: number24 density: number25 theme: ThemeMode26}) {27 const meshRef = React.useRef<THREE.Mesh>(null)28 const { primaryColor, mutedColor } = useShadcnTheme(theme)2930 useFrame((state) => {31 const mesh = meshRef.current32 if (!mesh) return33 const t = state.clock.elapsedTime * speed34 const pos = mesh.geometry.getAttribute("position") as THREE.BufferAttribute35 const arr = pos.array as Float32Array36 for (let i = 0; i < arr.length; i += 3) {37 const x = arr[i]38 const y = arr[i + 1]39 arr[i + 2] =40 Math.sin(x * 0.6 + t) * amplitude +41 Math.cos(y * 0.5 + t * 0.8) * amplitude * 0.642 }43 pos.needsUpdate = true44 mesh.geometry.computeVertexNormals()45 })4647 return (48 <group rotation={[-Math.PI / 2.5, 0, 0]} position={[0, -0.6, 0]}>49 {/* wireframe surface */}50 <mesh ref={meshRef}>51 <planeGeometry args={[16, 16, density, density]} />52 <meshBasicMaterial53 color={primaryColor}54 wireframe55 transparent56 opacity={0.55}57 />58 </mesh>59 {/* faint filled copy for body */}60 <mesh position={[0, 0, -0.02]}>61 <planeGeometry args={[16, 16, density, density]} />62 <meshBasicMaterial color={mutedColor} transparent opacity={0.04} />63 </mesh>64 </group>65 )66}6768export type WaveTerrainProps = {69 /** Peak height of the waves. */70 amplitude?: number71 /** Animation speed multiplier. */72 speed?: number73 /** Grid resolution (segments per side). */74 density?: number75 className?: string76 theme?: ThemeMode77 environment?: SceneContainerProps["environment"]78}7980/**81 * An undulating wireframe terrain seen in perspective. The grid uses `--primary`82 * over a faint `--muted-foreground` body. Vertices are displaced every frame.83 */84export function WaveTerrain({85 amplitude = 0.6,86 speed = 0.6,87 density = 48,88 className,89 theme = "auto",90 environment = "night",91}: WaveTerrainProps) {92 return (93 <SceneContainer94 className={className}95 theme={theme}96 environment={environment}97 camera={[0, 1.2, 6]}98 fov={45}99 >100// … truncated
What it pulls in
npm packages
Files it writes
More from threecn
All 28 items| Component | Registry | Kind | Access | Installs | Command |
|---|---|---|---|---|---|
| AuroraRibbonsaurora-ribbons | threecn | Components | Free | 3 deps · 3 files | |
| Boidsboids | threecn | Components | Free | 3 deps · 3 files | |
| Clothcloth | threecn | Components | Free | 3 deps · 3 files | |
| Crystalcrystal | threecn | Components | Free | 3 deps · 3 files | |
| CubeWavecube-wave | threecn | Components | Free | 3 deps · 3 files | |
| CurlFlowcurl-flow | threecn | Components | Free | 3 deps · 3 files | |
| DnaHelixdna-helix | threecn | Components | Free | 3 deps · 3 files | |
| FloatingCard3Dfloating-card-3d | threecn | Components | Free | 3 deps · 3 files |
