上一篇文章:填坑!完結娛樂圈明星關係圖譜 發佈後,古柳印象裏過往留下的坑貌似只剩下 圖像檢索(一):因緣際會與前瞻 的後續實踐代碼(原文裏給了參考代碼連接)和在豆瓣Top250電影海報上的嘗試效果了。
javascript
一想到全部坑都被填了(若是還有啥是我不記得的,請千萬不要提醒我),就以爲真是業界良心,倍感輕鬆。html
因而古柳某日點開 圖像檢索(一):因緣際會與前瞻一文,回顧「佳做」之餘,也找了下里面清華美院向帆老師的做品集網站 zeelab Projects。前端
PS:若是你沒看過這個演講,推薦一看,古柳至今難忘:【一席】向帆:若是把每一年的春晚都像蚊香同樣捲起來的話,它就是這樣的
java
而在這些做品中,古柳更中意且也想實現下相似網頁展現效果的是:AwardPuzzel - zeelab 。下面援引下「官方」介紹,建議去網頁體驗一下:編程
AwardPuzzel 是一個全國美展油畫類獲獎畫做的數據視覺化做品,收錄了美展第六屆至第十二屆的2276幅獲獎做品,經過動態交互的方式呈現了中國油畫30年間的藝術歷程、形態、色彩、尺寸和地區之間的變化和關係以及中國油畫大師們的藝術思路。
本做品能夠被看成研究工具爲研究者和評論家使用,亦可做藝術做品欣賞。
咱們但願經過這個平臺分享咱們的視角,也但願使用者經過本身的瀏覽和觀察獲得本身的結論。
全國美展是中國美術界最重要事件,每五年舉辦一次,第六屆是1984年舉辦,第十二屆爲2014年舉辦。canvas
雖然古柳不怎麼會前端,但自從接觸爬蟲以來,右鍵「審查元素」,查看網頁源代碼的習慣仍是有的。微信
因而不看不知道,一看又引出了後續的諸多故事,借用書上的一句話:「那日也是合該有事」,且聽古柳慢慢道來……
dom
點開網頁源代碼後,找到數據展現和交互的區域對應的代碼天然是不難的。這裏爲了展現方便,特意丟到 Carbon 裏,重點突出下這段代碼。編程語言
能夠看到 HTML
裏主要用了 canvas
標籤,這也沒什麼,古柳反正不懂 canvas
,睜眼瞎罷了,也看不出什麼名堂。可是卻發現標籤裏的 data-processing-soucres
屬性對應的 .pde
文件,特別不同凡響,「聞所未聞,見所未見」,而且想起當初也曾各類蒐羅,希冀能復現向帆老師的春晚或美展油畫項目,雖不了了之,但對 processing
這一能實現各類藝術創意的編程語言有了印象。
ide
因而谷歌了下 「HTML+Canvas+Processing」
等關鍵詞,意外地發現:基於 Java
的 Processing
語言的家譜中,還有對應 JavaScript
和 Python
版本,前者即:P5.js
,而這不由使古柳看到了能在網頁中復現上述效果的但願。
提及來,以前古柳壓根一丁點都沒據說過 P5.js
,搜了下對應的中文資料也不算多,更偏心看視頻學習的我,看到萬能的B站上有人搬運了油管上Daniel Shiffman
的教學視頻(1-12節),因而立馬刷了下,p5.js 基礎教程 1-7,並所有跟着敲了遍代碼,雖然無字幕,但還蠻好啃的,有不少針對初學編程的知識講解。(原始連接:Code! Programming with p5.js - YouTube)
習得新技能後,立馬用明星關係圖譜的圖片簡單粗暴的拼了下照片牆,雖然離美展油畫的效果差了十萬八千里,但也算是賣出了第一步。
其實之前就沒少拼照片牆,想來你們也都見過爬取微信好友而後拼圖的文章,但古柳仍是安利下這篇舊文,裏面的圖片絕對值得一看(若是你看完以爲也不咋地,那……也就隨它去吧):Python PIL庫實現的照片牆成果圖分享。
再就是幾天前,看到 @愛可可-愛生活
老師的這則微博:Processing 創做的生成藝術 via:おかず,配圖漂亮就不說了,重點是帶着 Processing
關鍵詞,因而就埋下了想用 P5.js
實現一波的念頭。
幸運地找到了做品的出處:Generative Art #146 via:おかず,欣喜地發現附有 Processing
實現代碼,並且該系列有更多不錯的做品,遂萌發了想將其全部做品用 P5.js
實現一波並開源的想法。
固然由於目前 P5.js
不夠熟練,JavaScript
/ ES6
之類也只是入門,不免有所擔憂和顧慮。但在復現這個做品時發現 Processing
和 P5.js
真的很像,不少函數接口官方設計成統一的,極大下降了門檻。
上圖就是古柳用 P5.js
復現的效果,雖然還有些小問題,代碼也不必定最規範,但先行分享,後續再優化哈!可在此網址體驗做品生成效果:editor.p5js.org/DesertsX/sk…
歡迎關注,「牛衣古柳」哈!
let particles;
const n = 120;
function setup() {
createCanvas(900, 900);
// pixelDensity(2);
colorMode(HSB, 360, 100, 100, 100);
rectMode(CENTER);
newParticles();
}
function draw() {
for (let i in particles) {
let p = particles[i];
p.run();
if (p.isDead()) {
particles.splice(i, 1);
}
}
}
function forms() {
for (let j = 0; j < n; j++) {
let x = random(width), y = random(height);
let s = random(20, 100);
let hs = s / 2;
let c = getCol();
noStroke();
fill(c);
if (random(1) > 0.5) {
for (let i = -s / 2; i < s / 2; i++) {
particles.push(new Particle(x + i, y - hs, c));
particles.push(new Particle(x + i, y + hs, c));
particles.push(new Particle(x - hs, y + i, c));
particles.push(new Particle(x + hs, y + i, c));
}
square(x, y, s);
} else {
for (let a = 0; a < TAU; a += TAU / 360) {
particles.push(new Particle(x + hs * cos(a), y + hs * sin(a), c));
}
circle(x, y, s);
}
}
}
function newParticles() {
// particles = new ArrayList<Particle>();
particles = new Array();
background("#FCFCF0");
forms();
noiseSeed(parseInt(random(100000)));
}
// function mousePressed() {
// newParticles();
// }
function keyPressed() {
// 還沒生效
if (keyCode === 's') {
saveFrame("123.png");
}
}
function getCol() {
let colors = ["#e4572e", "#29335c", "#f3a712", "#a8c686", "#669bbc", "#efc2f0"];
//let colors = ["#880D1E", "#DD2D4A", "#F26A8D", "#F49CBB", "#CBEEF3"];
let idx = parseInt(random(colors.length));
// console.log(idx + colors[idx]);
return colors[idx];
}
class Particle {
constructor(x, y, col) {
this.pos = createVector(x, y);
this.step = 1;
this.angle = random(10);
this.lifeSpan = 100;
this.noiseScale = 800;
this.noiseStrength = 90;
this.col = col;
}
show() {
noStroke();
// fill(this.col, this.lifeSpan);
fill(this.col);
circle(this.pos.x, this.pos.y, 0.5);
}
move() {
this.angle = noise(this.pos.x / this.noiseScale, this.pos.y / this.noiseScale) * this.noiseStrength;
this.pos.x += cos(this.angle) * this.step;
this.pos.y += sin(this.angle) * this.step;
this.lifeSpan -= 0.1;
}
isDead() {
return (this.lifeSpan < 0.0)
}
run() {
this.show();
this.move();
}
}複製代碼