[Help] Hỏi về lập trình animation bằng html

Thảo luận trong 'Thư giãn' bắt đầu bởi BadPlayBoy, 1/2/17.

  1. HeroJAV

    HeroJAV Cán Bộ Nguồn Lão Làng GVN

    Tham gia ngày:
    1/1/11
    Bài viết:
    10,081
    Cho hỏi ngu tí là cái này có giống gif không? Có dùng làm sticker được không
     
  2. haiduong87

    haiduong87 Knee before Eden Lord Lão Làng GVN

    Tham gia ngày:
    20/5/04
    Bài viết:
    24,516
    Nơi ở:
    TP HCM
    Khác, sticker dc
     
    HeroJAV thích bài này.
  3. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    Nghĩ cái này cũng đơn giản thôi, đâu có phức tạp, nếu chỉ có một chút như vậy mà phải học lập trình thì phiền quá. Lên mạng mò mẫm cũng được kết quả như bài đầu thôi, nói chung là đã đạt được kết quả có điều cần giúp để code nó ngắn gọn và dễ hiểu. (cái mẫu trong spoiler ở post 1 là đã làm hoàn chỉnh rồi, nhưng rối và chậm, ví dụ muốn tăng tốc độ chạy 24 frame/s với hình có kích thước lớn thì không được, có thể là tại máy yếu).
    Cái canvas có rồi, để bên file html (thẻ head, html...không cần thiết nên bỏ luôn):
    [​IMG]
    Làm như thế nào?
     
    Chỉnh sửa cuối: 1/2/17
  4. thinhmc123

    thinhmc123 Youtube Master Race Lão Làng GVN

    Tham gia ngày:
    22/6/08
    Bài viết:
    14
    bên file animated.js cậu xoá 3 thẻ HTML ở trên cùng đi và thay bằng init();
    thay dòng sprite.src = "003.png"; bằng sprite.src = "../003.png";

    setInterval(draw,100); dòng này có nghĩa là cứ sau 100 millisecond sẽ gọi hàm draw() 1 lần. vì vậy nếu muốn tăng frame thì chỉ cần giảm thời gian xuống < 100.

    cuối cùng là xoá nốt 3 thẻ HTML ở cuối file đi là được.
     
    BadPlayBoy thích bài này.
  5. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    Đã thử và không thành công.

    Thử copy đoạn code dưới này xem có chạy không, vì có thể tôi gõ sai, cái ảnh 003.png là cái ảnh ở post đầu:
    Mã:
    function init(){
        can = document.getElementById('animated');
        ctx = can.getContext('2d');
        sprite.onload = start;
        sprite.src = "../003.png";
    }
    function start() {
        row = 5 ; col = 3 ;
        w = sprite.width / col ;
        h = sprite.height / row ;
        frame = 0 ;
        setInterval(draw, 100);
    }
    function draw() {
        (frame == row*col-1) ? frame =0 : frame++;
        sX= Math.floor( frame % col) * w;
        sY= Math.floor( frame / col) * h;
        ctx.clearRect(0,0, can.width, can.height);
        ctx.drawImage(sprite,sX,sY,w,h,154,106, w*2, h*2);
    }
    
     
  6. haiduong87

    haiduong87 Knee before Eden Lord Lão Làng GVN

    Tham gia ngày:
    20/5/04
    Bài viết:
    24,516
    Nơi ở:
    TP HCM
    vào đây:
    http://www.w3schools.com/cssref/tryit.asp?filename=trycss3_keyframes
    paste đống này vào bên trái và bấm run.
    Dĩ nhiên là demo cho thấy nó chạy dc thôi, còn ko rảnh để dò pixel từ tấm hình đó để ra cái animate đẹp
    Và cũng là demo thôi, chứ thật ra thì nó ko dùng animation đâu
    Vừa thử lại nó dùng animation cũng dc :D
    Mã:
    <!DOCTYPE html>
    <html>
    <head>
    <style>
    div {
        background-image: url(https://scontent.fsgn3-1.fna.fbcdn.net/t39.1997-6/s600x600/14050148_1775288516045186_2084972320_n.png);
        background-size: 576px 432px;
        cursor: pointer;
        height: 120px;
        width: 120px;
        background-position: -12px -12px;
        image-rendering: -webkit-optimize-contrast;
        animation: mymove 5s infinite;
    }
    
    
    /* Standard syntax */
    @keyframes mymove {
        0%   {background-position: -12px -12px;}
        25%  {background-position: -12px 24px;}
        75%  {background-position: -12px 36px;}
        100% {background-position: -12px 48px;}
    }
    </style>
    </head>
    <body>
    
    <p><strong>Note:</strong> The @keyframes rule is not supported in Internet Explorer 9 and earlier versions.</p>
    
    <div></div>
    
    </body>
    </html>

    demo này đẹp hơn nè :3
    http://jsfiddle.net/simurai/CGmCe/light/
     
    Chỉnh sửa cuối: 1/2/17
    HeroJAV and BadPlayBoy like this.
  7. thinhmc123

    thinhmc123 Youtube Master Race Lão Làng GVN

    Tham gia ngày:
    22/6/08
    Bài viết:
    14
    cậu thử lại thế này xem sao.
    Mã:
    var can,ctx,row,col,w,h,frame,sX,sY;
    var sprite = new Image();
    init();
    function init(){
        can = document.getElementById('animated');
        ctx = can.getContext('2d');
        sprite.onload = start;
        sprite.src = "./003.png";
    }
    function start() {
        row = 5 ; col = 3 ;
        w = sprite.width / col ;
        h = sprite.height / row ;
        frame = 0 ;
        can.width = w;
        can.height = h;
        setInterval(draw, 100);
    }
    function draw() {
        (frame == row*col-1) ? frame =0 : frame++;
        sX= Math.floor( frame % col) * w;
        sY= Math.floor( frame / col) * h;
        ctx.clearRect(0,0, can.width, can.height);
        ctx.drawImage(sprite,sX,sY,w,h,0,0, w, h);
    }
    
     
    Chỉnh sửa cuối: 1/2/17
    BadPlayBoy thích bài này.
  8. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    Thử cái đầu thấy có vẻ khó xài, mà hình như nó không làm nhảy frame được mà chỉ di chuyển ảnh thôi (tức là thấy rõ từng frame chuyển động), với lại còn phải ngồi tính vị trí từng frame.
    Còn cái thứ hai thì chỉ áp dụng cho sprite ngang (1 hàng nhiều cột), không dùng được cho sprite chữ nhật (nhiều hàng nhiều cột) thì phải.
    Mã:
    .hi {
        width: 150px;
        height: 150px;
        background-image: url("https://scontent.fsgn3-1.fna.fbcdn.net/t39.1997-6/s600x600/14050148_1775288516045186_2084972320_n.png");
      
        -webkit-animation: play .8s steps(4) infinite;
    }
    
    @-webkit-keyframes play {
       from { background-position:    0px; }
         to { background-position: -600px; }
    }
    
    
    Vẫn không được.

    animated.html
    Mã:
    <html>
            <canvas id="animated" width="154" height="106"></canvas>
            <script src="./animated_files/animated.js"></script>
    </html>
    
    animated.js
    Mã:
    var can,ctx,row,col,w,h,frame,sX,sY;
    var sprite = new Image();
    init();
    function init(){
        can = document.getElementById('animated');
        ctx = can.getContext('2d');
        sprite.onload = start;
        sprite.src = "../003.png";
    }
    function start() {
        row = 5 ; col = 3 ;
        w = sprite.width / col ;
        h = sprite.height / row ;
        frame = 0 ;
        can.width = w;
        can.height = h;
        setInterval(draw, 100);
    }
    function draw() {
        (frame == row*col-1) ? frame =0 : frame++;
        sX= Math.floor( frame % col) * w;
        sY= Math.floor( frame / col) * h;
        ctx.clearRect(0,0, can.width, can.height);
        ctx.drawImage(sprite,sX,sY,w,h,0,0, w, h);
    }
    
     
  9. haiduong87

    haiduong87 Knee before Eden Lord Lão Làng GVN

    Tham gia ngày:
    20/5/04
    Bài viết:
    24,516
    Nơi ở:
    TP HCM
    uhm tui vừa làm lại cho đẹp mà bà mẹ nó còn dư cái thanh đen đen thằng nào fix giùm coi @@
    Mã:
    <!DOCTYPE html>
    <html>
    <head>
    <style>
    div {
        background-image: url(http://i.imgur.com/C5eSOeb.png);
        cursor: pointer;
        height: 104px;
        width: 152px;
        background-position: 0px 0px;
        animation: mymove 4s steps(1) infinite;
    }
    
    
    /* Standard syntax */
    @keyframes mymove {
        0%   {background-position: 0px 0px;}
        6.6%   {background-position: -154px 0px;}
        13.2%   {background-position: -308px 0px;}
        19.8%   {background-position: 0px -106px;}
        26.4%   {background-position: -154px -106px;}
        33.0%   {background-position: -308px -106px;}
        46.2%   {background-position: 0px -212px;}
        52.8%   {background-position: -154px -212px;}
        59.4%   {background-position: -308px -212px;}
        66.0%   {background-position: 0px -318px;}
        72.6%   {background-position: -154px -318px;}
        79.2%   {background-position: -308px -318px;}
        85.8%   {background-position: 0px -424px;}
        92.4%   {background-position: -154px -424px;}
        100%   {background-position: -308px -424px;}
    }
    
    </style>
    </head>
    <body>
    
    <p><strong>Note:</strong> The @keyframes rule is not supported in Internet Explorer 9 and earlier versions.</p>
    
    <div></div>
    
    </body>
    </html>
    
     
    Chỉnh sửa cuối: 1/2/17
    BadPlayBoy thích bài này.
  10. thinhmc123

    thinhmc123 Youtube Master Race Lão Làng GVN

    Tham gia ngày:
    22/6/08
    Bài viết:
    14
    cậu sửa lại cái sprite.src thành sprite.src = "./003.png"; // cái này tuỳ thuộc vào path ảnh của cậu.
     
    BadPlayBoy thích bài này.
  11. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    Thanh đen nó là trên hình rồi, không fix được đâu, sprite bình thường nó không có cái thanh đó. Nhưng mà như vậy là được rồi. :))
    Có điều ngồi tính position cả mấy ngàn file (kích thước khác nhau) chắc vỡ mồm quá. 8-}
    Ok, lần này thì được rồi. Thật là vcl.
    PS: sprite.src = "./003.png" hay sprite.src = "003.png" đều được (cùng folder), cái đầu không chạy có lẽ là do sai ở chỗ "../003.png"
    Làm được thế này thì sprite nào cũng dùng được vì nó tự biết xuống hàng, không cần phải tính tọa độ từng cái.
    Giờ thì chỉ còn rắc rối công đoạn xoay hình mà không làm nặng xử lý thôi.
    [​IMG]
     
    Chỉnh sửa cuối: 1/2/17
  12. LartenCrepsley

    LartenCrepsley Youtube Master Race GameOver

    Tham gia ngày:
    13/7/15
    Bài viết:
    0
    BadPlayBoy thích bài này.
  13. haiduong87

    haiduong87 Knee before Eden Lord Lão Làng GVN

    Tham gia ngày:
    20/5/04
    Bài viết:
    24,516
    Nơi ở:
    TP HCM
    @BadPlayBoy
    vừa sửa lại script trên rồi, chưa biết tại sao lại có dấu trừ (-) :))
    nhưng nó chạy như mong đợi rồi
     
  14. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    À thôi giờ tự xử lý được rồi, khỏi cần code, lật mẹ nó cái hình là xong, khỏi code kiếc gì cả: =))
    [​IMG] [​IMG]
    Cám ơn tất cả. :))
     
  15. LartenCrepsley

    LartenCrepsley Youtube Master Race GameOver

    Tham gia ngày:
    13/7/15
    Bài viết:
    0
    tại sao thêm dấu âm là nó hiển thị đúng nhỉ =))
     
  16. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    Vì hình như nó xuất ngược, nếu là dấu dương thì nó đi ngược từ frame cuối đến frame đầu, còn để dấu trừ thì nó đi từ frame đầu đến frame cuối. =))
    Hiểu đại khái là theo trình tự animation thì nó phải nhảy từ ảnh 1 -> 2 -> 3 -> 4 -> ... tức là đi từ trái qua phải, nhưng nếu muốn như thế thì tấm ảnh to sẽ di chuyển từ phải qua trái (tức là đi lùi, mà đi lùi là trừ, đi tới là cộng). =))
     
  17. haiduong87

    haiduong87 Knee before Eden Lord Lão Làng GVN

    Tham gia ngày:
    20/5/04
    Bài viết:
    24,516
    Nơi ở:
    TP HCM
    Có thể với setup kia thì bg-position là vị trí của background so với cái div, nhưng khi setup thì mình lại nghĩ là vị trí của cái div so với cái background nên nó sai bét
     
  18. hanhnn13

    hanhnn13 Mr & Ms Pac-Man

    Tham gia ngày:
    5/8/09
    Bài viết:
    235
    nhiều code quá, bản nào update mới nhất đấy
     
  19. BadPlayBoy

    BadPlayBoy Dante, the strongest Demon Slayer Lão Làng GVN

    Tham gia ngày:
    7/4/05
    Bài viết:
    14,071
    Vcl, bao lâu rồi giờ lại lôi lên.
    Có thể dùng 1 trong 2 code này, đây là những bước làm thủ công (không cần trình soạn thảo web):

    1. Dùng html và js:
    - Tạo file html, có thể right click -> new -> text document (tạo file notepad), sửa tên file thành *.html (ví dụ a.html).
    - Mở file a.html bằng notepad, chép đoạn code vào:
    canvas id là gán tên cho nó (tên gì cũng được), width là độ rộng ảnh hiển thị, height là độ cao ảnh hiển thị. Ảnh gốc nó là 461 x 534, 461 chia cho 3 cột là 153.66 (làm tròn 154 hay 153 cũng được), 534 chia cho 5 hàng là 106.8 (làm tròn 106)
    script src là đường dẫn đến file *.js.

    - Tạo file *.js, tạo 1 folder mới đặt cùng folder với file html, folder này sẽ là folder con của html, đặt tên folder mới trùng tên với html kèm theo _files, ví dụ file a.html thì folder con sẽ là a_files (cái này tùy mình đặt tên thôi, code trên kia tôi đặt tên là animated.html nên folder con cũng phải đặt là animated_files).
    - Bên trong folder con a_files, right click -> new -> text document, sửa tên file thành *.js (tên gì cũng được, nhưng phải trùng tên với đường dẫn trên file html.
    - Mở file *.js bằng notepad, chép đoạn code vào:
    can = document.getElementById là tên canvas id mình đã đặt trước đó.
    sprite.src là đường dẫn đến file ảnh, nếu để cùng folder với file html thì chỉ cần copy tên file ảnh là được, còn nếu có tạo folder con chứa ảnh trong đó thì phải sửa đường dẫn vào. Ví dụ này tôi dùng ảnh trong máy nên đặt tên nó là 003.png, còn nếu dùng ảnh đã up trên mạng thì copy/paste đường dẫn vào, ví dụ http://i.imgur.com/C5eSOeb.png.
    row là số hàng, col là số cột (cái này để nó chia ảnh gốc ra nhiều phần, nếu row là 2 thì nó sẽ chia ảnh thành 2 phần, nếu row là 3 thì nó sẽ chia ảnh thành 3 phần...) trong ví dụ này thì cái ảnh nó có 5 hàng 3 cột.
    setInterval là tốc độ chuyển ảnh, số càng nhỏ thì nó chạy càng nhanh.
    Dùng cái này thì tuy set hơi cực nhưng chỉ cần tạo 1 lần, những lần sau có xài ảnh khác chỉ cần copy rồi thay đổi mấy cái chỗ tôi bôi màu cho phù hợp là được.

    2. Dùng html:
    - Tạo file html, right click -> new -> text document, sửa tên file thành *.html (ví dụ b.html).
    - Mở file a.html bằng notepad, chép đoạn code vào:
    background-image là đường dẫn đến file ảnh, tương tự phương pháp (1), có thể dùng ảnh up trên mạng hoặc ảnh trên máy.
    height là độ cao ảnh hiển thị, width là độ rộng ảnh hiển thị. Cũng tương tự phương pháp (1) thôi, kích thước nhỏ hơn vì muốn che đi cái đường viền màu đen thôi.
    background-position là vị trí điểm ảnh gốc (ở đây set 0-0)
    animation là tốc độ tính bằng giây cho mỗi lần lặp, số cành nhỏ tốc độ càng nhanh, ví dụ này là 1.5 giây.
    keyframes mymove là vị trí điểm ảnh của từng frame. Bước này sẽ phải tính toán xem ảnh gốc kích thước bao nhiêu, tổng cộng là bao nhiêu frame. Trong ví dụ này thì có 15 frame.
    + % là giai đoạn animation, do có 15 frame tức là có 15 giai đoạn, lấy 100/15 =6.6%, mỗi giai đoạn nó là 6.6%, bắt đầu từ giai đoạn 1 là 0%, giai đoạn 2 là 6.6%, giai đoạn 3 là 13.3%, giai đoạn 4 là 20% (hoặc như trong ví dụ này tính theo kiểu 1 giai đoạn 6.6%, nhân 2 là 13.2%, nhân 3 là 19.8%... nói chung không cần chính xác tuyệt đối). Tiếp tục đến 100% là kết thúc.
    + background-position là vị trí điểm ảnh từng frame, tính đơn giản là chiều rộng ảnh full gốc 461 chia cho 3 cột là 153.6, ở ví dụ này lấy vị trí 154, 154+154=308.
    + Tiếp tục tính vị trí chiều cao, lấy chiều cao ảnh full gốc là 534 chia cho 5 hàng là 106.8 (ví dụ này lấy vị trí 106, 106+106=212, 212+106=318, 318+106=424.
    <div></div> là vị trí hiển thị, viết gì vào đấy thì nó sẽ hiện chữ ra (ví dụ <div>Viết chữ vào đây</div>), nếu không muốn hiện gì hết thì để trống.
    Dùng phương pháp (2) thì set khá khỏe, nhưng sau này nếu dùng ảnh khác, kích thước khác thì sẽ phải tự tính lại vị trí từng frame.
     
    Chỉnh sửa cuối: 11/2/17

Chia sẻ trang này