p5.js 光速入門

本文簡介

點(diǎn)贊 + 關(guān)注 + 收藏 = 學(xué)會了


本文的目標(biāo)是和各位工友一起有序的快速上手 p5.js ,會講解 p5.js 的基礎(chǔ)用法。

本文會涉及到的內(nèi)容包括:

  • 項(xiàng)目搭建
  • p5.js 基礎(chǔ)2D圖形
  • 文字
  • 圖形樣式設(shè)置
  • 圖片
  • 事件(交互相關(guān)的)
  • 基礎(chǔ)動畫

其中還會講解部分 p5.js 全局方法。

本文不涉及3d部分(放到下一篇吧)。


官方文檔很重要,但對于初學(xué)者來說可能會有點(diǎn)懵。因?yàn)楣俜轿臋n主要講解api的用法,第一次接觸p5.js的工友可能不是那么容易將各個知識點(diǎn)串聯(lián)起來。

本文在基于官方案例的基礎(chǔ)上,把我覺得入門必學(xué)的知識點(diǎn)過一遍,然后串起來搞一個小特效。

要快速學(xué)習(xí)一個庫,尤其是可視化方面的庫,最快速的方法是找到一個好教程,然后跟著敲代碼,建立自己的 “demo倉庫” 。


學(xué)習(xí)本文內(nèi)容,你需要有 JavaScript 基礎(chǔ)。



什么是p5.js

p5.js 簡介

引用官網(wǎng)的話:

p5.js 是個 JavaScript 創(chuàng)意編程程式庫,其專注在讓編程更易于使用及更加廣泛的包容藝術(shù)家、設(shè)計師、教育家、初學(xué)者以及任何人!p5.js 是個免費(fèi)及開源的軟件因?yàn)槲覀兿嘈潘腥硕紤?yīng)該能自由使用軟件及用于學(xué)習(xí)軟件的工具。

p5.js 使用繪圖的比喻并有一副完整的繪畫功能。除此之外,您也不單限于您的繪圖畫布。您可以將您整個瀏覽器頁面當(dāng)作您的繪圖,這包括了 HTML5 物件,如文字、輸入框、視頻、攝像頭及音頻。


簡單來說,p5.js 能讓“切圖仔”更容易做出具有藝術(shù)感的作品(很能整活)。

舉個例子,p5.js 很擅長實(shí)現(xiàn)下圖效果。

file


p5.jsProcessing 往瀏覽器延伸的一個 canvas庫 。Processing 是使用 Java 編寫的,而 Java 對于從事藝術(shù)工作的工友來說上手是有點(diǎn)難度的。

瀏覽器暫時只接受 HTMLCSSJavaScript,如果能將 Processing 直接搬上瀏覽器運(yùn)行的話,對于藝術(shù)家來說是大大的好事。于是,p5.js 應(yīng)運(yùn)而生!

p5.js 第一個測試版在 2014年8月 發(fā)布。

更多的故事可在 p5.js 官網(wǎng) 中尋找,本文的目標(biāo)是光速入門 p5.js 。


找到 p5.js



快速上手

本文的目標(biāo)是和各位工友快速上手 p5.js,所以 CDN 的方式引入 p5.js,因?yàn)檫@樣非???!

接下來我們試試在畫布創(chuàng)建一個圓形吧~


環(huán)境搭建

CDN

<script src="https://cdn.jsdelivr.net/npm/p5@[p5_version]/lib/p5.js"></script>

[p5_version] 改成指定版本號即可,本文使用的版本是 1.5.0 ,所以我是這樣引入 1.5.0 版的 p5.js

<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>


查看其他版本可以瀏覽:https://cdn.jsdelivr.net/npm/p5@1.5.0/


npm

安裝

npm i p5 --save


引入

import p5 from 'p5'


在畫布創(chuàng)建一個圓形

我使用的開發(fā)工具是 vs code,并裝了 Live Server 插件。這個插件可以幫我們快速啟動一個服務(wù)端運(yùn)行當(dāng)前頁面,并具備熱更新的能力。啟動完服務(wù),在瀏覽器運(yùn)行指定頁面后,你代碼的每一次保存,瀏覽器都會自動刷新。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200) // 創(chuàng)建一個 200 * 200 像素的畫布
    background(180, 180, 180) // 畫布背景色 background(r, g, b)
  }

  function draw() {
    circle(60, 60, 100) // 畫一個圓形
  }
