用Canvas繪制自己的時鐘

這次我通過用Canvas實現(xiàn)一個時鐘來牵现,學習Canvas繪圖的基本API和用法,對于例子里面用到的每一個API科乎,我都會詳細的列出它的用法贼急。

首先來看一下繪制完成后的效果圖

時鐘.PNG

這個時鐘可以通過調(diào)整畫布的寬高來增大和縮小空闲,效果不會有改變走敌。

繪制的基本思路是

  • 時鐘背景圖的繪制
  • 時針、分針、秒針、原點的繪制
  • 讓時針矫户、分針残邀、秒針動起來
時鐘背景圖的繪制

首先在HTML中定義一個寬高為400的畫布Canvas

<div>
       <canvas id="clock" height="400" width="400"></canvas>
   </div>

然后獲取畫布元素,定義畫布的執(zhí)行上下文ctx

/*獲取畫布元素*/
var dom = document.getElementById("clock");
/*獲得2d執(zhí)行環(huán)境*/
var ctx = dom.getContext('2d');

獲取畫布的寬高,以及定義時鐘的半徑

/*定義半徑為寬度的一半*/
var r = width/2;
/*縮放比例*/
var rem = width / 200;

接下來進行背景圖的繪制驱闷,包括背景圓空另,12個數(shù)字扼菠,還有60個點的繪制坝咐,代碼如下,注釋已經(jīng)詳細說明了過程

/*畫時鐘的背景圖*/
function drawBackground(){
    /*一開始先把畫布的初始狀態(tài)保存下來*/
    ctx.save();
    /*將畫布的中心原點由(0,0)變成(r,r)*/
    ctx.translate(r,r);
    /*開始繪畫*/
    ctx.beginPath();
    /*定義畫筆的寬度*/
    ctx.lineWidth = 10*rem;
    /*繪制一個圓*/
    ctx.arc(0,0,r-5*rem,0,2*Math.PI,false);
    /*進行填充*/
    ctx.stroke();
    /*畫時鐘上的12個數(shù)字*/
    var hourNumber = [3,4,5,6,7,8,9,10,11,12,1,2];//12個小時數(shù)
    ctx.font = 18*rem +'px Arial';//定義字體大小和樣式
    ctx.textAlign='center';//將文本內(nèi)容居中對齊
    ctx.textBaseline='middle';//將文本基線設置為中線
    hourNumber.forEach(function(number,i){
        var rad = 2*Math.PI/12*i;//每個數(shù)字的弧度
        /*求出數(shù)字存放位置的x和y坐標*/
        var x = Math.cos(rad)*(r - 30*rem);
        var y = Math.sin(rad)*(r - 30*rem);
        /*填充數(shù)字*/
        ctx.fillText(number,x,y);
    });
    /*繪制60個點*/
    for(var i=0;i<60;i++){
        var rad = 2*Math.PI/60*i;
        var x = Math.cos(rad)*(r-18*rem);
        var y = Math.sin(rad)*(r-18*rem);
        ctx.beginPath();
        /*如果是小時數(shù)的位置就繪制成黑色*/
        if(i % 5 === 0){
            ctx.fillStyle = "#000";
            ctx.arc(x,y,2*rem,0,2 * Math.PI,false);
        }else{
            ctx.fillStyle = "#ccc";
            ctx.arc(x,y,2*rem,0,2 * Math.PI,false);
        }
        ctx.fill();
    }
}

時針秧饮、分針盗尸、秒針咪辱、圓點的繪制

代碼如下

function drawHour(hour,minute){
    /*再次保存當前畫布的狀態(tài)*/
    ctx.save();
    ctx.beginPath();
    var rad = 2 * Math.PI / 12 * hour;
    var mrad = 2 * Math.PI / 12 /60 * minute;
    ctx.rotate(rad+mrad);//旋轉當前繪畫
    ctx.lineWidth = 6*rem;
    ctx.lineCap = 'round';
    ctx.moveTo(0,10*rem);
    ctx.lineTo(0,-r/2);
    ctx.stroke();
    /*返回最近的一次SAVE的畫布狀態(tài)*/
    ctx.restore();
}
function drawMinute(minute){
    ctx.save();
    ctx.beginPath();
    var rad = 2 * Math.PI / 60 * minute;
    ctx.rotate(rad);
    ctx.lineWidth = 3*rem;
    ctx.lineCap = 'round';
    ctx.moveTo(0,10*rem);
    ctx.lineTo(0,-r + 40*rem);
    ctx.stroke();
    ctx.restore();
}
function drawSecond(second){
    ctx.save();
    ctx.beginPath();
    ctx.fillStyle = "#c14543";
    var rad = 2 * Math.PI / 60 * second;
    ctx.rotate(rad);
    ctx.moveTo(-3,20*rem);
    ctx.lineTo(3,20*rem);
    ctx.lineTo(1,-r+18*rem);
    ctx.lineTo(-1,-r+18*rem);
    ctx.fill();
    ctx.restore();
}
function drawDot(){
    ctx.beginPath();
    ctx.fillStyle="#fff";
    ctx.arc(0,0,3*rem,0,2*Math.PI,false);
    ctx.fill();
}

