50个前端入门练手项目,助你掌握前端基础知识

1.Expanding Cards

效果如图所示:

1.png

  • 源码[1]

  • 在线示例[2]

  • [ ] 知识点总结:

CSS:弹性盒子布局中的flex属性:让所有弹性盒模型对象的子元素都有相同的长度,且忽略它们内部的内容。

JavaScript:利用[].filter.call()方法可快速实现简单的选项卡切换。如上述示例源码:

 
  
  1. const panelItems = document.querySelectorAll(".container > .panel");

  2. panelItems.forEach(item => {

  3.     item.addEventListener('click',() => {

  4.         [].filter.call(item.parentElement.children,el => el !== item).forEach(el => el.classList.remove('active'));

  5.         item.classList.add('active')

  6.     });

  7. });

  8. 复制代码

2.Progress Steps

效果如图所示:

2.gif

  • 源码[3]

  • 在线示例[4]

  • [ ] 知识点总结:

CSS:CSS变量的用法以及弹性盒子垂直水平居中外加伪元素的用法。JavaScript:计算进度条的宽度,类名的操作。如上述示例部分源码如下:

 
  
  1. function handleClass(el){

  2.     let methods = {

  3.         addClass,

  4.         removeClass

  5.     };

  6.     function addClass(c){

  7.         el.classList.add(c);

  8.         return methods;

  9.     };

  10.     function removeClass(c){

  11.         el.classList.remove(c);

  12.         return methods;

  13.     }

  14.     return methods

  15. }

  16. 复制代码

3.Rotating Navigation Animation

效果如图所示:

3.gif

  • 源码[5]

  • 在线示例[6]

  • [ ] 知识点总结:

CSS:CSS弹性盒子布局加rotate动画。

JavaScript:添加和移除类名的操作。如上述示例部分源码如下:

 
  
  1. const addClass = (el,className) => el.classList.add(className);

  2. const removeClass = (el,className) => el.classList.remove(className);

  3. 复制代码

4.hidden-search-widget

效果如图所示:

4.gif

  • 源码[7]

  • 在线示例[8]

  • [ ] 知识点总结:

CSS:CSS过渡动画 + 宽度的更改 + inputplaceholder样式。

JavaScript:添加和移除类名的操作。如上述示例部分源码如下:

 
  
  1. .search.active > .input {

  2.     width: 240px;

  3. }

  4. .search.active > .search-btn {

  5.     transform: translateX(238px);

  6. }

  7. .search > .search-btn,.search > .input {

  8.     border: none;

  9.     width: 45px;

  10.     height: 45px;

  11.     outline: none;

  12.     transition: all .3s cubic-bezier(0.25, 0.46, 0.45, 0.94);

  13.     border-radius: 8px;

  14. }

  15. 复制代码

 
  
  1. searchBtn.addEventListener('click',() => {

  2.     searchContainer.classList.toggle('active');

  3.     searchInput.focus();

  4. })

  5. 复制代码

5.Blurry Loading

效果如图所示:

5.gif

  • 源码[9]

  • 在线示例[10]

  • [ ] 知识点总结:

CSS:CSS filter属性的用法;。

JavaScript:定时器加动态设置样式。如上述示例部分源码如下:

 
  
  1. let load = 0;

  2. let timer = null;

  3. let blurryLoadingHandler = function(){

  4.     load++;

  5.     if(load > 99){

  6.         clearTimeout(timer)

  7.     }else{

  8.         timer = setTimeout(blurryLoadingHandler,20);

  9.     }

  10.     text.textContent = `页面加载${ load }%`;

  11.     text.style.opacity = scale(load,0,100,1,0);

  12.     bg.style.filter = `blur(${scale(load,0,100,20,0)}px)`;

  13. }

  14. blurryLoadingHandler();

  15. 复制代码

这里有一个非常重要的工具函数(后续有好几个示例都用到了这个工具函数),如下所示:

 
  
  1. const scale = (n,inMin,inMax,outerMin,outerMax) => (n - inMin) * (outerMax - outerMin) / (inMax - inMin) + outerMin;

  2. 复制代码

这个工具函数的作用就是将一个范围数字映射到另一个数字范围。比方说,将1 ~ 100的数字范围映射到0 ~ 1之间。详情[11]。

6.Scroll Animation

效果如图所示:

6.gif

  • 源码[12]

  • 在线示例[13]

  • [ ] 知识点总结:

CSS:CSS位移动画。

JavaScript:动态创建元素+元素滚动事件监听+视图可见区域的判断 + 防抖函数。如上述示例部分源码如下:

 
  
  1. function debounce(fn,time = 100){

  2.     let timer = null;

  3.     return function(){

  4.         if(timer)clearTimeout(timer);

  5.         timer = setTimeout(fn,time);

  6.     }

  7. }

  8. let triggerBottom = window.innerHeight / 5 * 4;

  9. boxElements.forEach((box,index) => {

  10.    const top = box.getBoundingClientRect().top;

  11.    if(top <= triggerBottom){

  12.        box.classList.add('show');

  13.    }else{

  14.       box.classList.remove('show');

  15.    }

  16. })

  17. 复制代码

7. Split Landing Page

效果如图所示:

7.gif

  • 源码[14]

  • 在线示例[15]

  • [ ] 知识点总结:

CSS:CSS过渡特效 + 弹性盒子垂直水平居中 + CSS定位 + 宽度的更改。

JavaScript:鼠标悬浮事件 + 类名的操作。如上述示例部分源码如下:

 
  
  1. HTMLElement.prototype.addClass = function(className) {

  2.     this.classList.add(className);

  3. };

  4. HTMLElement.prototype.removeClass = function(className){

  5.     this.classList.remove(className);

  6. }

  7. const on = (el,type,handler,useCapture = false) => {

  8.     if(el && type && handler) {

  9.         el.addEventListener(type,handler,useCapture);

  10.     }

  11. }

  12. on(leftSplit,'mouseenter',() => container.addClass('hover-left'));

  13. on(leftSplit,'mouseleave',() => container.removeClass('hover-left'));

  14. on(rightSplit,'mouseenter',() => container.addClass('hover-right'));

  15. on(rightSplit,'mouseleave',() => container.removeClass('hover-right'));

  16. 复制代码

从这个示例,我也知道了mouseenter、mouseleavemouseover、mouseout的区别,总结如下:

  1. enter只触发1次,只有等到鼠标离开了目标元素之后再进入才会继续触发,同理leave也是如此理解。而over与out就是不断的触发。

  2. enter进入子元素,通过e.target也无法区分是移入/移出子元素还是父元素,而over与out则可以区分。