</script>


上面的代碼用到幾個“奇怪”的方法,逐一講解一下。

  • setup(): 可以理解為 p5.js 的一個生命周期,創(chuàng)建畫布的方法通常寫在 setup() 里。
  • draw(): 同樣可以理解為 p5.js 的一個生命周期,在這函數(shù)里的代碼會以 60幀每秒 的速度執(zhí)行。
  • createCanvas(): 創(chuàng)建畫布的方法,這個方法是 p5.js 在全局創(chuàng)建的,傳入畫布的寬高后,p5.js 會自動在頁面的最后插入一個 canvas 元素。
  • background(): 設(shè)置背景色,可以分別傳入 r、g、b ,該方法也是 p5.js 在全局創(chuàng)建的。
  • circle(): 創(chuàng)建圓形的方法,3個參數(shù)分別代表:圓心x坐標(biāo)、圓心y坐標(biāo)、直徑。


暫時只需大概了解一下怎么畫一個圓就行,詳細(xì)的后面會講到。



項(xiàng)目代碼結(jié)構(gòu)

使用 p5.js ,你可以理解為用這個工具創(chuàng)造一個“有生命”的世界。

  • 創(chuàng)造世界的工作是放在 setup() 函數(shù)里的。

  • “有聲明” 的意思是這個世界有生物,生物無時無刻都在活動。而活動的過程是放在 draw() 函數(shù)里。

setup()draw() 這兩個函數(shù)非常重要,在前端的世界里,你可以把 setup()draw() 理解為生命周期函數(shù)。


啟動函數(shù) setup

使用 CDN 的方式開發(fā)時,引入 p5.js 后就會在全局創(chuàng)建一些函數(shù)和常量。

setup()p5.js 里一個很重要的方法,你可以簡單的理解為 setupp5.js 里的一個生命周期函數(shù)。在該函數(shù)里可以做很多初始化工作,比如創(chuàng)建畫布并設(shè)置大小、畫布背景色等。

setup() 在每個頁面都只能出現(xiàn)一次,并且它不能在一開始執(zhí)行后再次被調(diào)用。


更多說明可查看 setup()說明文檔


繪圖 draw

draw()p5.js 里另一個很重要的函數(shù)。

draw() 會在 setup() 之后執(zhí)行,并且會重復(fù)的執(zhí)行。如果想打斷 draw() 可以試用 noLoop() 方法。

draw() 每秒執(zhí)行次數(shù)受到 frameRate() 影響,frameRate() 默認(rèn)每秒60幀。如果需要修改幀率,可以直接傳入指定數(shù)值,比如 frameRate(20)。


如果要做動畫,代碼可以寫在 draw() 里。


更多說明可查看 draw()說明文檔



2D基礎(chǔ)圖形

p5.js 可以繪制 2D 和 3D 圖形,但在光速入門階段只會講解 2D 圖形的基礎(chǔ)用法。

先從最簡單的點(diǎn)線面開始學(xué)起~


點(diǎn) point

點(diǎn)是 p5.js 的基礎(chǔ)元素之一,語法如下:

point(x, y, [z])

point() 接收3個參數(shù),其中 xy 是必傳參;如果是在 2D 畫布里,z 不需要傳。

  • x 表示點(diǎn)在 x 軸的坐標(biāo)
  • y 表示點(diǎn)在 y軸的坐標(biāo)


點(diǎn)出現(xiàn)在畫布的中間

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    point(100, 100)
  }
</script>

上面的例子中,畫布的寬高是200像素,點(diǎn)在 100, 100 的位置,仔細(xì)看可以發(fā)現(xiàn)點(diǎn)出現(xiàn)在畫布的中心。


如果需要畫一個更大的點(diǎn),可以通過 strokeWeight() 方法設(shè)置

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    point(100, 100)
    strokeWeight(10) // 更大的點(diǎn)
  }
</script>

其實(shí) strokeWeight() 方法是用來設(shè)置描邊粗細(xì)的,用在 point 里也完全沒問題。


更多說明可查看 point()說明文檔


線段 line

要畫一根線段的語法:

line(x1, y1, [z1], x2, y2, [z2])

注意上面的參數(shù)順序,一定不能寫錯的。

