打字效果动画的4种实现方法(超简单)


Posted in Javascript onOctober 18, 2017

方法一(纯css实现):

html代码:

<h1 class="typing typing-item">打字动画打字动画打字动画</h1>

css样式:

.typing{
 font-size: 1rem;
 padding-top: 6%;
 margin-bottom: 5%;
 font-weight: normal;
 letter-spacing: .3rem;
 -webkit-animation: type 2s steps(50, end) forwards;
 animation: type 2s steps(50, end) forwards;
}
.typing-item{
 text-align: center;
 color: black;
 width:100%;
 white-space:nowrap;
 overflow:hidden;
}
@-webkit-keyframes type{
 from { width: 0;}
}

@keyframes type{
 from { width: 0;}
}

缺点:只能实现一行式的打字效果,无法打出一段落文字

方法二(jquery):

html代码:

<div class="text-container">
 <span class="text-static"></span>
 <span class="text"></span>
 <span class="cursor">|</span>
</div>

jquery代码:

<script type="text/javascript" src="../js/jquery.js"></script>
<script>
  $(function() {
   myPrint(["hello my word!"], 100);

   function myPrint(arr, speed) {
    var index = 0;
    var str = arr[index];
    var i = 0;
    var add = true;
    var mySetInterval = setInterval(function() {
     // 延时4个字符的时间
     if (i == str.length + 4) {
      add = false;
      // 如果是最后一个字符串则终止循环函数
      if (index + 1 >= arr.length) {
       clearInterval(mySetInterval);
      }
     } else if (i == -2) {
      // 删除后延时2个字符的时间
      add = true;
      str = arr[++index];
     }
     setTimeout(function() {
      if (add) {
       i++;
       $(".text").html(str.substring(0, i));
      } else {
       $(".text").html(str.substring(0, i - 1));
       i--;
      }
     })

    }, speed)
   }

  })
 </script>

方法三(jquery-typed插件):

html代码:

<div class="content">
 <div class="content-div">
  <span id="content-item"></span>
 </div>
</div>
<input type="hidden" id="content" value="内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容" />

引入Typed.js,Typed.js内容如下

// The MIT License (MIT)

// Typed.js | Copyright (c) 2014 Matt Boldt | www.mattboldt.com

// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:

// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.

// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.