讓時鐘動起來

function draw(){
    /*動態(tài)改變的時候历恐,每一次都要先將之前的矩形畫布清除掉弱贼,然后重新繪制*/
    ctx.clearRect(0,0,width,height);
    var now = new Date();
    var hour = now.getHours();
    var minute = now.getMinutes();
    var second = now.getSeconds();
    drawBackground(width);//背景
    drawHour(hour,minute);//小時
    drawMinute(minute);//分鐘
    drawSecond(second);//秒
    drawDot();//中心原點
    /*恢復到一開始save的那個畫布狀態(tài)吮旅,進行重新繪制*/
    ctx.restore();
}
draw();
setInterval(draw,1000);
最后編輯于
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市檬嘀,隨后出現(xiàn)的幾起案子责嚷,更是在濱河造成了極大的恐慌,老刑警劉巖揍异,帶你破解...
    沈念sama閱讀 221,820評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件衷掷,死亡現(xiàn)場離奇詭異柿菩,居然都是意外死亡,警方通過查閱死者的電腦和手機碗旅,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,648評論 3 399
  • 文/潘曉璐 我一進店門祟辟,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人醇份,你說我怎么就攤上這事吼具∞趾校” “怎么了?”我有些...
    開封第一講書人閱讀 168,324評論 0 360
  • 文/不壞的土叔 我叫張陵痊臭,是天一觀的道長广匙。 經(jīng)常有香客問我恼策,道長,這世上最難降的妖魔是什么分唾? 我笑而不...
    開封第一講書人閱讀 59,714評論 1 297
  • 正文 為了忘掉前任改含,我火速辦了婚禮迄汛,結果婚禮上骤视,老公的妹妹穿的比我還像新娘专酗。我一直安慰自己,他們只是感情好沉填,可當我...
    茶點故事閱讀 68,724評論 6 397
  • 文/花漫 我一把揭開白布翼闹。 她就那樣靜靜地躺著蒋纬,像睡著了一般猎荠。 火紅的嫁衣襯著肌膚如雪蜀备。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,328評論 1 310
  • 那天输虱,我揣著相機與錄音脂凶,去河邊找鬼。 笑死艰猬,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的冠桃。 我是一名探鬼主播,決...
    沈念sama閱讀 40,897評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼污茵,長吁一口氣:“原來是場噩夢啊……” “哼泞当!你這毒婦竟也來了?” 一聲冷哼從身側響起襟士,我...
    開封第一講書人閱讀 39,804評論 0 276
  • 序言:老撾萬榮一對情侶失蹤陋桂,失蹤者是張志新(化名)和其女友劉穎蝶溶,沒想到半個月后抖所,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,345評論 1 318
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,431評論 3 340
  • 正文 我和宋清朗相戀三年涯鲁,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片抹腿。...
    茶點故事閱讀 40,561評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡岛请,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出警绩,到底是詐尸還是另有隱情崇败,我是刑警寧澤,帶...
    沈念sama閱讀 36,238評論 5 350
  • 正文 年R本政府宣布肩祥,位于F島的核電站后室,受9級特大地震影響,放射性物質發(fā)生泄漏混狠。R本人自食惡果不足惜岸霹,卻給世界環(huán)境...
    茶點故事閱讀 41,928評論 3 334
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望将饺。 院中可真熱鬧贡避,春花似錦痛黎、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,417評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春垢袱,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背姚糊。 一陣腳步聲響...
    開封第一講書人閱讀 33,528評論 1 272
  • 我被黑心中介騙來泰國打工肠槽, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留秸仙,地道東北人赌结。 一個月前我還...
    沈念sama閱讀 48,983評論 3 376
  • 正文 我出身青樓,卻偏偏與公主長得像穴店,于是被迫代替她去往敵國和親迹鹅。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 45,573評論 2 359

推薦閱讀更多精彩內(nèi)容