其中 z1z2 在 2D 情況下是不需要傳的,所以語法變成這樣:

line(x1, y1, x2, y2)
  • x1y1 代表起點(diǎn)坐標(biāo)
  • x2y2 代表終點(diǎn)坐標(biāo)

使用 line() 方法會自動將起點(diǎn)和終點(diǎn)連接起來,形成一根線段。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    line(60, 30, 130, 140)
  }
</script>


更多說明可查看 line()說明文檔


三角形 triangle

三角形的語法是:

triangle(x1, y1, x2, y2, x3, y3)

和前面的 點(diǎn)(point) 和 線段(line) 不同,三角形(triangle) 的所有參數(shù)都是必傳的。

三角形有3個點(diǎn),每個點(diǎn)需要用2個坐標(biāo)(x和y)來描述,所以 triangle() 一共要傳入6個參數(shù)。


經(jīng)過前面的 點(diǎn)(point) 和 線段(line) 練習(xí),相信你看到三角形的參數(shù)名稱就已經(jīng)知道什么意思了。

確定了3個點(diǎn)的坐標(biāo)后,triangle() 會使用直線連接這3個點(diǎn),形成一個三角形。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    triangle(100, 30, 40, 140, 160, 140)
  }
</script>


更多說明可查看 triangle()說明文檔


正方形 square

正方形是特殊的四邊形,也可以說是特殊的矩形。

所以先從正方形講起。


創(chuàng)建正方形用到的方法是 square(),語法如下所示:

square(x, y, s, [tl], [tr], [br], [bl])
  • xy 是正方形左上角的坐標(biāo)
  • s 是正方形的邊長

tl、tr、br、bl 是用來設(shè)置正方形的圓角半徑,分別是 上左、上右下右、下左。如果不傳這幾個參數(shù),正方形的角默認(rèn)是90°(直角)。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    square(10, 10, 80)
  }
</script>


圓角半徑

圓角半徑參數(shù)遵循以下規(guī)則:

省略的角半徑參數(shù)設(shè)置為參數(shù)列表中先前指定的半徑值的值。

意思是,如果只傳入1個半徑值,那么后面3個圓角半徑的值會取左上的圓角半徑。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    square(10, 10, 80, 10)
  }
</script>


如果是傳入2個圓角半徑,那第三和第四個圓角半徑的值會取第二個的值。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(200, 200)
    background(220, 220, 220)
  }

  function draw() {
    square(10, 10, 80, 10, 30)
  }
</script>


更多說明可查看 square()說明文檔


矩形 rect

前面了解完 正方形(quad) 如何創(chuàng)建后,學(xué)習(xí) 矩形(rect) 會覺得非常簡單。

p5.js 提供了 rect() 方法繪制矩形,而且會根據(jù)參數(shù)的數(shù)量判斷繪制矩形還是繪制正方形。

語法如下:

rect(x, y, w, [h], [tl], [tr], [br], [bl])
  • xy 是矩形左上角坐標(biāo)位置
  • w 是邊長

如果只傳3個參數(shù),繪制出來的是正方形(長和寬的值都使用第三個參數(shù))

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    rect(10, 10, 60) // 矩形
  }
</script>


如果傳4個參數(shù)的話,就可以分別設(shè)置長和寬了,第3和第4個參數(shù)分別是 wy。

  • w: x軸方向的長度(寬)
  • h: y軸方向的長度(高)


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    rect(10, 10, 60, 100) // 矩形
  }
</script>


后面的4個參數(shù) tltr、br、bl 分別設(shè)置四個角的圓角半徑,不設(shè)置的話默認(rèn)就是90°。用法和正方形一樣的,自己動手試試看吧~


更多說明可查看 rect()說明文檔


四邊形 quad

如果需要繪制四邊形,使用 quad() 即可。

四邊形有4個頂點(diǎn),1個定點(diǎn)用2個參數(shù)表示 xy 坐標(biāo)。

語法如下:

quad(x1, y1, x2, y2, x3, y3, x4, y4)

需要注意繪制四邊形時頂點(diǎn)的繪制順序


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    quad(80, 40, 180, 40, 140, 80, 40, 80) // 四邊形
  }
</script>


更多說明可查看 quad()說明文檔


圓形 circle

圓形是“特殊橢圓”,使用 circle() 方法可以創(chuàng)建圓形。