8.Form Wave

效果如图所示:

8.gif

  • 源码[16]

  • 在线示例[17]

  • [ ] 知识点总结:

CSS:CSS渐变 + 弹性盒子垂直水平居中 + CSS过渡动画 + CSS位移变换 + 关注焦点伪类选择器与同级元素选择器的用法。

JavaScript:字符串替换成标签 + 动态创建元素。如上述示例部分源码如下:

 
  
  1. const createLetter = v => v.split("").map((letter,idx) => `${ letter }`).join("");

  2. 复制代码

9.Sound Board

效果如图所示:

9.gif

  • 源码[18]

  • 在线示例[19]

  • [ ] 知识点总结:

CSS:CSS渐变 + 弹性盒子垂直水平居中 + 基本样式。

JavaScript:动态创建元素 + 播放音频(audio标签)。如上述示例部分源码如下:

 
  
  1. sounds.forEach(sound => {

  2.     const btn = create('button');

  3.     btn.textContent = sound;

  4.     btn.type = "button";

  5.     const audio = create('audio');

  6.     audio.src = "./audio/" + sound + '.mp3';

  7.     audio.id = sound;

  8.     btn.addEventListener('click',() => {

  9.         stopSounds();

  10.         $('#' + sound).play();

  11.     });

  12.     buttonContainer.appendChild(btn);

  13.     buttonContainer.insertAdjacentElement('beforebegin',audio);

  14. });

  15. 复制代码

10. Dad Jokes

效果如图所示:

10.gif

  • 源码[20]

  • 在线示例[21]

  • [ ] 知识点总结:

CSS:CSS渐变 + 弹性盒子垂直水平居中 + 基本样式。

JavaScript:事件监听 + fetch API请求接口。如上述示例部分源码如下:

 
  
  1. const api = 'https://icanhazdadjoke.com';

  2. const on = (el,type,handler,useCapture = false) => {

  3.     if(el && type && handler){

  4.         el.addEventListener(type,handler,useCapture);

  5.     }

  6. }

  7. on(getJokeBtn,'click',request);

  8. request();

  9. async function request(){

  10.     const res = await fetch(api,headerConfig);

  11.     const data = await res.json();

  12.     content.innerHTML = data.joke;

  13. }

  14. 复制代码

11. Event Keycodes

效果如图所示:

11.gif

  • 源码[22]

  • 在线示例[23]

  • [ ] 知识点总结:

CSS:CSS渐变 + 弹性盒子垂直水平居中 + 基本样式。

