样式-径向渐变-3D球

6 阅读3分钟

3D 球效果实现原理分析

核心代码

const x = 100, y = 100, radius = 60;

const gradient = ctx.createRadialGradient(
    x - radius * 0.3,  // x1 = 82  (高光点 x)
    y - radius * 0.3,  // y1 = 82  (高光点 y)
    0,                 // r1 = 0   (起点半径)
    x,                 // x2 = 100 (球心 x)
    y,                 // y2 = 100 (球心 y)
    radius             // r2 = 60  (终点半径)
);

gradient.addColorStop(0, 'white');         // 高光
gradient.addColorStop(0.2, 'lightblue');   // 亮部
gradient.addColorStop(0.8, 'lightblue');   // 中间调
gradient.addColorStop(1, 'rgba(0,0,0,0.3)'); // 暗部

一、createRadialGradient 的双圆定义

createRadialGradient(x1, y1, r1, x2, y2, r2) 参数解析:

参数几何意义
(x1, y1, r1)(82, 82, 0)起点圆 - 退化为点(高光位置)
(x2, y2, r2)(100, 100, 60)终点圆 - 球体外轮廓

二、"中间圆族"的几何插值

插值公式

对于 t ∈ [0, 1],中间圆 C(t) 定义为:

圆心 O(t) = (1-t) × O₁ + t × O₂
          = (1-t) × (82, 82) + t × (100, 100)
          = (82 + 18t, 82 + 18t)

半径 r(t) = (1-t) × r₁ + t × r₂
          = 0 + 60t
          = 60t

关键位置的中间圆

t圆心半径颜色
0(82, 82)0white(高光)
0.2(85.6, 85.6)12lightblue
0.8(96.4, 96.4)36lightblue
1(100, 100)60暗色(边缘)

三、渐变区域的几何形状

几何示意图

                         ● O₁(82,82) r=0
                          │
                          │ 圆心移动向量 (18,18)
                          │ 长度 ≈ 25.5
                          ▼
                         ● O₂(100,100) r=60
                        ╱│╲
                       ╱ │ ╲
                      ╱  │  ╲  终点圆边界
                     ╱   │   ╲
                    ╱━━━━┻━━━━╲
    
    中间圆族 = 所有 C(t) 圆的并集
    有效区域 = 以 O₂为圆心、r=60 的圆盘
  • 从 0.2 到 0.8 这个区间内,颜色都是 lightblue,不会有渐变效果
  • 渐变只会在不同颜色之间发生,比如:
    • 0.0 → 0.2:从 white 渐变到 lightblue
    • 0.8 → 1.0:从 lightblue 渐变到 white

颜色插值的数学原理

对于圆内任意点 P,浏览器求解方程找到对应的 t 值:

|P - O(t)|² = r(t)²

代入 O(t) 和 r(t),解关于 t 的二次方程
→ 得到 P 点对应的插值位置 t
→ 颜色 = lerp(colorStops, t)

四、3D 立体感的来源

1. 高光偏移 → 光源方向

高光在 (82,82),球心在 (100,100)
     ↓
光源从左上角照射

2. 颜色配置 → 光影层次

t=0      white      → 镜面高光(最亮)
t=0.2    lightblue  → 直接受光区
t=0.8    lightblue  → 过渡区(颜色平台)
t=1      rgba(0,0,0,0.3) → 背光阴影(最暗)

3. 视觉效果

        光源↗
      ╭───────╮
     ╱   白    ╲   ← 高光区
    │  lightblue  │ ← 受光面
    │   blue    │ ← 中间调
     ╲  dark   ╱   ← 背光面
      ╰───────╯

五、完整绘制流程

1. 定义径向渐变(双圆 + 颜色 stops)
       ↓
2. 计算每个点的插值参数 t(二次方程求解)
       ↓
3. 根据 t 查找 colorStop 表,插值得到颜色
       ↓
4. 绘制圆形路径 ctx.arc()
       ↓
5. 用渐变填充 → 3D 球效果

六、技术要点总结

技术要点作用
双圆不同心产生高光偏移,模拟光源方向
起点圆半径=0高光集中于一点
颜色平台 (0.2-0.8)让球体大部分区域颜色均匀,只有边缘变暗
透明暗色边缘融入背景,增强立体感

结论

这个实现用纯 2D 渐变模拟了Phong 光照模型的效果,是计算机图形学中经典的"伪 3D"技术。

核心思想:

  • 通过 createRadialGradient双圆插值定义渐变场
  • 利用高光偏移模拟光源方向
  • 通过颜色阶梯模拟光影层次
  • 最终在 2D 平面上呈现出 3D 立体感