一個(gè)非常好用的emoji插件
如何利用該插件迅速搭建搭建emoji界面?
在主布局文件下寫(xiě)下如下代碼
<script>
var $wysiwyg = $('.emojis-wysiwyg').emojiarea({wysiwyg: true,button: '.showemoji'});
//button: '.showemoji' 則是用于自定義打開(kāi)emoji選擇界面的按鈕的樣式
//emojis-wysiwyg則是textarea對(duì)應(yīng)的class,該操作用于創(chuàng)建一個(gè)div與我們的textarea綁定
</script>
分析源碼
jquery-emojiarea.js
數(shù)據(jù)存儲(chǔ)與emojiarea構(gòu)造方法
//$.fx是類級(jí)別的插件開(kāi)發(fā),即給jQuery添加新的全局函數(shù)
$.emojiarea = {
path: '',//path代表儲(chǔ)存emoji相關(guān)信息的json文件
icons: {},//icons儲(chǔ)存著詳細(xì)的emoji名稱(轉(zhuǎn)義后),以及圖片的名字
defaults: {
button: null,
buttonLabel: 'Emojis',
buttonPosition: 'after'
}
};
$.fn.emojiarea = function(options) {
//extend方法用于合并參數(shù)到{},后面覆蓋前面(例如options覆蓋 $.emojiarea.defaults部分內(nèi)容)
options = $.extend({}, $.emojiarea.defaults, options);
return this.each(function() {
var $textarea = $(this);
if ('contentEditable' in document.body && options.wysiwyg !== false) { //表示可編輯屬性是否在document.body里
new EmojiArea_WYSIWYG($textarea, options);//將$textarea屬性傳入EmojiArea_WYSIWYG函數(shù),構(gòu)造一個(gè)emoji輸入框?qū)ο? } else {
new EmojiArea_Plain($textarea, options);
}
});
};
(函數(shù)/對(duì)象)EmojiArea_WYSIWYG
var EmojiArea_WYSIWYG = function($textarea, options) {
var self = this;
CONST = this;
this.options = options;
this.$textarea = $textarea;
this.$editor = $('<div>').addClass('emoji-wysiwyg-editor');//editor就是代替了textarea的一個(gè)聊天框,它與$textarea綁定
this.$editor.text($textarea.val());
this.$editor.attr({contenteditable: 'true'});//contenteditable: 'true'屬性的設(shè)置極為重要,它使得div變成可編輯狀態(tài),例如編輯文字,復(fù)制圖片(下一章會(huì)講)
this.$editor.on('blur keyup paste', function() { return self.onChange.apply(self, arguments); });//onChange方法用以editor和textarea之間的內(nèi)容更新
this.$editor.on('mousedown focus', function() { document.execCommand('enableObjectResizing', false, false); });
this.$editor.on('blur', function() { document.execCommand('enableObjectResizing', true, true); });
var html = this.$editor.text();
var emojis = $.emojiarea.icons;
for (var key in emojis) {
if (emojis.hasOwnProperty(key)) {
html = html.replace(new RegExp(util.escapeRegex(key), 'g'), EmojiArea.createIcon(key));
}
}//遍歷emojis,其中escapeRegex方法用于通過(guò)替換為轉(zhuǎn)義碼來(lái)轉(zhuǎn)義最小的元字符集(\、*、+、?、|、{、[、(、)、^、$、.、# 和空白)
//createIcon通過(guò)key創(chuàng)建一個(gè)<img>替換:iconname:形式的表情(在textarea中,:iconname:代表一個(gè)表情)
this.$editor.html(html);
$textarea.hide().after(this.$editor);
this.setup();
this.$button.on('mousedown', function() {
if (self.hasFocus) {
self.selection = util.saveSelection();
}
});
};
editor中對(duì)鼠標(biāo)劃取部分的操作
util.replaceSelection = (function() {
if (window.getSelection) {//如果瀏覽器支持window.getSelection就使用這個(gè)方法,否則就用document.selection
return function(content) {
// 獲取選定對(duì)象
var range, sel = window.getSelection();
var node = typeof content === 'string' ? document.createTextNode(content) : content;
if (sel.getRangeAt && sel.rangeCount) {
range = sel.getRangeAt(0);//設(shè)置光標(biāo)對(duì)象,把選中的文字轉(zhuǎn)化為range對(duì)象,可以進(jìn)行操作。接受一個(gè)參數(shù),一般填寫(xiě)為0,表示從selection對(duì)象從0開(kāi)始進(jìn)行轉(zhuǎn)化;
range.deleteContents();
range.insertNode(document.createTextNode(' '));
range.insertNode(node);
range.setStart(node, 0);//光標(biāo)位置定位在表情節(jié)點(diǎn)開(kāi)始位置,第一個(gè)參數(shù)為這個(gè)range對(duì)象的container,第2個(gè)參數(shù)為索引值,可以指定選擇某段文字從哪開(kāi)始
window.setTimeout(function() {
range = document.createRange();//selection創(chuàng)建
range.setStartAfter(node);
range.collapse(true);// 使光標(biāo)開(kāi)始和光標(biāo)結(jié)束重疊
sel.removeAllRanges();// 清除選定對(duì)象的所有光標(biāo)對(duì)象
sel.addRange(range);// 插入新的光標(biāo)對(duì)象
}, 0);
}
}
} else if (document.selection && document.selection.createRange) {
return function(content) {
var range = document.selection.createRange();
if (typeof content === 'string') {
range.text = content;
} else {
range.pasteHTML(content.outerHTML);
}
}
}
})();
util.restoreSelection = (function() {//用于加載editor中的光標(biāo)
if (window.getSelection) {
return function(savedSelection) {
var sel = window.getSelection();
sel.removeAllRanges();
for (var i = 0, len = savedSelection.length; i < len; ++i) {
sel.addRange(savedSelection[i]);
}
};
} else if (document.selection && document.selection.createRange) {
return function(savedSelection) {
if (savedSelection) {
savedSelection.select();
}
};
}
})();