! function($) {

 "use strict";

 var Typed = function(el, options) {

  // chosen element to manipulate text
  this.el = $(el);

  // options
  this.options = $.extend({}, $.fn.typed.defaults, options);

  // attribute to type into
  this.isInput = this.el.is('input');
  this.attr = this.options.attr;

  // show cursor
  this.showCursor = this.isInput ? false : this.options.showCursor;

  // text content of element
  this.elContent = this.attr ? this.el.attr(this.attr) : this.el.text()

  // html or plain text
  this.contentType = this.options.contentType;

  // typing speed
  this.typeSpeed = this.options.typeSpeed;

  // add a delay before typing starts
  this.startDelay = this.options.startDelay;

  // backspacing speed
  this.backSpeed = this.options.backSpeed;

  // amount of time to wait before backspacing
  this.backDelay = this.options.backDelay;

  // input strings of text
  this.strings = this.options.strings;

  // character number position of current string
  this.strPos = 0;

  // current array position
  this.arrayPos = 0;

  // number to stop backspacing on.
  // default 0, can change depending on how many chars
  // you want to remove at the time
  this.stopNum = 0;

  // Looping logic
  this.loop = this.options.loop;
  this.loopCount = this.options.loopCount;
  this.curLoop = 0;

  // for stopping
  this.stop = false;

  // custom cursor
  this.cursorChar = this.options.cursorChar;

  // shuffle the strings
  this.shuffle = this.options.shuffle;
  // the order of strings
  this.sequence = [];

  // All systems go!
  this.build();
 };

 Typed.prototype = {

  constructor: Typed

  ,
  init: function() {
   // begin the loop w/ first current string (global self.string)
   // current string will be passed as an argument each time after this
   var self = this;
   self.timeout = setTimeout(function() {
    for (var i=0;i<self.strings.length;++i) self.sequence[i]=i;

    // shuffle the array if true
    if(self.shuffle) self.sequence = self.shuffleArray(self.sequence);

    // Start typing
    self.typewrite(self.strings[self.sequence[self.arrayPos]], self.strPos);
   }, self.startDelay);
  }

  ,
  build: function() {
   // Insert cursor
   if (this.showCursor === true) {
    this.cursor = $("<span class=\"typed-cursor\">" + this.cursorChar + "</span>");
    this.el.after(this.cursor);
   }
   this.init();
  }

  // pass current string state to each function, types 1 char per call
  ,
  typewrite: function(curString, curStrPos) {
   // exit when stopped
   if (this.stop === true) {
    return;
   }

   // varying values for setTimeout during typing
   // can't be global since number changes each time loop is executed
   var humanize = Math.round(Math.random() * (100 - 30)) + this.typeSpeed;
   var self = this;

   // ------------- optional ------------- //
   // backpaces a certain string faster
   // ------------------------------------ //
   // if (self.arrayPos == 1){
   // self.backDelay = 50;
   // }
   // else{ self.backDelay = 500; }

   // contain typing function in a timeout humanize'd delay
   self.timeout = setTimeout(function() {
    // check for an escape character before a pause value
    // format: \^\d+ .. eg: ^1000 .. should be able to print the ^ too using ^^
    // single ^ are removed from string
    var charPause = 0;
    var substr = curString.substr(curStrPos);
    if (substr.charAt(0) === '^') {
     var skip = 1; // skip atleast 1
     if (/^\^\d+/.test(substr)) {
      substr = /\d+/.exec(substr)[0];
      skip += substr.length;
      charPause = parseInt(substr);
     }

     // strip out the escape character and pause value so they're not printed
     curString = curString.substring(0, curStrPos) + curString.substring(curStrPos + skip);
    }

    if (self.contentType === 'html') {
     // skip over html tags while typing
     var curChar = curString.substr(curStrPos).charAt(0)
     if (curChar === '<' || curChar === '&') {
      var tag = '';
      var endTag = '';
      if (curChar === '<') {
       endTag = '>'
      } else {
       endTag = ';'
      }
      while (curString.substr(curStrPos).charAt(0) !== endTag) {
       tag += curString.substr(curStrPos).charAt(0);
       curStrPos++;
      }
      curStrPos++;
      tag += endTag;
     }
    }

    // timeout for any pause after a character
    self.timeout = setTimeout(function() {
     if (curStrPos === curString.length) {
      // fires callback function
      self.options.onStringTyped(self.arrayPos);

      // is this the final string
      if (self.arrayPos === self.strings.length - 1) {
       // animation that occurs on the last typed string
       self.options.callback();

       self.curLoop++;

       // quit if we wont loop back
       if (self.loop === false || self.curLoop === self.loopCount)
        return;
      }

      self.timeout = setTimeout(function() {
       self.backspace(curString, curStrPos);
      }, self.backDelay);
     } else {

      /* call before functions if applicable */
      if (curStrPos === 0)
       self.options.preStringTyped(self.arrayPos);

      // start typing each new char into existing string
      // curString: arg, self.el.html: original text inside element
      var nextString = curString.substr(0, curStrPos + 1);
      if (self.attr) {
       self.el.attr(self.attr, nextString);
      } else {
       if (self.isInput) {
        self.el.val(nextString);
       } else if (self.contentType === 'html') {
        self.el.html(nextString);
       } else {
        self.el.text(nextString);
       }
      }

      // add characters one by one
      curStrPos++;
      // loop the function
      self.typewrite(curString, curStrPos);
     }
     // end of character pause
    }, charPause);

    // humanized value for typing
   }, humanize);

  }

  ,
  backspace: function(curString, curStrPos) {
   // exit when stopped
   if (this.stop === true) {
    return;
   }

   // varying values for setTimeout during typing
   // can't be global since number changes each time loop is executed
   var humanize = Math.round(Math.random() * (100 - 30)) + this.backSpeed;
   var self = this;

   self.timeout = setTimeout(function() {

    // ----- this part is optional ----- //
    // check string array position
    // on the first string, only delete one word
    // the stopNum actually represents the amount of chars to
    // keep in the current string. In my case it's 14.
    // if (self.arrayPos == 1){
    // self.stopNum = 14;
    // }
    //every other time, delete the whole typed string
    // else{
    // self.stopNum = 0;
    // }

    if (self.contentType === 'html') {
     // skip over html tags while backspacing
     if (curString.substr(curStrPos).charAt(0) === '>') {
      var tag = '';
      while (curString.substr(curStrPos).charAt(0) !== '<') {
       tag -= curString.substr(curStrPos).charAt(0);
       curStrPos--;
      }
      curStrPos--;
      tag += '<';
     }
    }

    // ----- continue important stuff ----- //
    // replace text with base text + typed characters
    var nextString = curString.substr(0, curStrPos);
    if (self.attr) {
     self.el.attr(self.attr, nextString);
    } else {
     if (self.isInput) {
      self.el.val(nextString);
     } else if (self.contentType === 'html') {
      self.el.html(nextString);
     } else {
      self.el.text(nextString);
     }
    }

    // if the number (id of character in current string) is
    // less than the stop number, keep going
    if (curStrPos > self.stopNum) {
     // subtract characters one by one
     curStrPos--;
     // loop the function
     self.backspace(curString, curStrPos);
    }
    // if the stop number has been reached, increase
    // array position to next string
    else if (curStrPos <= self.stopNum) {
     self.arrayPos++;

     if (self.arrayPos === self.strings.length) {
      self.arrayPos = 0;

      // Shuffle sequence again
      if(self.shuffle) self.sequence = self.shuffleArray(self.sequence);

      self.init();
     } else
      self.typewrite(self.strings[self.sequence[self.arrayPos]], curStrPos);
    }

    // humanized value for typing
   }, humanize);

  }
  /**
   * Shuffles the numbers in the given array.
   * @param {Array} array
   * @returns {Array}
   */
  ,shuffleArray: function(array) {
   var tmp, current, top = array.length;
   if(top) while(--top) {
    current = Math.floor(Math.random() * (top + 1));
    tmp = array[current];
    array[current] = array[top];
    array[top] = tmp;
   }
   return array;
  }

  // Start & Stop currently not working

  // , stop: function() {
  //  var self = this;

  //  self.stop = true;
  //  clearInterval(self.timeout);
  // }

  // , start: function() {
  //  var self = this;
  //  if(self.stop === false)
  //  return;

  //  this.stop = false;
  //  this.init();
  // }

  // Reset and rebuild the element
  ,
  reset: function() {
   var self = this;
   clearInterval(self.timeout);
   var id = this.el.attr('id');
   this.el.after('<span id="' + id + '"/>')
   this.el.remove();
   if (typeof this.cursor !== 'undefined') {
    this.cursor.remove();
   }
   // Send the callback
   self.options.resetCallback();
  }

 };

 $.fn.typed = function(option) {
  return this.each(function() {
   var $this = $(this),
    data = $this.data('typed'),
    options = typeof option == 'object' && option;
   if (!data) $this.data('typed', (data = new Typed(this, options)));
   if (typeof option == 'string') data[option]();
  });
 };

 $.fn.typed.defaults = {
  strings: ["These are the default values...", "You know what you should do?", "Use your own!", "Have a great day!"],
  // typing speed
  typeSpeed: 0,
  // time before typing starts
  startDelay: 0,
  // backspacing speed
  backSpeed: 0,
  // shuffle the strings
  shuffle: false,
  // time before backspacing
  backDelay: 500,
  // loop
  loop: false,
  // false = infinite
  loopCount: false,
  // show cursor
  showCursor: true,
  // character for cursor
  cursorChar: "|",
  // attribute to type (null == text)
  attr: null,
  // either html or text
  contentType: 'html',
  // call when done callback function
  callback: function() {},
  // starting callback function before each string
  preStringTyped: function() {},
  //callback for every typed string
  onStringTyped: function() {},
  // callback for reset
  resetCallback: function() {}
 };


}(window.jQuery);