語法如下:

circle(x, y, d)
  • xy 是圓形的坐標(biāo)
  • d 是圓的直徑


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    circle(80, 80, 100) // 圓形
  }
</script>

上面代碼的意思:圓心在 (80, 80) 的位置,直徑是 100。換算一下半徑就是50咯。


更多說明可查看 circle()說明文檔


橢圓 ellipse

使用 ellipse() 可以創(chuàng)建橢圓,橢圓(ellipse) 的創(chuàng)建方法和 矩形(rect) 其實(shí)是有點(diǎn)像的。

ellipse() 方法會根據(jù)傳入的參數(shù)數(shù)量判斷創(chuàng)建圓形還是創(chuàng)建橢圓。

語法如下:

ellipse(x, y, w, [h])
  • xy 確定了橢圓的圓心
  • w 橢圓在x軸的寬度
  • h 橢圓在y軸的高度

如果只傳3個參數(shù),h 會取 w 的值,所以畫出來的是正圓形。

如果傳4個參數(shù),并且 wh 的值不一樣,那畫出來就是一個橢圓。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    ellipse(80, 80, 100, 50) // 橢圓
  }
</script>


更多說明可查看 ellipse()說明文檔


弧狀 arc

弧形(arc) 是一個很好玩的方法,你可以用 arc() 畫圓形、橢圓、餅圖和弧線。

隨著功能的增加, arc() 所需的參數(shù)也會比圓形和橢圓更多。

先來看看語法:

arc(x, y, w, h, start, stop, [mode], [detail])
  • xy: 圓弧的圓心坐標(biāo)
  • w : x軸方向的寬度
  • h: y軸方向的高度
  • start: 弧形開始的角度(用弧度定義)
  • stop: 弧形結(jié)束的角度(用弧度定義)
  • mode: 定義弧形的畫法??蛇x值:開放式半圓形(OPEN),封閉式半圓形(CHORD),封閉式餅形段(PIE)
  • detail: 指定構(gòu)成圓弧周長的頂點(diǎn)數(shù)量,在 2D 模式下不會用到


我知道有很些工友對弧度制不太熟悉,其實(shí)也不需要擔(dān)心,p5.js 提供了 radians() 方法,可以將角度轉(zhuǎn)成弧度。

接下來我就用角度的方式去畫圖展示一下 arc() 是如何使用的。


我畫4個弧形,分別表示 90°、180° 、270° 和 360°。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    // 左上角的圖形,0-90°(角度)
    arc(50, 50, 50, 50, radians(0), radians(90))

    // 右上角的圖形,0-180°(角度)
    arc(250, 50, 50, 50, radians(0), radians(180))

    // 左下角的圖形,0-270°(角度)
    arc(50, 250, 50, 50, radians(0), radians(270))

    // 右下角的圖形,0-360°(角度)
    arc(250, 250, 50, 50, radians(0), radians(360))
  }
</script>

從上面的代碼可以看出,0°(角度)是在圖形的正右方。


順便展示一下不同 mode 的效果

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    // 左上角的圖形,默認(rèn)
    arc(50, 50, 50, 50, radians(0), radians(270))

    // 右上角的圖形,開放式半圓形(OPEN)
    arc(250, 50, 50, 50, radians(0), radians(270), OPEN)

    // 左下角的圖形,封閉式半圓形(CHORD)
    arc(50, 250, 50, 50, radians(0), radians(270), CHORD)

    // 右下角的圖形,封閉式餅形段(PIE)
    arc(250, 250, 50, 50, radians(0), radians(270), PIE)
  }
</script>

OPEN、CHORDPIE 這幾個常量都不需要我們定義的,p5.js 已經(jīng)在全局定義好了。


更多說明可查看 arc()說明文檔



其他圖形

除了前面講到的幾個基礎(chǔ)圖形,p5.js 還提供了貝塞爾曲線、球體、立方體、圓錐等圖形元素,甚至還能自定義多邊形。

但在光速入門階段我們只需掌握基礎(chǔ)的圖形,再加上自己的創(chuàng)意就可以做出很漂亮的作品。



文本

創(chuàng)建文本的方法叫 text()。

語法如下:

