You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在React应用中使用Three.js实现管道水流模拟功能

React + Three.js 管道水流模拟实现方案

前置依赖

首先安装需要的第三方包:

npm install three @react-three/fiber @react-three/drei

核心实现逻辑

  • 管道绘制:使用双层圆柱实现,外层为半透明灰色管壁,内层为空心区域承载水体,默认水平放置
  • 蓄水百分比控制:根据传入的百分比值动态调整内层水体圆柱的轴向长度,水体使用半透蓝色材质模拟真实水效
  • 水流方向动画:通过动态偏移水体表面的箭头纹理实现流动效果,方向切换时直接调整纹理偏移的正负值即可

完整组件代码

import { useRef, useState, useMemo } from 'react'
import { Canvas, useFrame } from '@react-three/fiber'
import { OrbitControls } from '@react-three/drei'
import * as THREE from 'three'

// 本地生成箭头纹理,无需引入外部资源
const createArrowTexture = () => {
  const canvas = document.createElement('canvas')
  canvas.width = 512
  canvas.height = 128
  const ctx = canvas.getContext('2d')
  ctx.fillStyle = 'rgba(255,255,255,0.8)'
  ctx.fillRect(0, 0, 512, 128)
  ctx.fillStyle = '#1e88e5'
  // 绘制重复箭头图案
  for (let i = 0; i < 8; i++) {
    const x = i * 64 + 10
    ctx.beginPath()
    ctx.moveTo(x, 64)
    ctx.lineTo(x + 30, 24)
    ctx.lineTo(x + 30, 44)
    ctx.lineTo(x + 50, 44)
    ctx.lineTo(x + 50, 84)
    ctx.lineTo(x + 30, 84)
    ctx.lineTo(x + 30, 104)
    ctx.closePath()
    ctx.fill()
  }
  const texture = new THREE.CanvasTexture(canvas)
  texture.wrapS = THREE.RepeatWrapping
  texture.wrapT = THREE.RepeatWrapping
  texture.repeat.set(4, 1)
  return texture
}

const Pipe = ({ waterPercent = 70, flowDirection = 'right' }) => {
  const pipeLength = 10
  const pipeRadius = 1
  const waterMaterialRef = useRef()
  const arrowTexture = useMemo(() => createArrowTexture(), [])

  // 按百分比计算水体长度
  const waterLength = useMemo(() => {
    return (waterPercent / 100) * pipeLength
  }, [waterPercent, pipeLength])

  // 逐帧更新纹理偏移实现流动动画
  useFrame((state, delta) => {
    if (waterMaterialRef.current) {
      const offsetSpeed = flowDirection === 'right' ? -delta * 0.5 : delta * 0.5
      waterMaterialRef.current.map.offset.x += offsetSpeed
    }
  })

  return (
    <group rotation={[0, 0, Math.PI / 2]}>
      {/* 外层管壁 */}
      <mesh>
        <cylinderGeometry args={[pipeRadius, pipeRadius, pipeLength, 32]} />
        <meshStandardMaterial color="#90a4ae" transparent opacity={0.6} side={THREE.BackSide} />
      </mesh>
      {/* 管壁外层边框 */}
      <mesh>
        <cylinderGeometry args={[pipeRadius + 0.05, pipeRadius + 0.05, pipeLength, 32]} />
        <meshStandardMaterial color="#546e7a" transparent opacity={0.8} />
      </mesh>
      {/* 内部水体 */}
      {waterPercent > 0 && (
        <mesh position={[- (pipeLength - waterLength) / 2, 0, 0]}>
          <cylinderGeometry args={[pipeRadius - 0.1, pipeRadius - 0.1, waterLength, 32]} />
          <meshStandardMaterial
            ref={waterMaterialRef}
            map={arrowTexture}
            transparent
            opacity={0.7}
            color="#42a5f5"
          />
        </mesh>
      )}
    </group>
  )
}

// 组件调用示例
const PipeWaterFlowDemo = () => {
  const [percent, setPercent] = useState(70)
  const [direction, setDirection] = useState('right')

  return (
    <div style={{ width: '100%', height: '500px' }}>
      <div style={{ marginBottom: '16px' }}>
        <label>蓄水百分比:{percent}% </label>
        <input
          type="range"
          min="0"
          max="100"
          value={percent}
          onChange={(e) => setPercent(Number(e.target.value))}
          style={{ marginRight: '24px' }}
        />
        <label>水流方向:</label>
        <button
          onClick={() => setDirection(direction === 'right' ? 'left' : 'right')}
          style={{ padding: '4px 12px', marginLeft: '8px' }}
        >
          切换为{direction === 'right' ? '从右到左' : '从左到右'}
        </button>
      </div>
      <Canvas camera={{ position: [0, 5, 10] }}>
        <ambientLight intensity={0.5} />
        <directionalLight position={[10, 10, 5]} intensity={1} />
        <Pipe waterPercent={percent} flowDirection={direction} />
        <OrbitControls />
      </Canvas>
    </div>
  )
}

export default PipeWaterFlowDemo

效果验证

上述代码实现了全部需求:

  1. 自动生成带透明管壁的3D管道模型,支持鼠标拖拽旋转查看
  2. 拖动滑块可实时调整管道蓄水占比,支持0-100%任意数值设置
  3. 点击切换按钮可调整水流方向,箭头会对应朝对应方向流畅移动
    管道水流模拟效果图

内容的提问来源于stack exchange,提问作者Jerry

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 04:27:00