arctext.js实现文字平滑弯曲弧形效果的插件

时间:2021-05-28

本文介绍了实现文字平滑弯曲弧形效果的插件-arctext.js,分享给大家,具体如下:

扇形的文字

有时候产品大佬就是很任性,说做一个宣传页,一个类似拱门的效果,每次文字不一样,但是文字得呈现拱形状,类似上图啦。

尝试自己使用canvas画和css3的rotate旋转div,两种方法都是计算旋转角度的时候很麻烦,因为可能5个字10个字,但是得均匀地呈拱形分布,要知道让每个文字都沿着弯曲路径排布相当的复杂,于是便发现了这个好用的插件---arctext.js

它能够自动计算每个文字正确的旋转角度,并且生成对应的CSS ,其实就是基于css3和jquery,使用起来也很方便。

1.创建一个容器装文字

<h3 id="title">文字弯曲效果类似扇形拱桥状</h3>

2.引入jquery和arctext.js

<script type="text/javascript" src="//code.jquery.com/jquery-1.8.2.min.js" ></script><script src="jquery.arctext.js"></script>

3.调用arctext的方法:

$(function(){ $("#title").show().arctext({ radius:180 }) })

arctext参数说明:

  • radius:弯曲度数,最小的值是文字长度,如果设置为-1,则显示直线。
  • rotate:默认true,为false则不旋转文字
  • dir:默认1 (1:向下弯曲 非1(-1,0,2等):向上弯曲 )
  • fitText:默认false,如果你想尝试使用fitText插件,设置为true,记住包装的标签需要fluid布局。

效果图完整demo:

<!DOCTYPE html><html><head lang="en"> <meta charset="UTF-8"> <title></title> <style> #title{ font-size: 20px; color: #ffe400; text-align: center; } </style></head><body> <h3 id="title">文字弯曲效果类似扇形拱桥状</h3><script type="text/javascript" src="//code.jquery.com/jquery-1.8.2.min.js" ></script><script src="jquery.arctext.js"></script><script> $(function(){ $("#title").arctext({ radius:180 }) })</script></body></html>

jquery.arctext.js