text(str, x, y, [x2], [y2])
  • str: 文本
  • xy 是文本基線左側(cè)的坐標(biāo)
  • x2y2 定義文本內(nèi)容占用的面積,x2 表示寬度,y2 表示高度。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    text('雷猴', 10, 20)
  }
</script>


我們還可以傳入 x2y2 參數(shù)來控制內(nèi)容的展示方式。

x2 會影響文本換行方式,y2 控制文本顯示的內(nèi)容。

先說 x2,這個參數(shù)是控制文本在 x 軸方向的展示長度,x2 - x 就可以得出這段文字在 x 軸方向可以展示的長度。

比如一個字符的寬度是 5px ,x 設(shè)為10,x2 設(shè)為20,那么一行就可以展示2個文字。

x2 并不能很好的控制文本長度,它只會判斷這行文本里有沒有空格,如果出現(xiàn)空格,且超出文本框?qū)挾鹊膬?nèi)容就會換行。


y2 - y 得出的長度就是y軸方向可展示的區(qū)域。超出這個區(qū)域的文本都不會展示出來了。


舉個例子

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(220, 220, 220)
  }

  function draw() {
    text(
      'Lorem ipsum dolor sit amet, consectetur adipisicing elit. Doloremque et assumenda quibusdam quis, rerum incidunt animi nihil perspiciatis temporibus neque!',
      10,
      20,
      40,
      60
    )
  }
</script>

此時,在 x2y2 的限制下,文本已經(jīng)無法完全展示出來了。



基礎(chǔ)樣式

p5.js 提供了幾個設(shè)置樣式的方法,我挑常用的幾個來講講。


顏色

p5.js 支持多種顏色值,比如 顏色關(guān)鍵字、十六進(jìn)制CSS顏色字符串RGB、HSBHSL、灰度


關(guān)鍵字 與 十六進(jìn)制

顏色關(guān)鍵字十六進(jìn)制CSS顏色字符串 就不多說了,合格的切圖仔都懂這個。

  • 關(guān)鍵字: 'red'、'blue' 等
  • 十六進(jìn)制: #ff0000


需要注意的是 RGBHSBHSL灰度。

其中,RGB、HSBHSL 都支持傳入第4個參數(shù),這個參數(shù)表示透明通道。


RGB

RGB 的第4個參數(shù)取值范圍是 0 ~ 255,0 表示完全透明,255 表示完全不透明。

如果不傳第4個參數(shù),默認(rèn)值是 255。

我用 background 背景色來舉例。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(152, 231, 162) // 設(shè)置綠色背景色
  }
</script>

如果此時在 background() 里傳入第4個參數(shù)就可以改變背景色的不透明度。

比如

file
background(152, 231, 162, 100)


HSB 與 HSL

HSBHSL 都是顏色表示的一種方法。

  • HSB: H(Hue) 色相、S(Saturation) 飽和度、B(Brightness) 亮度
  • HSL: H(Hue) 色相、S(Saturation) 飽和度、L(Lightness) 明度

它們二者之間的區(qū)別可以自行百度搜搜,或者可以看看這篇文章:《色彩空間中的 HSL、HSV、HSB 有什么區(qū)別?》。這不是本文的重點(diǎn)。


HSBHSL用法 上差不多,但和 RGB 是有區(qū)別的。

  1. 使用 HSBHSL 前,要設(shè)置顏色模式,告訴 p5.js 要使用哪種顏色模式去渲染。而 RGB 就省略了這步。
  2. HSBHSL 第1個參數(shù)取值 0 ~ 360,第2和第3個參數(shù)取值是 0 ~ 100。而 RGB 前3個參數(shù)的取值都是 0 ~ 255
  3. 在透明度上,HSBHSL 在第4個參數(shù)的取值范圍是 0 ~ 1 ,而 RGB0 ~ 255 。

如果要使用 HSB ,就需要使用 colorMode(HSB) 設(shè)置一下;HSL 就用 colorMode(HSL) 設(shè)置一下。


還是用 background() 舉例

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    colorMode(HSB) // 設(shè)置 HSB 顏色模式
    background(360, 30, 80) // 設(shè)置背景色
    // background(360, 30, 80, 0.5) // 背景色,添加透明通道
  }
</script>


灰度

灰度模式的意思是只有 “黑白灰” 三種顏色,而灰色是過渡顏色。

灰度模式是默認(rèn)的顏色模式,不需要進(jìn)行特殊設(shè)置。

