欧美日韩精品一区二区在线线,一级无码在线收看,精品国产高清91,久久精品欧美电影

# Canvas 畫布

canvas 組件 提供了繪制界面,可以在之上進行任意繪制

# 基礎使用

# 第一步:在 WXML 中添加 canvas 組件

<!-- 2d 類型的 canvas -->
<canvas id="myCanvas" type="2d" style="border: 1px solid; width: 300px; height: 150px;" />

首先需要在 WXML 中添加 canvas 組件。

指定 id="myCanvas" 唯一標識一個 canvas,用于后續(xù)獲取 Canvas 對象

指定 type 用于定義畫布類型,本例子使用 type="2d" 示例。

# 第二步:獲取 Canvas 對象和渲染上下文

this.createSelectorQuery()
    .select('#myCanvas') // 在 WXML 中填入的 id
    .fields({ node: true, size: true })
    .exec((res) => {
        // Canvas 對象
        const canvas = res[0].node
        // 渲染上下文
        const ctx = canvas.getContext('2d')
    })

通過 SelectorQuery 選擇上一步的 canvas,可以獲取到 Canvas 對象。

再通過 Canvas.getContext,我們可以獲取到 渲染上下文 RenderingContext。

后續(xù)的畫布操作與渲染操作,都需要通過這兩個對象來實現(xiàn)。

# 第三步:初始化 Canvas

this.createSelectorQuery()
    .select('#myCanvas') // 在 WXML 中填入的 id
    .fields({ node: true, size: true })
    .exec((res) => {
        // Canvas 對象
        const canvas = res[0].node
        // 渲染上下文
        const ctx = canvas.getContext('2d')

        // Canvas 畫布的實際繪制寬高
        const width = res[0].width
        const height = res[0].height

        // 初始化畫布大小
        const dpr = wx.getWindowInfo().pixelRatio
        canvas.width = width * dpr
        canvas.height = height * dpr
        ctx.scale(dpr, dpr)
    })

canvas 的寬高分為渲染寬高和邏輯寬高:

  • 渲染寬高為 canvas 畫布在頁面中所實際占用的寬高大小,即通過對節(jié)點進行 boundingClientRect 請求獲取到的大小。
  • 邏輯寬高為 canvas 在渲染過程中的邏輯寬高大小,如繪制一個長方形與邏輯寬高相同,最終長方形會占滿整個畫布。邏輯寬高默認為 300 * 150。

不同的設備上,存在物理像素和邏輯像素不相等的情況,所以一般我們需要用 wx.getWindowInfo 獲取設備的像素比,乘上 canvas 的渲染大小,作為畫布的邏輯大小。

# 第四步:進行繪制

在開發(fā)者工具中預覽效果

// 省略上面初始化步驟,已經(jīng)獲取到 canvas 對象和 ctx 渲染上下文

// 清空畫布
ctx.clearRect(0, 0, width, height)

// 繪制紅色正方形
ctx.fillStyle = 'rgb(200, 0, 0)';
ctx.fillRect(10, 10, 50, 50);

// 繪制藍色半透明正方形
ctx.fillStyle = 'rgba(0, 0, 200, 0.5)';
ctx.fillRect(30, 30, 50, 50);

通過 渲染上下文 上的繪圖 api,我們可以在畫布上進行任意的繪制。

# 進階使用

# 繪制圖片

在開發(fā)者工具中預覽效果

// 省略上面初始化步驟,已經(jīng)獲取到 canvas 對象和 ctx 渲染上下文

// 圖片對象
const image = canvas.createImage()
// 圖片加載完成回調
image.onload = () => {
    // 將圖片繪制到 canvas 上
    ctx.drawImage(image, 0, 0)
}
// 設置圖片src
image.src = 'https://open.weixin.qq.com/zh_CN/htmledition/res/assets/res-design-download/icon64_wx_logo.png'

通過 Canvas.createImage 我們可以創(chuàng)建圖片對象并加載圖片。當圖片加載完成觸發(fā) onload 回調之后,使用 ctx.drawImage 即可將圖片繪制到 canvas 上。

# 生成圖片

在開發(fā)者工具中預覽效果

// 省略上面初始化步驟,已經(jīng)獲取到 canvas 對象和 ctx 渲染上下文

// 繪制紅色正方形
ctx.fillStyle = 'rgb(200, 0, 0)';
ctx.fillRect(10, 10, 50, 50);

// 繪制藍色半透明正方形
ctx.fillStyle = 'rgba(0, 0, 200, 0.5)';
ctx.fillRect(30, 30, 50, 50);

// 生成圖片
wx.canvasToTempFilePath({
    canvas,
    success: res => {
        // 生成的圖片臨時文件路徑
        const tempFilePath = res.tempFilePath
    },
})

通過 wx.canvasToTempFilePath 接口,可以將 canvas 上的內容生成圖片臨時文件。

# 幀動畫

在開發(fā)者工具中預覽效果

// 省略上面初始化步驟,已經(jīng)獲取到 canvas 對象和 ctx 渲染上下文

const startTime = Date.now()

// 幀渲染回調
const draw = () => {
  const time = Date.now()
  // 計算經(jīng)過的時間
  const elapsed = time - startTime

  // 計算動畫位置
  const n = Math.floor(elapsed / 3000)
  const m = elapsed % 3000
  const dx = (n % 2 ? 0 : 1) + (n % 2 ? 1 : -1) * (m < 2500 ? easeOutBounce(m / 2500) : 1)
  const x = (width - 50) * dx

  // 渲染
  ctx.clearRect(0, 0, width, height)
  ctx.fillStyle = 'rgb(200, 0, 0)';
  ctx.fillRect(x, height / 2 - 25, 50, 50);

  // 注冊下一幀渲染
  canvas.requestAnimationFrame(draw)
}

draw()

通過 Canvas.requestAnimationFrame 可以注冊動畫幀回調,在回調內進行動畫的逐幀繪制。

# 自定義字體

通過 wx.loadFontFace 可以為 Canvas 加載自定義字體。

在開發(fā)者工具中預覽效果

# 錄制視頻

通過 MediaRecorder 可以將 Canvas 內容錄制為視頻并保存。

在開發(fā)者工具中預覽效果

# WebGL

在開發(fā)者工具中預覽效果

<canvas type="webgl" id="myCanvas" />
// 省略上面初始化步驟,已經(jīng)獲取到 canvas 對象

const gl = canvas.getContext('webgl') // 獲取 webgl 渲染上下文