JavaScript:键盘事件监听 + 事件对象的属性。如上述示例部分源码如下:

 
  
  1. const container = document.querySelector('#container');

  2. window.addEventListener("keydown",event => {

  3.     createKeyCodeTemplate(event);

  4. });

  5. function createKeyCodeTemplate(e){

  6.     const { key,keyCode,code } = e;

  7.     let template = "";

  8.     [

  9.         {

  10.             title:"event.key",

  11.             content:key === " " ? "Space" : key

  12.         },

  13.         {

  14.             title:"event.keyCode",

  15.             content:keyCode

  16.         },

  17.         {

  18.             title:"event.code",

  19.             content:code

  20.         }

  21.     ].forEach(value => {

  22.         template += `${ value.title }${ value.content }

`;

  •     });

  •     container.innerHTML = template;

  • }

  • 复制代码

  • 12. Faq Collapse

    效果如图所示:

    12.gif

    • 源码[24]

    • 在线示例[25]

    • [ ] 知识点总结:

    CSS:font-awesome字体库的使用 + 伪元素选择器 + 定位 + CSS渐变 + 基本样式。

    JavaScript:动态创建元素 + 类名的切换 + 事件代理。如上述示例部分源码如下:

     
      
    1. const faqs = document.querySelectorAll('.faq-container > .faq');

    2. container.addEventListener('click',e => {

    3.    if(e.target.className.indexOf('faq-icon') > -1){

    4.       faqs[[].indexOf.call(faqs,e.target.parentElement)].classList.toggle('active');

    5.    }

    6. });

    7. 复制代码

    13. Random Choice Picker

    效果如图所示:

    13.gif

    • 源码[26]

    • 在线示例[27]

    • [ ] 知识点总结:

    CSS:基本样式。

    JavaScript:动态创建元素 + 类名的切换 + 延迟定时器的用法 + 随机数 + 键盘事件的监听。如上述示例部分源码如下:

     
      
    1. function createTags(value,splitSymbol){

    2.     if(!value || !value.length)return;

    3.     const words = value.split(splitSymbol).map(v => v.trim()).filter(v => v);

    4.     tags.innerHTML = '';

    5.     words.forEach(word => {

    6.         const tag = document.createElement('span');

    7.         tag.classList.add('tag');

    8.         tag.innerText = word;

    9.         tags.appendChild(tag);

    10.     })

    11. }

    12. function randomTag(){

    13.     const time = 50;

    14.     let timer = null;

    15.     let randomHighLight = () => {

    16.         const randomTagElement = pickerRandomTag();

    17.         highLightTag(randomTagElement);

    18.         timer = setTimeout(randomHighLight,100);

    19.         setTimeout(() => {

    20.             unHighLightTag(randomTagElement);

    21.         },100);

    22.     }

    23.     randomHighLight();

    24.     setTimeout(() => {

    25.         clearTimeout(timer);

    26.         setTimeout(() => {

    27.             const randomTagElement = pickerRandomTag();

    28.             highLightTag(randomTagElement);

    29.         },100);

    30.     },time * 100);

    31. }

    32. function pickerRandomTag(){

    33.     const tagElements = document.querySelectorAll('#tags .tag');

    34.     return tagElements[Math.floor(Math.random() * tagElements.length)];

    35. }

    36. 复制代码

    14. Animated Navigation

    效果如图所示:

    14.gif

    • 源码[28]

    • 在线示例[29]

    • [ ] 知识点总结:

    CSS:基本样式 + 定位 + 位移变换以及角度旋转。

    JavaScript:类名的切换。如上述示例部分源码如下:

     
      
    1. toggle.addEventListener('click',() => nav.classList.toggle('active'));

    2. 复制代码

    15. Incrementing Counter

    效果如图所示:

    15.gif

    • 源码[30]

    • 在线示例[31]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + font-awesome字体库的使用。

    JavaScript:动态创建元素 + 定时器实现增量相加。如上述示例部分源码如下:

     
      
    1. function updateCounterHandler() {

    2.     const counters_elements = document.querySelectorAll('.counter');

    3.     counters_elements.forEach(element => {

    4.         element.textContent = '0';

    5.         const updateCounter = () => {

    6.             const value = +element.getAttribute('data-count');

    7.             const textContent = +element.textContent;

    8.             const increment = value / 100;

    9.             if (textContent < value) {

    10.                 element.textContent = `${Math.ceil(increment + textContent)}`;

    11.                 setTimeout(updateCounter, 10);

    12.             } else {

    13.                 element.textContent = value;

    14.             }

    15.         }

    16.         updateCounter();

    17.     });

    18. }

    19. 复制代码

    16. Drink Water

    效果如图所示:

    16.gif

    • 源码[32]

    • 在线示例[33]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + CSS过渡特效。

    JavaScript:正则表达式 + 循环 + 样式与内容的设置。如上述示例部分源码如下:

     
      
    1. if (actives.length === l) {

    2.                 setHeightVisible('0', 'hidden', '350px', 'visible');

    3.                 setTextContent("100%", "0L");

    4.             } else if (actives.length === 0) {

    5.                 setHeightVisible('350px', 'visible', '0', 'hidden');

    6.                 setTextContent("12.5%", "2L");

    7.             } else {

    8.                 const h1 = unitHei * (l - actives.length) + 'px';

    9.                 const h2 = unitHei * actives.length + 'px';

    10.                 setHeightVisible(h1, 'visible', h2, 'visible');

    11.                 const t1 = (unitHei * actives.length / 350) * 100 + "%";

    12.                 const t2 = (cups[i].textContent.replace(/ml/, "").replace(/\s+/, "") - 0) * (l - actives.length) / 1000 + 'L';

    13.                 setTextContent(t1, t2);

    14. }

    15. 复制代码

    17. movie-app

    效果如图所示:

    17.gif

    • 源码[34]

    • 在线示例[35]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + CSS过渡特效 + 清除浮动。

    JavaScript:接口请求 + 键盘事件的监听。如上述示例部分源码如下:

     
      
    1. search.addEventListener('keydown',e => {

    2.         if(e.keyCode === 13){

    3.             let value = e.target.value.replace(/\s+/,"");

    4.             if(value){

    5.                 getMovies(SEARCH_API + value);

    6.                 setTimeout(() => {

    7.                     e.target.value = "";

    8.                 },1000);

    9.             }else{

    10.                 window.location.reload(true);

    11.             }

    12.         }

    13.     })

    14. 复制代码

    PS:这个示例效果由于接口访问受限,需要xx访问。

    18. background-slider

    效果如图所示:

    18.gif

    • 源码[36]

    • 在线示例[37]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + 阴影效果 + 定位 + 伪元素选择器。

    JavaScript:背景设置与类名的操作。如上述示例部分源码如下:

     
      
    1. let currentActive = 0;

    2. function setBackgroundImage(){

    3.     const url = slideItems[currentActive].style.backgroundImage;

    4.     background.style.backgroundImage = url;

    5. }

    6. function setSlideItem(){

    7.     const currentSlide = slideItems[currentActive];

    8.     const siblings = [].filter.call(slideItems,slide => slide !== currentSlide);

    9.     currentSlide.classList.add('active');

    10.     siblings.forEach(slide => slide.classList.remove('active'));

    11. }

    12. 复制代码

    19. theme-clock

    效果如图所示:

    19.gif

    • 源码[38]

    • 在线示例[39]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS变量 + 阴影效果 + 定位。

    JavaScript:中英文的切换以及主题模式的切换,还有日期对象的处理。如上述示例部分源码如下:

     
      
    1. function setCurrentDate(){

    2.     const date = new Date();

    3.     const month = date.getMonth();

    4.     const day = date.getDay();

    5.     const time = date.getDate();

    6.     const hour = date.getHours();

    7.     const hourForClock = hour % 12;

    8.     const minute = date.getMinutes();

    9.     const second = date.getSeconds();

    10.     const amPm = hour >= 12 ? langText[currentLang]['time-after-text'] : langText[currentLang]['time-before-text'];

    11.     const w = currentLang === 'zh' ? dayZHs : days;

    12.     const m = currentLang === 'zh' ? monthZHs : months;

    13.     const values = [

    14.         `translate(-50%,-100%) rotate(${ scale(hourForClock,0,11,0,360) }deg)`,

    15.         `translate(-50%,-100%) rotate(${ scale(minute,0,59,0,360) }deg)`,

    16.         `translate(-50%,-100%) rotate(${ scale(second,0,59,0,360) }deg)`

    17.     ];

    18.     [hourEl,minuteEl,secondEl].forEach((item,index) => setTransForm(item,values[index]));

    19.     timeEl.innerHTML = `${ hour }:${ minute >= 10 ? minute : '0' + minute } ${ amPm }`;

    20.     dateEl.innerHTML = `${w[day]},${ m[month]}${ time }${ langText[currentLang]['date-day-text'] }`;

    21.     timer = setTimeout(setCurrentDate,1000);

    22. }

    23. 复制代码

    PS:本示例也用到了与示例5一样的工具函数scale函数

    20. button-ripple-effect

    效果如图所示:

    20.gif

    • 源码[40]

    • 在线示例[41]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + CSS动画。

    JavaScript:坐标的计算 + 偏移 + 定时器。如上述示例部分源码如下:

     
      
    1. const x = e.clientX;

    2. const y = e.clientY;

    3. const left = this.offsetLeft;

    4. const top = this.offsetTop;

    5. const circleX = x - left;

    6. const circleY = y - top;

    7. const span = document.createElement('span');

    8. span.classList.add('circle');

    9. span.style.left = circleX + 'px';

    10. span.style.top = circleY + 'px';

    11. this.appendChild(span);

    12. setTimeout(() => span.remove(),1000);

    13. 复制代码

    21. drawing-app

    效果如图所示:

    21.gif

    • 源码[42]

    • 在线示例[43]

    • [ ] 知识点总结:

    CSS:基本样式。

    JavaScript:canvas API + mouse事件以及计算xy坐标 + ewColorPicker的用法。如上述示例部分源码如下:

     
      
    1. function mouseDownHandler(e){

    2.     isPressed = true;

    3.     x = e.offsetX;

    4.     y = e.offsetY;

    5. }

    6. function throttle(fn,wait = 100){

    7.     let done = false;

    8.     return (...args) => {

    9.         if(!done){

    10.             fn.call(this,args);

    11.             done = true;

    12.         }

    13.         setTimeout(() => {

    14.             done = false;

    15.         },wait);

    16.     }

    17. }

    18. 复制代码

    22. drag-n-drop

    效果如图所示:

    22.png

    • 源码[44]

    • 在线示例[45]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + CSS弹性盒子布局。

    JavaScript:drag event API + 随机生成图片。如上述示例部分源码如下:

     
      
    1. function onDragStart(){

    2.     this.classList.add('drag-move');

    3.     setTimeout(() => this.className = "invisible",200);

    4. }

    5. function onDragEnd(){

    6.     this.classList.add("drag-fill");

    7. }

    8. function onDragOver(e){

    9.     e.preventDefault();

    10. }

    11. function onDragEnter(e){

    12.     e.preventDefault();

    13.     this.classList.add('drag-active');

    14. }

    15. function onDragLeave(){

    16.     this.className = "drag-item";

    17. }

    18. function onDrop(){

    19.     this.className = "drag-item";

    20.     this.appendChild(dragFill);

    21. }

    22. 复制代码

    23. content-placholder

    效果如图所示:

    23.gif

    • 源码[46]

    • 在线示例[47]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + CSS卡片样式。

    JavaScript:骨架屏加载效果。如上述示例部分源码如下:

     
      
    1. animated_bgs.forEach(bg => bg.classList.remove("animated-bg"));

    2. animated_bgs_texts.forEach(text => text.classList.remove("animated-bg-text"));

    3. 复制代码

    24. sticky-navbar

    效果如图所示:

    24.gif

    • 源码[48]

    • 在线示例[49]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + 固定定位导航。

    JavaScript:滚动事件。如上述示例部分源码如下:

     
      
    1. window.addEventListener("scroll",e => {

    2.     if(window.scrollY > nav.offsetHeight + 100) {

    3.         nav.classList.add("active");

    4.     }else{

    5.         nav.classList.remove("active");

    6.     }

    7. })

    8. 复制代码

    PS:这里也做了移动端的布局。

    25. double-slider

    效果如图所示:

    25.gif

    • 源码[50]

    • 在线示例[51]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变 + 位移变换。

    JavaScript:轮播图的实现思路,主要还是利用transformY移动端使用transformX。如上述示例部分源码如下:

     
      
    1. function setTransform(){

    2.     let translate = isHorizontal() ? "translateX" : "translateY";

    3.     leftSlide.style.transform = `${ translate }(${position * currentIndex}px)`;

    4.     rightSlide.style.transform = `${ translate }(${-(position * currentIndex)}px)`;

    5. }

    6. 复制代码

    26. toast-notification

    效果如图所示:

    26.gif

    • 源码[52]

    • 在线示例[53]

    • [ ] 知识点总结:

    CSS:基本样式 + 消息提示框的基本样式。

    JavaScript:封装一个随机创建消息提示框。如上述示例部分源码如下:

     
      
    1. function createNotification({message = null,type = null,auto = false,autoTime = 1000,left = 0,top = 0}){

    2.     const toastItem = createEle("div");

    3.     let closeItem = null;

    4.     if(!auto){

    5.         closeItem = createEle("span");

    6.         closeItem.innerHTML = "×";

    7.         closeIte.className = "toast-close-btn";

    8.     }

    9.     toastItem.className = `toast toast-${type}`;

    10.     toastItem.textContent = message;

    11.     if(closeItem)toastItem.appendChild(closeItem);

    12.     container.appendChild(toastItem);

    13.     const leftValue = (left - toastItem.clientWidth) <= 0 ? 0 : left - toastItem.clientWidth - 30;

    14.     const topValue = (top - toastItem.clientHeight) <= 0 ? 0 : top - toastItem.clientHeight - 30;

    15.     toastItem.style.left = leftValue + 'px';

    16.     toastItem.style.top = topValue + 'px';

    17.     if(auto){

    18.         setTimeout(() => {

    19.             toastItem.remove();

    20.         },autoTime);

    21.     }else{

    22.         closeItem.addEventListener("click",() => {

    23.             toastItem.remove();

    24.         });

    25.     }

    26.     

    27. }

    28. 复制代码

    消息提示框实现思路可以参考这篇文章[54]。

    27. github-profiles

    效果如图所示:

    27.gif

    • 源码[55]

    • 在线示例[56]

    • [ ] 知识点总结:

    CSS:基本样式。

    JavaScript:try-catch处理异常语法 + axios API请求github API + async-await语法。如上述示例部分源码如下:

     
      
    1. async function getRepoList(username){

    2.     try {

    3.         const { data } = await axios(githubAPI + username + '/repos?sort=created');

    4.         addRepoList(data);

    5.     } catch (error) {

    6.         if(error.response.status == 404){

    7.             createErrorCard("查找仓库出错!");

    8.         }

    9.     }

    10. }

    11. 复制代码

    28. double-click-heart

    效果如图所示:

    28.gif

    • 源码[57]

    • 在线示例[58]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS画爱心。

    JavaScript:事件次数的计算。如上述示例部分源码如下:

     
      
    1. function clickHandler(e){

    2.     if(clickTime === 0){

    3.         clickTime = Date.now();

    4.     }else{

    5.         if(Date.now() - clickTime < 400){

    6.             createHeart(e);

    7.             clickTime = 0;

    8.         }else{

    9.             clickTime = Date.now();

    10.         }

    11.     }

    12. }

    13. 复制代码

    29. auto-text-effect

    效果如图所示:

    29.gif

    • 源码[59]

    • 在线示例[60]

    • [ ] 知识点总结:

    CSS:基本样式。

    JavaScript:定时器 + 定时器时间的计算。如上述示例部分源码如下:

     
      
    1. let time = 300 / speed.value;

    2. writeText();

    3. function writeText(){

    4.     text.innerHTML = string.slice(0,idx);

    5.     idx++;

    6.     if(idx > string.length){

    7.         idx = 1;

    8.     }

    9.     setTimeout(writeText,time);

    10. }

    11. speed.addEventListener("input",e => time = 300 / e.target.value);

    12. 复制代码

    30. password generator

    效果如图所示:

    30.gif

    • 源码[61]

    • 在线示例[62]

    • [ ] 知识点总结:

    CSS:基本样式布局。

    JavaScript:中英文切换 + 选择框事件监听 + 随机数 + copy API。如上述示例部分源码如下:

     
      
    1. function getRandomLower(){

    2.     // a ~ z 的code为 97 ~ 122

    3.     // 可根据charCodeAt()方法获取

    4.     return String.fromCharCode(Math.floor(Math.random() * 26) + 97);

    5. }

    6. function getRandomUpper(){

    7.     // A ~ Z 的code为 65 ~ 90

    8.     // 可根据charCodeAt()方法获取

    9.     return String.fromCharCode(Math.floor(Math.random() * 26) + 65);

    10. }

    11. function getRandomNumber(){

    12.     // 0 ~ 9的code为48 ~ 57

    13.     // 可根据charCodeAt()方法获取

    14.     return String.fromCharCode(Math.floor(Math.random() * 10) + 48);

    15. }

    16. 复制代码

    31. good-cheap-fast

    效果如图所示:

    31.gif

    • 源码[63]

    • 在线示例[64]

    • [ ] 知识点总结:

    CSS:CSS实现开关小组件样式 + 基本布局样式。

    JavaScript:inputchange事件的监听。如上述示例部分源码如下:

     
      
    1. const checkBoxElements = document.querySelectorAll(".switch-container input[type='checkbox']");

    2. checkBoxElements.forEach(item => item.addEventListener("change",e => {

    3.     const index = Array.from(checkBoxElements).indexOf(e.target);

    4.     if(Array.from(checkBoxElements).every(v => v.checked)){

    5.         if(index === 0){

    6.             checkBoxElements[2].checked = false;

    7.         }else if(index === 1){

    8.             checkBoxElements[0].checked = false;

    9.         }else{

    10.             checkBoxElements[1].checked = false;

    11.         }

    12.     }

    13. }));

    14. 复制代码

    32. notes-app

    效果如图所示:

    32.gif

    • 源码[65]

    • 在线示例[66]

    • [ ] 知识点总结:

    CSS:基本样式 + 卡片布局。

    JavaScript:marked.js的使用 + localStorage API存储数据 + 鼠标光标位置的计算。如上述示例部分源码如下:

     
      
    1.  on($(".edit", note), "click", e => {

    2.       const isFocus = textarea.getAttribute("data-focus");

    3.       if (isFocus === "false") {

    4.             textarea.setAttribute("data-focus","true");

    5.             if(textarea.classList.contains("hidden")){

    6.                 textarea.classList.remove("hidden");

    7.             }

    8.             if(!focusStatus){

    9.                 textarea.value = notes[index].text;

    10.             }

    11.             const text = textarea.value.trim();

    12.             // console.log(text);

    13.             if (textarea.setSelectionRange) {

    14.                 textarea.focus();

    15.                 textarea.setSelectionRange(text.length, text.length);

    16.             }else if (textarea.createTextRange) {

    17.                 const range = textarea.createTextRange();

    18.                 range.collapse(true);

    19.                 range.moveEnd('character', text.length);

    20.                 range.moveStart('character', text.length);

    21.                 range.select();

    22.             }

    23.      } else {

    24.         textarea.setAttribute("data-focus","false");

    25.         notes[index].text = textarea.value;

    26.         main.innerHTML = marked(notes[index].text);

    27.         setData("notes", notes);

    28.     }

    29. });

    30. 复制代码

    33. animated-countdown

    效果如图所示:

    33.gif

    • 源码[67]

    • 在线示例[68]

    • [ ] 知识点总结:

    CSS:基本样式 + 位移、旋转、缩放动画。

    JavaScript:动画事件 + 动画的创建与重置。如上述示例部分源码如下:

     
      
    1. function runAnimation(){

    2.     const numArr = $$("span",numGroup);

    3.     const nextToLast = numArr.length - 1;

    4.     numArr[0].classList.add("in");

    5.     numArr.forEach((num,index) => {

    6.         num.addEventListener("animationend",e => {

    7.             const {animationName} = e;

    8.             if(animationName === "goIn" && index !== nextToLast){

    9.                 num.classList.remove("in");

    10.                 num.classList.add("out");

    11.             }else if(animationName === "goOut" && num.nextElementSibling){

    12.                 num.nextElementSibling.classList.add("in");

    13.             }else{

    14.                 counter.classList.add("hide");

    15.                 final.classList.add("show");

    16.             }

    17.         })

    18.     })

    19. }

    20. function resetAnimation(){

    21.     counter.classList.remove("hide");

    22.     final.classList.remove("show");

    23.     const numArr = $$("span",numGroup);

    24.     if(numArr){

    25.         numArr.forEach(num => num.classList.value = '');

    26.         numArr[0].classList.add("in");

    27.     }

    28. }

    29. 复制代码

    34. image-carousel

    效果如图所示:

    34.png

    • 源码[69]

    • 在线示例[70]

    • [ ] 知识点总结:

    CSS:基本样式布局。

    JavaScript:定时器实现轮播。如上述示例部分源码如下:

     
      
    1. function changeCarouselItem(){

    2.     if(currentIndex > carouselItems.length - 1){

    3.         currentIndex = 0;

    4.     }else if(currentIndex < 0){

    5.         currentIndex = carouselItems.length - 1;

    6.     }

    7.         carousel.style.transform = `translateX(-${ currentIndex * carouselContainer.offsetWidth     }px)`;

    8. }

    9. 复制代码

    PS:这里额外踩了一个定时器的坑,也就是说,比如我们使用setTimeout模拟实现setInterval方法在这里是会出现问题的,我在js代码里添加了注释说明。

     
      
    1. // let interval = mySetInterval(run,1000);

    2. // Why use this method can't achieve the desired effect?

    3. // Use this method as follow to replace window.setInterval,clicked the prev button more to get the stranger effect.

    4. // Maybe this method does not conform to the specification,So make sure to use window.setInterval.

    5. // function mySetInterval(handler,time = 1000){

    6. //     let timer = null;

    7. //     const interval = () => {

    8. //         handler();

    9. //         timer = setTimeout(interval,time);

    10. //     }

    11. //     interval();

    12. //     return {

    13. //         clearMyInterval(){

    14. //             clearTimeout(timer);

    15. //         }

    16. //     }

    17. // }

    18. 复制代码

    这是因为我们用setTimeout实现的定时器并不符合规范,setInterval默认会有10ms的延迟执行。参考规范[71]。

    35. hover board

    效果如图所示:

    35.gif

    • 源码[72]

    • 在线示例[73]

    • [ ] 知识点总结:

    CSS:基本样式 + CSS渐变。

    JavaScript:动态创建元素 + 悬浮事件。如上述示例部分源码如下:

     
      
    1. function setColor(element){

    2.     element.style.background = `linear-gradient(135deg, ${ randomColor() } 10%, ${ randomColor() } 100%)`;

    3.     element.style.boxShadow = `0 0 2px ${ randomColor() },0 0 10px ${ randomColor() }`;

    4. }

    5. function removeColor(element){

    6.     element.style.background = `linear-gradient(135deg, #1d064e 10%, #10031a 100%)`;

    7.     element.style.boxShadow = `0 0 2px #736a85`;

    8. }

    9. 复制代码

    36. pokedex

    效果如图所示:

    36.gif

    • 源码[74]

    • 在线示例[75]

    • [ ] 知识点总结:

    CSS:基本样式布局 + CSS渐变。

    JavaScript:fetch API接口请求 + 创建卡片。如上述示例部分源码如下:

     
      
    1. function createPokemon(pokemon){

    2.     const pokemonItem = document.createElement("div");

    3.     pokemonItem.classList.add("pokedex");

    4.     const name = pokemon.name[0].toUpperCase() + pokemon.name.slice(1).toLowerCase();

    5.     const id = pokemon.id.toString().padStart(3,"0");

    6.     const poke_types = pokemon.types.map(type => type.type.name);

    7.     const type = main_types.find(type => poke_types.indexOf(type) > -1);

    8.     const color = colors[type];

    9.     pokemonItem.style.background = `linear-gradient(135deg, ${ color } 10%, ${ randomColor() } 100%)`;

    10.     pokemonItem.innerHTML = `

    11.     

    12.         

    13.     

  •     

  •         #${ id }

  •         ${ name }

  •         Type:${ type }

  •     

  • `;

  •     container.appendChild(pokemonItem);

  • }

  • 复制代码

  • 特别说明:接口似乎不太稳定,也许是我网络原因,图片没有加载出来。

    37. mobile-tab-navigation

    效果如图所示:

    37.gif

    • 源码[76]

    • 在线示例[77]

    • [ ] 知识点总结:

    CSS:基本样式布局 + CSS渐变实现手机布局。2. JavaScript:感觉就是移动端实现一个轮播图切换,利用opacity的设置,没什么好说的。如上述示例部分源码如下:

     
      
    1. function hideAllElement(nodeList){

    2.     nodeList.forEach(item => item.classList.remove("active"));

    3. }

    4. navItems.forEach((item,index) => {

    5.     item.addEventListener("click",() => {

    6.         hideAllElement(navItems);

    7.         hideAllElement(carouselItems);

    8.         item.classList.add("active");

    9.         carouselItems[index].classList.add("active");

    10.     })

    11. })

    12. 复制代码

    38. password-strength-background

    效果如图所示:

    38.gif

    • 源码[78]

    • 在线示例[79]

    • [ ] 知识点总结:

    CSS:其实主要是使用tailwind.css这个原子化CSS框架。

    JavaScript:监听输入框事件,然后改变背景模糊度。如上述示例部分源码如下:

     
      
    1. password.addEventListener("input",e => {

    2.     const { value } = e.target;

    3.     const blur = 20 - value.length * 2;

    4.     background.style.filter = `blur(${ blur }px)`;

    5. });

    6. 复制代码

    39. 3D-background-boxes

    效果如图所示:

    39.gif

    • 源码[80]

    • 在线示例[81]

    • [ ] 知识点总结:

    CSS:vw、vh布局 + skew倾斜变换。

    JavaScript:循环 + 背景图定位的设置。如上述示例部分源码如下:

     
      
    1. function createBox(){

    2.     for(let i = 0;i < 4;i++){

    3.         for(let j = 0;j < 4;j++){

    4.             const box = document.createElement("div");

    5.             box.classList.add("box");

    6.             box.style.backgroundPosition = `${ -j * 15 }vw ${ -i * 15 }vh`;

    7.             boxContainer.appendChild(box);

    8.         }

    9.     }

    10. }

    11. 复制代码

    40. Verify Your Account

    效果如图所示:

    40.gif

    • 源码[82]

    • 在线示例[83]

    • [ ] 知识点总结:

    CSS:基本样式布局 + input的一些特别样式设置。

    JavaScript:JavaScript focus事件。如上述示例部分源码如下:

     
      
    1. .code-container .code:focus {

    2.     border-color: #2397ef;

    3. }

    4. .code::-webkit-outer-spin-button,

    5. .code::-webkit-inner-spin-button {

    6.   -webkit-appearance: none;

    7.   margin: 0;

    8. }

    9. .code:valid {

    10.     border-color: #034775;

    11.     box-shadow: 0 10px 10px -5px rgba(0, 0, 0, 0.25);

    12. }

    13. 复制代码

     
      
    1. function onFocusHandler(nodeList){

    2.     onFocus(nodeList[0]);

    3.     nodeList.forEach((node,index) => {

    4.         node.addEventListener("keydown",e => {

    5.             // console.log(e.key);

    6.             if(e.key >= 0 && e.key <= 9){

    7.                 nodeList[index].value = "";

    8.                 setTimeout(() => onFocus(nodeList[index + 1]),0);

    9.             }else{

    10.                 setTimeout(() => onFocus(nodeList[index - 1]),0);

    11.             }

    12.         })

    13.     });

    14. }

    15. function onFocus(node){

    16.     if(!node)return;

    17.     const { nodeName } = node;

    18.     return nodeName && nodeName.toLowerCase() === "input" && node.focus();

    19. }

    20. 复制代码

    41. live-user-filter

    效果如图所示:

    41.gif

    • 源码[84]

    • 在线示例[85]

    • [ ] 知识点总结:

    CSS:基本样式布局 + 滚动条样式。

    JavaScript:fetch API接口请求 + input事件过滤数据。如上述示例部分源码如下:

     
      
    1. async function requestData(){

    2.     const res = await fetch('https://randomuser.me/api?results=50');

    3.     const { results } = await res.json();

    4.     result.innerHTML = "";

    5.     results.forEach(user => {

    6.         const listItem = document.createElement("li");

    7.         filterData.push(listItem);

    8.         const { picture:{ large },name:{ first,last },location:{ city,country } } = user;

    9.         listItem.innerHTML = `

    10.             

    11.             

    12.                 

      ${ first }  ${ last }

    13.                 

      ${ city },${ country }

    14.             

  •         `;

  •         result.appendChild(listItem);

  •     })

  • }

  • 复制代码

  • 42. feedback-ui-design

    效果如图所示:

    42.gif

    • 源码[86]

    • 在线示例[87]

    • [ ] 知识点总结:

    CSS:CSS画爱心 + 基本样式布局。

    JavaScript:选项卡切换功能的实现。如上述示例部分源码如下:

     
      
    1. ratingItem.forEach(item => {

    2.     item.addEventListener("click",e => {

    3.         siblings(item).forEach(sib => sib.classList.remove("active"));

    4.         item.classList.add("active");

    5.         selectRating = item.innerText;

    6.     })

    7. });

    8. send.addEventListener("click",() => {

    9.     selectRatingItem.innerText = selectRating;

    10.     sendPage.classList.add("hide");

    11.     receivePage.classList.remove("hide");

    12. });

    13. back.addEventListener("click",() => {

    14.     selectRating = $(".rating.active").innerText;

    15.     selectRatingItem.innerText = $(".rating.active").innerText;

    16.     sendPage.classList.remove("hide");

    17.     receivePage.classList.add("hide");

    18. });

    19. 复制代码

    43. custom-range-slider

    效果如图所示:

    43.gif

    • 源码[88]

    • 在线示例[89]

    • [ ] 知识点总结:

    CSS:input元素的样式设置(兼容写法) + 基本样式布局。

    JavaScript:input range元素的input事件监听。如上述示例部分源码如下:

     
      
    1. input[type="range"]::-webkit-slider-runnable-track {

    2.     background-image: linear-gradient(135deg, #E2B0FF 10%, #9F44D3 100%);

    3.     width: 100%;

    4.     height: 12px;

    5.     cursor: pointer;

    6.     border-radius: 4px;

    7. }

    8. input[type="range"]::-webkit-slider-thumb {

    9.     -webkit-appearance: none;

    10.     width: 25px;

    11.     height: 25px;

    12.     border-radius: 50%;

    13.     background-image: linear-gradient(135deg, #d9e2e6 10%, #e4e1e4 100%);

    14.     border: 1px solid #b233e4;

    15.     cursor: pointer;

    16.     margin-top: -6px;

    17. }

    18. 复制代码

     
      
    1. range.addEventListener("input",e => {

    2.     // string to the number

    3.     const value = +e.target.value;

    4.     const label = e.target.nextElementSibling;

    5.     const range_width = getStyle(e.target,"width");//XXpx

    6.     const label_width = getStyle(label,"width");//XXpx

    7.     // Due to contain px,slice the width

    8.     const num_width = +range_width.slice(0,range_width.length - 2);

    9.     const num_label_width = +label_width.slice(0,label_width.length - 2);

    10.     const min = +e.target.min;

    11.     const max = +e.target.max;

    12.     const left = value * (num_width / max) - num_label_width / 2 + scale(value,min,max,10,-10);

    13.     label.style.left = `${left}px`;

    14.     label.innerHTML = value;

    15. });

    16. 复制代码

    44. netflix-mobile-navigation

    效果如图所示:

    44.gif

    • 源码[90]

    • 在线示例[91]

    • [ ] 知识点总结:

    CSS:导航宽度的变化 + CSS渐变 + 基本样式布局。

    JavaScript:点击按钮切换导航栏的显隐。如上述示例部分源码如下:

     
      
    1. function changeNav(type){

    2.     navList.forEach(nav => nav.classList[type === "open" ? "add" : "remove"]("visible"));

    3. }

    4. 复制代码

    45. quiz-app

    效果如图所示:

    45.gif

    • 源码[92]

    • 在线示例[93]

    • [ ] 知识点总结:

    CSS:卡片布局 + 基本样式。

    JavaScript:表单提交 + 选择题的计算。如上述示例部分源码如下:

     
      
    1. submit.addEventListener("click",() => {

    2.     const answer = getSelected();

    3.     if(answer){

    4.         if(answer === quizData[currentQuestion].correct){

    5.             score++;

    6.         }

    7.         currentQuestion++;

    8.         if(currentQuestion > quizData.length - 1){

    9.             quizContainer.innerHTML = `

    10.                 

      You answered ${ score } / ${ quizData.length } questions correctly!

    11.                 reload

    12.             `

    13.         }else{

    14.             loadQuiz();

    15.         }

    16.     }

    17. })

    18. 复制代码

    46. testimonial-box-switcher

    效果如图所示:

    46.gif

    • 源码[94]

    • 在线示例[95]

    • [ ] 知识点总结:

    CSS:CSS动画 + 宽度的改变实现进度条 + font-awesome字体库的使用 + 基本样式布局。

    JavaScript:定时器的用法,注意定时器的执行时间与设置进度条的执行动画时间一样。如上述示例部分源码如下:

     
      
    1. .progress-bar {

    2.     width: 100%;

    3.     height: 4px;

    4.     background-color: #fff;

    5.     animation: grow 10s linear infinite;

    6.     transform-origin: left;

    7. }

    8. @keyframes grow {

    9.     0% {

    10.         transform: scaleX(0);

    11.     }

    12. }

    13. 复制代码

     
      
    1. function updateTestimonial(){

    2.     const { text,name,position,photo } = testimonials[currentIndex];

    3.     const renderElements = [testimonial,username,role];

    4.     userImage.setAttribute("src",photo);

    5.     order.innerHTML = currentIndex + 1;

    6.     [text,name,position].forEach((item,index) => renderElements[index].innerHTML = item);

    7.     currentIndex++;

    8.     if(currentIndex > testimonials.length - 1){

    9.         currentIndex = 0;

    10.     }

    11. }

    12. 复制代码

    特别说明:CSS也是可以实现进度条的。

    47. random-image-feed

    效果如图所示:

    47.gif

    • 源码[96]

    • 在线示例[97]

    • [ ] 知识点总结:

    CSS:图片布局 + 基本样式布局 + CSS提示框的实现(定位 + 伪元素) + CSS实现回到顶部效果。

    JavaScript:随机数 + (滚动事件的监听)控制回到顶部按钮的显隐。如上述示例部分源码如下:

     
      
    1. function onLoad(rows = 5) {

    2.     container.innerHTML = "";

    3.     for (let i = 0; i < rows * 3; i++) {

    4.         const imageItem = document.createElement("img");

    5.         imageItem.src = `${refreshURL}${getRandomSize()}`;

    6.         imageItem.alt = "random image-" + i;

    7.         imageItem.loading = "lazy";

    8.         container.appendChild(imageItem);

    9.     }

    10. }

    11. function getRandomSize() {

    12.     return `${getRandomValue()}x${getRandomValue()}`;

    13. }

    14. function getRandomValue() {

    15.     return Math.floor(Math.random() * 10) + 300;

    16. }

    17. window.onload = () => {

    18.     changeBtn.addEventListener("click", () => onLoad());

    19.     window.addEventListener("scroll", () => {

    20.         const { scrollTop, scrollHeight } = document.documentElement || document.body;

    21.         const { clientHeight } = flexCenter;

    22.         back.style.display = scrollTop + clientHeight > scrollHeight ? 'block' : 'none';

    23.     })

    24.     onLoad();

    25. }

    26. 复制代码

    48. todo-list

    效果如图所示:

    48.gif

    • 源码[98]

    • 在线示例[99]

    • [ ] 知识点总结:

    CSS:基本样式布局 + CSS渐变。

    JavaScript:keydowncontextmenu事件的监听 + localStorage API存储数据。如上述示例部分源码如下:

     
      
    1. function addTodo(todo){

    2.     let inputValue = input.value;

    3.     if(todo){

    4.         inputValue = todo.text;

    5.     }

    6.     if(inputValue){

    7.         const liItem = document.createElement("li");

    8.         liItem.innerText = inputValue;

    9.         if(todo && todo.complete){

    10.             liItem.classList.add("complete");

    11.         }

    12.         liItem.addEventListener("click",() => {

    13.             liItem.classList.toggle("complete");

    14.             updateList();

    15.         });

    16.         liItem.addEventListener("contextmenu",(e) => {

    17.             e.preventDefault();

    18.             liItem.remove();

    19.             updateList();

    20.         });

    21.         todoList.appendChild(liItem);

    22.         input.value = "";

    23.         updateList();

    24.     }

    25. }

    26. function updateList(){

    27.     const listItem = $$("li",todoList);

    28.     const saveTodoData = [];

    29.     listItem.forEach(item => {

    30.         saveTodoData.push({

    31.             text:item.innerText,

    32.             complete:item.classList.contains("complete")

    33.         })

    34.     });

    35.     localStorage.setItem("todoData",JSON.stringify(saveTodoData));

    36. }

    37. 复制代码

    49. insect-catch-game

    效果如图所示:

    49.gif

    • 源码[100]

    • 在线示例[101]

    • [ ] 知识点总结:

    CSS:基本样式布局。

    JavaScript:中英文切换 + 替换元素中的文本(不包含标签元素) + 定时器的用法。如上述示例部分源码如下:

     
      
    1. function replaceText(el,text,wrapSymbol = ""){

    2.     let newText = [];

    3.     if(wrapSymbol){

    4.         // why not use split method?,because it can filter the wrap symbol.

    5.         const getIndex = (txt) => txt.search(new RegExp("\\" + wrapSymbol));

    6.         let searchIndex = getIndex(text),i = 0,len = text.length;

    7.         while(searchIndex !== -1){

    8.             newText.push(text.slice(i,searchIndex) + wrapSymbol);

    9.             i = searchIndex;

    10.             if(getIndex(text.slice(searchIndex + 1)) === -1){

    11.                 newText.push(text.slice(searchIndex + 1,len));

    12.             }

    13.             searchIndex = getIndex(text.slice(searchIndex + 1));

    14.         }

    15.     }

    16.     const walk = (el,handler) => {

    17.         const children = Array.from(el.childNodes);

    18.         let wrapIndex = children.findIndex(node => node.nodeName.toLowerCase() === "br");

    19.         children.forEach((node,index) => {

    20.             if(node.nodeType === 3 && node.textContent.replace(/\s+/,"")){

    21.                 wrapSymbol ? handler(node,newText[index - wrapIndex < 0 ? 0 : index - wrapIndex]) : handler(node,text);;

    22.             }

    23.         });

    24.     }

    25.     walk(el,(node,txt) => {

    26.         const parent = node.parentNode;

    27.         parent.insertBefore(document.createTextNode(txt),node);

    28.         parent.removeChild(node);

    29.     });

    30. }

    31. 复制代码

    以上工具函数的实现参考这里来实现的[102]。

    特别说明:这个示例算是一个比较综合的示例了。

    50. kinetic-loader

    效果如图所示:

    50.gif

    • 源码[103]

    • 在线示例[104]

    • [ ] 知识点总结:

    CSS:CSS旋转动画 + 基本样式布局。

    如上述示例部分源码如下:

     
      
    1. @keyframes rotateA {

    2.     0%,25% {

    3.         transform: rotate(0deg);

    4.     }

    5.     50%,75% {

    6.         transform: rotate(180deg);

    7.     }

    8.     100% {

    9.         transform: rotate(360deg);

    10.     }

    11. }

    12. @keyframes rotateB {

    13.     0%,25% {

    14.         transform: rotate(90deg);

    15.     }

    16.     50%,75% {

    17.         transform: rotate(270deg);

    18.     }

    19.     100% {

    20.         transform: rotate(450deg);

    21.     }

    22. }

    23. 复制代码

    最后一天,额外的实现了一个404效果,算是特别结尾吧,是不是很花哨(^_^)。这算是一个CSS动画的综合使用,如下所示:

    51. 404 page

    效果如图所示:

    51.gif

    • 源码[105]

    • 在线示例[106]

    • [ ] 知识点总结:

    1. CSS:CSS动画的用法 + 基本样式布局 + svg图标元素的样式设置。

    如上述示例部分源码如下:

     
      
    1. @keyframes background {

    2.     from {

    3.         background: linear-gradient(135deg,#e0e0e0 10%,#ffffff 90%);

    4.     }

    5.     to {

    6.         background: linear-gradient(135deg,#ffffff 10%,#e0e0e0 90%);

    7.     }

    8. }

    9. @keyframes stampSlide {

    10.     0% {

    11.         transform: rotateX(90deg) rotateZ(-90deg) translateZ(-200px) translateY(130px);

    12.     }

    13.     100% {

    14.         transform: rotateX(90deg) rotateZ(-90deg) translateZ(-200px) translateY(-4000px);

    15.     }

    16. }

    17. @keyframes slide {

    18.     0% {

    19.         transform: translateX(0);

    20.     }

    21.     100% {

    22.         transform: translateX(-200px);

    23.     }

    24. }

    25. @keyframes roll {

    26.     0% {

    27.         transform: rotateZ(0deg);

    28.     }

    29.     85% {

    30.         transform: rotateZ(90deg);

    31.     }

    32.     87% {

    33.         transform: rotateZ(88deg);

    34.     }

    35.     90% {

    36.         transform: rotateZ(90deg);

    37.     }

    38.     100% {

    39.         transform: rotateZ(90deg);

    40.     }

    41. }

    42. @keyframes zeroFour {

    43.     0% {

    44.         content:"4";

    45.     }

    46.     100% {

    47.         content:"0";

    48.     }

    49. }

    50. @keyframes draw {

    51.     0% {

    52.         stroke-dasharray: 30 150;

    53.         stroke-dashoffset: 42;

    54.     }

    55.     100% {

    56.         stroke:rgba(8, 69, 131, 0.9);

    57.         stroke-dasharray: 224;

    58.         stroke-dashoffset: 0;

    59.     }

    60. }

    61. 复制代码

    来源:夕水

    https://segmentfault.com/a/1190000040481518

    示例源码地址:https://github.com/eveningwater/my-web-projects/tree/master/js

    你可能感兴趣的:(javascript,css,html)