灰度模式的取值范圍是 0 ~ 255。0表示黑色,255表示白色,中間的其他值表示不同程度的灰色。


使用 RGB 設(shè)置顏色,需要傳 3 ~ 4 個參數(shù),而使用灰度模式只需傳1個參數(shù)。

還是拿 background() 舉例

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(128) // 設(shè)置背景色
  }
</script>


背景色 background()

前面一直使用背景色,相信大家已經(jīng)對 background() 的用法非常熟悉了。

通常 background() 會在2個地方用到。

一個是寫在 setup() 里,在初始化畫布時可以設(shè)置畫布背景色。

還可以寫在 draw() 里,每次刷新畫布都可以設(shè)置畫布背景色。寫在 draw() 里,畫布每次刷新都會重新設(shè)置一次背景色。某些情況下是很有用的,比如移動圖像時,如果背景色沒重新設(shè)置一次,那么圖形移動后會產(chǎn)生“殘留”的現(xiàn)象。這個放在動畫章節(jié)說。


填充顏色 fill()

創(chuàng)建圖像后,圖像默認(rèn)的填充色是白色。

要修改圖像填充色,使用 fill() 方法即可。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }
  function draw() {
    fill('#f2c0ca') // 設(shè)置填充色
    rect(30, 30, 100, 80)
    circle(220, 70, 80)
  }
</script>

需要注意的是,一旦設(shè)置了 fill() ,在它后面創(chuàng)建的圖形都會使用相同的填充色,正如上面的例子那樣。

如果希望后面的圖形使用別的顏色,可以再重新調(diào)用一遍 fill() 進(jìn)行設(shè)置。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }
  function draw() {
    fill('#f2c0ca') // 設(shè)置填充色
    rect(30, 30, 100, 80)
    fill('yellow') // 重新設(shè)置填充色
    circle(220, 70, 80)
  }
</script>


無填充 noFill()

如果不想設(shè)置填充色,可以使用 noFill() 方法。

不填充的情況下,圖形內(nèi)部將會設(shè)置成透明,會直接顯示在它下層的顏色,如果它下層沒有其他元素,則會直接顯示背景色。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }

  function draw() {
    noFill()
    rect(30, 30, 100, 80)
    circle(220, 70, 80)
  }
</script>


邊框顏色 stroke()

p5.js 創(chuàng)建出來的元素默認(rèn)是有一個黑色邊框,如果想要修改邊框顏色,可以使用 stroke() 方法。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }

  function draw() {
    stroke('red') // 設(shè)置邊框顏色
    rect(30, 30, 100, 80)
    circle(220, 70, 80)
  }
</script>

fill() 一樣,在使用 stroke() 設(shè)置完顏色之后的圖形都會使用這個邊框顏色。如果要再次修改邊框顏色,只需再次使用 stroke() 即可。


無邊框 noStroke()

如果不希望圖形有邊框,可以使用 noStroke() 方法。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }

  function draw() {
    noStroke() // 無邊框
    rect(30, 30, 100, 80)
    circle(220, 70, 80)
  }
</script>


設(shè)置邊框粗細(xì) strokeWeight()

使用 strokeWeight() 方法可以設(shè)置圖形邊框的粗細(xì)。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }

  function draw() {
    strokeWeight(10) // 設(shè)置邊框粗細(xì)
    rect(30, 30, 100, 80)
    circle(220, 70, 80)
  }
</script>


修改文字大小 textSize()

使用 textSize() 方法可以修改文字的字號

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(200)
  }

  function draw() {
    textSize(100)
    text('雷猴', 20, 100)
  }
</script>


關(guān)于文字的樣式,前面說到的 fill()stroke()、strokeWeight() 方法都可以對文字的填充色、描邊等樣式進(jìn)行設(shè)置。自己動手試試吧~



圖片

在打算將圖片加入到畫布之前,我們需要了解 preload() 函數(shù)。

preload() 函數(shù)也是 p5.js 的一個生命周期函數(shù),它會在 setup() 前執(zhí)行。

preload() 可以強(qiáng)制程序等待,直到 preload() 函數(shù)內(nèi)的資源加載完成或者事件執(zhí)行完再執(zhí)行其他代碼。

所以一般會把圖片和視頻等資源加載寫在 preload() 里。