/** * Arctext.js * A jQuery plugin for curved text * http:///) set this to true. Don't forget the wrapper should be fluid. }; $.Arctext.prototype = { _init : function( options ) { this.options = $.extend( true, {}, $.Arctext.defaults, options ); // apply the lettering plugin. this._applyLettering(); this.$el.data( 'arctext', true ); // calculate values this._calc(); // apply transformation. this._rotateWord(); // load the events this._loadEvents(); }, _applyLettering : function() { this.$el.lettering(); if( this.options.fitText ) this.$el.fitText(); this.$letters = this.$el.find('span').css('display', 'inline-block'); }, _calc : function() { if( this.options.radius === -1 ) return false; // calculate word / arc sizes & distances. this._calcBase(); // get final values for each letter. this._calcLetters(); }, _calcBase : function() { // total word width (sum of letters widths) this.dtWord = 0; var _self = this; this.$letters.each( function(i) { var $letter = $(this), letterWidth = $letter.outerWidth( true ); _self.dtWord += letterWidth; // save the center point of each letter: $letter.data( 'center', _self.dtWord - letterWidth / 2 ); }); // the middle point of the word. var centerWord = this.dtWord / 2; // check radius : the minimum value allowed is half of the word length. if( this.options.radius < centerWord ) this.options.radius = centerWord; // total arc segment length, where the letters will be placed. this.dtArcBase = this.dtWord; // calculate the arc (length) that goes from the beginning of the first letter (x=0) to the end of the last letter (x=this.dtWord). // first lets calculate the angle for the triangle with base = this.dtArcBase and the other two sides = radius. var angle = 2 * Math.asin( this.dtArcBase / ( 2 * this.options.radius ) ); // given the formula: L(ength) = R(adius) x A(ngle), we calculate our arc length. this.dtArc = this.options.radius * angle; }, _calcLetters : function() { var _self = this, iteratorX = 0; this.$letters.each( function(i) { var $letter = $(this), // calculate each letter's semi arc given the percentage of each letter on the original word. dtArcLetter = ( $letter.outerWidth( true ) / _self.dtWord ) * _self.dtArc, // angle for the dtArcLetter given our radius. beta = dtArcLetter / _self.options.radius, // distance from the middle point of the semi arc's chord to the center of the circle. // this is going to be the place where the letter will be positioned. h = _self.options.radius * ( Math.cos( beta / 2 ) ), // angle formed by the x-axis and the left most point of the chord. alpha = Math.acos( ( _self.dtWord / 2 - iteratorX ) / _self.options.radius ), // angle formed by the x-axis and the right most point of the chord. theta = alpha + beta / 2, // distances of the sides of the triangle formed by h and the orthogonal to the x-axis. x = Math.cos( theta ) * h, y = Math.sin( theta ) * h, // the value for the coordinate x of the middle point of the chord. xpos = iteratorX + Math.abs( _self.dtWord / 2 - x - iteratorX ), // finally, calculate how much to translate each letter, given its center point. // also calculate the angle to rotate the letter accordingly. xval = 0| xpos - $letter.data( 'center' ), yval = 0| _self.options.radius - y, angle = ( _self.options.rotate ) ? 0| -Math.asin( x / _self.options.radius ) * ( 180 / Math.PI ) : 0; // the iteratorX will be positioned on the second point of each semi arc iteratorX = 2 * xpos - iteratorX; // save these values $letter.data({ x : xval, y : ( _self.options.dir === 1 ) ? yval : -yval, a : ( _self.options.dir === 1 ) ? angle : -angle }); }); }, _rotateWord : function( animation ) { if( !this.$el.data('arctext') ) return false; var _self = this; this.$letters.each( function(i) { var $letter = $(this), transformation = ( _self.options.radius === -1 ) ? 'none' : 'translateX(' + $letter.data('x') + 'px) translateY(' + $letter.data('y') + 'px) rotate(' + $letter.data('a') + 'deg)', transition = ( animation ) ? 'all ' + ( animation.speed || 0 ) + 'ms ' + ( animation.easing || 'linear' ) : 'none'; $letter.css({ '-webkit-transition' : transition, '-moz-transition' : transition, '-o-transition' : transition, '-ms-transition' : transition, 'transition' : transition }) .css({ '-webkit-transform' : transformation, '-moz-transform' : transformation, '-o-transform' : transformation, '-ms-transform' : transformation, 'transform' : transformation }); }); }, _loadEvents : function() { if( this.options.fitText ) { var _self = this; $(window).on( 'resize.arctext', function() { _self._calc(); // apply transformation. _self._rotateWord(); }); } }, set : function( opts ) { if( !opts.radius && !opts.dir && opts.rotate === 'undefined' ) { return false; } this.options.radius = opts.radius || this.options.radius; this.options.dir = opts.dir || this.options.dir; if( opts.rotate !== undefined ) { this.options.rotate = opts.rotate; } this._calc(); this._rotateWord( opts.animation ); }, destroy : function() { this.options.radius = -1; this._rotateWord(); this.$letters.removeData('x y a center'); this.$el.removeData('arctext'); $(window).off('.arctext'); } }; var logError = function( message ) { if ( this.console ) { console.error( message ); } }; $.fn.arctext = function( options ) { if ( typeof options === 'string' ) { var args = Array.prototype.slice.call( arguments, 1 ); this.each(function() { var instance = $.data( this, 'arctext' ); if ( !instance ) { logError( "cannot call methods on arctext prior to initialization; " + "attempted to call method '" + options + "'" ); return; } if ( !$.isFunction( instance[options] ) || options.charAt(0) === "_" ) { logError( "no such method '" + options + "' for arctext instance" ); return; } instance[ options ].apply( instance, args ); }); } else { this.each(function() { var instance = $.data( this, 'arctext' ); if ( !instance ) { $.data( this, 'arctext', new $.Arctext( options, this ) ); } }); } return this; }; })( jQuery );

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。

声明:本页内容来源网络,仅供用户参考;我单位不保证亦不表示资料全面及准确无误,也不保证亦不表示这些资料为最新信息,如因任何原因,本网内容或者用户因倚赖本网内容造成任何损失或损害,我单位将不会负任何法律责任。如涉及版权问题,请提交至online#300.cn邮箱联系删除。

相关文章