调用Typed.js

var string = $('#content').val();
$('#content-item').typed({
 strings: ["" + string],
 typeSpeed: 50,
 backDelay: 800,
 loop: false,
 loopCount: false
});

方法四(纯js):

html代码:

<div id="typing"></div>

js代码:

<script>
 var str = '内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容';
 var i = 0;
 function typing(){
  var divTyping = document.getElementById('typing');
  if (i <= str.length) {
   divTyping.innerHTML = str.slice(0, i++) + '_';
   setTimeout('typing()', 200);
  }
  else{
   divTyping.innerHTML = str;
  }
 }
 typing();
</script>

最后,发现实现打字效果还是蛮简单的对吧,css的思路是利用width和overflow:hidden,动画让宽度变宽实现像打字的样式,但是样式有限,不能实现多行显示。js/jquery,普遍都是先得到字的内容,然后再逐字往容器中添加文字。问题不难,主要是要善于思考!!

以上这篇打字效果动画的4种实现方法(超简单)就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
关于文本限制字数的js代码
Apr 02 Javascript
JavaScript入门教程(10) 认识其他对象
Jan 31 Javascript
JavaScript 注册事件代码
Jan 27 Javascript
固定表格行列(expression)在IE下适用
Jul 25 Javascript
js实现的GridView即表头固定表体有滚动条且可滚动
Feb 19 Javascript
使用JavaScript 编写简单计算器
Nov 24 Javascript
深入理解JavaScript系列(50):Function模式(下篇)
Mar 04 Javascript
jQuery实现在列表的首行添加数据
May 19 Javascript
javascript事件捕获机制【深入分析IE和DOM中的事件模型】
Dec 15 Javascript
JavaScript常用正则函数用法示例
Jan 23 Javascript
详解Vue学习笔记入门篇之组件的内容分发(slot)
Jul 17 Javascript
bootstrap table实现合并单元格效果
Dec 24 Javascript
Angularjs 手写日历的实现代码(不用插件)
Oct 18 #Javascript
基于JavaScript表单脚本(详解)
Oct 18 #Javascript
VUE饿了么树形控件添加增删改功能的示例代码
Oct 17 #Javascript
vue-router实现tab标签页(单页面)详解
Oct 17 #Javascript
BACKBONE.JS 简单入门范例
Oct 17 #Javascript
JS获取一个表单字段中多条数据并转化为json格式
Oct 17 #Javascript
JS解决position:sticky的兼容性问题的方法
Oct 17 #Javascript
You might like
php5数字型字符串加解密代码
2008/04/24 PHP
在Javascript中定义对象类别
2006/12/22 Javascript
javascript编程起步(第四课)
2007/02/27 Javascript
实现png图片和png背景透明(支持多浏览器)的方法
2009/09/08 Javascript
juqery 学习之三 选择器 层级 基本
2010/11/25 Javascript
javascript实现浏览器窗口传递参数的方法
2014/09/03 Javascript
AngularJS实现的省市二级联动功能示例【可对选项实现增删】
2017/10/26 Javascript
jQuery简单实现向列表动态添加新元素的方法示例
2017/12/25 jQuery
Vue实现点击后文字变色切换方法
2018/02/11 Javascript
vue2.0+vue-dplayer实现hls播放的示例
2018/03/02 Javascript
微信小程序通过保存图片分享到朋友圈功能
2018/05/24 Javascript
vue-quill-editor富文本编辑器简单使用方法
2018/09/21 Javascript
vue实现与安卓、IOS交互的方法
2018/11/02 Javascript
深入解析Vue源码实例挂载与编译流程实现思路详解
2019/05/05 Javascript
JS数据类型(基本数据类型、引用数据类型)及堆和栈的区别分析
2020/03/04 Javascript
微信小程序实现电子签名功能
2020/07/29 Javascript
解决Vue watch里调用方法的坑
2020/11/07 Javascript
Python内置函数bin() oct()等实现进制转换
2012/12/30 Python
python实现随机密码字典生成器示例
2014/04/09 Python
Python类方法__init__和__del__构造、析构过程分析
2015/03/06 Python
Python3 socket同步通信简单示例
2017/06/07 Python
用TensorFlow实现戴明回归算法的示例
2018/05/02 Python
Python实现去除列表中重复元素的方法总结【7种方法】
2019/02/16 Python
python定时复制远程文件夹中所有文件
2019/04/30 Python
python常用库之NumPy和sklearn入门
2019/07/11 Python
python写入数据到csv或xlsx文件的3种方法
2019/08/23 Python
解决Pytorch训练过程中loss不下降的问题
2020/01/02 Python
Python3+Selenium+Chrome实现自动填写WPS表单
2020/02/12 Python
Python操作Excel的学习笔记
2021/02/18 Python
CSS3制作轮播图的一种方法
2019/11/11 HTML / CSS
浅析canvas元素的html尺寸和css尺寸对元素视觉的影响
2019/07/22 HTML / CSS
Antonioli美国在线商店:时尚前卫奢华
2019/07/29 全球购物
乡镇网格化管理实施方案
2014/03/23 职场文书
代领毕业证委托书
2014/08/02 职场文书
详解redis分布式锁的这些坑
2021/05/19 Redis
浅谈MySQL表空间回收的正确姿势
2021/10/05 MySQL