了解完 preload() 后,我們就可以使用 loadImage() 方法加載圖片,使用 image() 方法渲染圖片。

注意:加載和渲染是分開2步操作的!

本例請來的演員是我的貓 Bubble

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  let img = null

  function preload() {
    img = loadImage('./cat-bubble.jpg') // 加載圖片
  }

  function setup() {
    createCanvas(200, 200) // 創(chuàng)建畫布
  }

  function draw() {
    image(img, 0, 0) // 渲染圖片
  }
</script>
  • loadImage() 方法傳入圖片地址
  • image(img, x, y) 方法第一個參數(shù)是圖片對象。xy 是圖片左上角的坐標(biāo)。


除了可以渲染 jpgpng 外,p5.js 還可以渲染動圖gif。

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  let img = null

  function preload() {
    img = loadImage('./portrait.gif') // 加載 gif
  }

  function setup() {
    createCanvas(240, 150)
  }

  function draw() {
    image(img, 0, 0) // 渲染圖片
  }
</script>

可以在 setup() 函數(shù)里使用 frameRate() 方法設(shè)置幀率,這可以影響gif的刷新率。



交互事件

p5.js 提供了很多鼠標(biāo)和鍵盤的交互事件,入門階段我們挑2個來學(xué)就行。

交互事件通常寫在 draw() 函數(shù)里。


鼠標(biāo)點(diǎn)擊 mouseIsPressed

本例使用 mouseIsPressed 判斷用戶是否點(diǎn)擊了鼠標(biāo),點(diǎn)擊鼠標(biāo)時畫布背景是藍(lán)色,松開鼠標(biāo)后畫布背景是橙色

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background('orange')
  }

  function draw() {
    if (mouseIsPressed) { // 檢測鼠標(biāo)是否按下
      background('skyblue')
    } else {
      background('orange')
    }
  }
</script>

draw() 函數(shù)在頁面運(yùn)行時會一直執(zhí)行,所以 mouseIsPressed 寫在 draw() 里可以被捕捉到。如果用戶點(diǎn)擊鼠標(biāo),且被捕捉到 mouseIsPressed 時,mouseIsPressed 會返回 true


按住鍵盤 keyIsPressed

keyIsPressed 可以檢測用戶當(dāng)前是否按住鍵盤,如果鍵盤被按下會返回 true ,否則返回 false。


file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background('orange')
  }

  function draw() {
    if (mouseIsPressed) { // 檢測鍵盤是否按下
      background('skyblue')
    } else {
      background('orange')
    }
  }
</script>



動畫

動畫其實(shí)就是在修改元素屬性的同時不斷刷新畫布。

p5.js 里做動畫效果其實(shí)很簡單,只需要在 draw() 里修改元素屬性即可。


舉個例子:圓形圖案跟隨鼠標(biāo)指針移動

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(100)
  }

  function draw() {
    background(100)
    circle(mouseX, mouseY, 40, 40)
  }
</script>


有沒有發(fā)現(xiàn),上面的例子在 draw() 里首先設(shè)置背景色,再創(chuàng)建一個新的圓。

如果沒重新設(shè)置背景色的話,上一幀的圓會保留下來。很多時候保留上一幀的數(shù)據(jù)會產(chǎn)生不錯的藝術(shù)作品。

試試把 draw() 里的 background(100) 這句刪掉

file
<script src="https://cdn.jsdelivr.net/npm/p5@1.5.0/lib/p5.js"></script>
<script>
  function setup() {
    createCanvas(300, 300)
    background(100)
  }

  function draw() {
    circle(mouseX, mouseY, 40, 40)
  }
</script>

這個也是p5.js官網(wǎng)的例子


到此,相信各位工友已經(jīng)對 p5.js 有一定的了解了。



代碼倉庫

?P5.js 學(xué)習(xí)案例



推薦閱讀

??《Canvas 從入門到勸朋友放棄(圖解版)》

??《SVG 從入門到后悔,怎么不早點(diǎn)學(xué)起來(圖解版)》

??《Three.js 起飛》

??《Fabric.js 從入門到膨脹》

??《純CSS實(shí)現(xiàn)117個Loading效果》

??《這18個網(wǎng)站能讓你的頁面背景炫酷起來》


點(diǎn)贊 + 關(guān)注 + 收藏 = 學(xué)會了
代碼倉庫

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容