亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 開發(fā) > Java > 正文

javascript開發(fā)隨筆3 開發(fā)iframe富文本編輯器的一點(diǎn)體會

2024-07-21 02:53:56
字體:
供稿:網(wǎng)友
前段時(shí)間有個(gè)需求是開發(fā)富文本編輯器,這個(gè)之前隨做過,但看了需求,發(fā)現(xiàn)有些地方還需google
 
就把遇到的問題記錄一下。寫這篇文章時(shí)用的TinyMCE編輯器就很強(qiáng)大,但畢竟是第三方的,項(xiàng)目也考慮了這些,如果做些自定義的東西不太方便。 
1. 判斷光標(biāo)位置的元素(或者選中的部分)的樣式。光標(biāo)位置改變的時(shí)候更新工具欄對應(yīng)按鈕的樣式。什么情況下光標(biāo)的位置會改變呢?是鍵盤方向鍵和鼠標(biāo)點(diǎn)擊,于是就判斷鍵盤事件和鼠標(biāo)事件來執(zhí)行光標(biāo)移動的處理。 
a. 獲得光標(biāo)位置或選中元素:首先getSelection,創(chuàng)建range。然后獲得元素,獲取到元素之后就可以或得樣式、tagName等等,做更多的操作,運(yùn)行代碼: 
復(fù)制代碼代碼如下:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> 
<html> 
<head> 
<title></title> 
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 
<style type="text/css"> 
p{width:600px;text-align: left;text-indent:2em;line-height:20px;font-size:12px} 
textarea{width:600px;height:100px;font-size:12px;overflow:auto} 
</style> 
</head> 
<body> 
<span style="display:block;height:150px; font-size:12px;line-height:150%">信息</span> 
<script type="text/javascript"> 
function createEditor(){ 
var iframe = document.createElement('iframe'); 
iframe.id = 'iframe'; 
iframe.frameBorder = 1; 
iframe.width = 400; 
iframe.height = 200; 
document.body.appendChild(iframe); 
return iframe; 

var bind = function(element,eventType,fn,useCapture){ 
useCapture = useCapture || false; 
if(arguments.length < 3){ 
return true 
}; 
if(window.addEventListener){ 
element.addEventListener(eventType, fn, useCapture); 
}else{ 
element.attachEvent('on'+eventType,fn, useCapture); 


//from 司徒正美 
var css = document.defaultView ? function(el,style){ 
return document.defaultView.getComputedStyle(el, null).getPropertyValue(style) 
} : function(el,style){ 
style = style.replace(//-(/w)/g, function($, $1){ 
return $1.toUpperCase(); 
}); 
return el.currentStyle[style]; 

function bindEditor(){ 
var iframe = createEditor(); 
var ifr_win = iframe.contentWindow; 
var ifr_doc = ifr_win.document; 

var editorContent = '<span style="font-family: 黑體; font-weight: bold;">阿四大四大四</span>大<span style="font-style: italic; text-decoration: underline;">四大四大打算</span>打打<span style="font-style: italic; color: #ff0000;">雙打薩斯</span>大師'; 
ifr_doc.designMode='On';//可編輯 
ifr_doc.contentEditable = true; 
ifr_doc.open(); 
ifr_doc.writeln('<html><head><style type="text/css">body{padding:10px;margin:0;font-size:13px;font-family:宋體;text-align:left;overflow:auto;word-wrap: break-word;cursor:text;background-color: transparent; }body,p,font,div,ul,li {line-height: 1.5;}p,font,div,ul,li {line-height: 1.5;margin:0;padding:0}a{color:#548DD4}</style></head><body>'+ editorContent +'</body></html>'); 
ifr_doc.close(); 

var getRange = function(){ 
var range = window.getSelection ? ifr_win.getSelection() : ifr_win.document.selection; 
if (!range) { 
return { 
node : null, 
range : null, 
text : null 
}; 

range = range.createRange ? range.createRange() : range.getRangeAt(0); 
var text = window.getSelection ? range : range.text; 
var rangeNode = null; 
if (range.commonAncestorContainer) { 
rangeNode = range.commonAncestorContainer; 
} else { 
if (range.parentElement) rangeNode = range.parentElement(); 

return { 
node : rangeNode, 
range : range, 
text : text 


var info = document.getElementsByTagName('span')[0]; 
var getStyle = function(node){ 
//console.log(node) 
var html = ''; 
html+= '<span style="font-family:'+ css(node,'font-family') +'">字體:'+ css(node,'font-family') + '</span><br />'; 
html+= '<span style="color:'+ css(node,'color') +'">顏色:'+ css(node,'color') + '</span><br />'; 
html+= '<span style="font-style:'+ css(node,'font-style') +'">斜體:'+ css(node,'font-style') + '</span><br />'; 
html+= '<span style="font-weight:'+ css(node,'font-weight') +'">粗體:'+ css(node,'font-weight') + '</span><br />'; 
html+= '<span style="text-decoration:'+ css(node,'text-decoration') +'">下劃線:'+ css(node,'text-decoration') + '</span><br />'; 
html+= 'tagName:'+ node.tagName + ',style:'+ node.getAttribute('style') +'<br />'; 

info.innerHTML = html; 

//當(dāng)光標(biāo)位置改變時(shí)候執(zhí)行 
var onselectionchange = function(event){ 
var e = event || window.event; 
if(!e.keyCode)e.keyCode = e.which; 
//方向鍵移動光標(biāo),獲取光標(biāo)位置的dom 
if((e.keyCode >= 37 && e.keyCode <= 40 )|| e.type == "click"){ 

var node = getRange().node;//獲取光標(biāo)位置元素 
if(node !== null){ 
while(node.nodeType != 1){ 
node = node.parentNode; 

getStyle(node); 




bind(ifr_doc,'click',onselectionchange,false); 
bind(ifr_doc,'keydown',onselectionchange,false); 

window.onload = function(){ 
bindEditor(); 

</script> 
</body> 
</html> 

2. ie不能保持光標(biāo)位置,這個(gè)是在添加超鏈接時(shí)候出現(xiàn)的問題,當(dāng)不使用瀏覽器內(nèi)置的輸入框,光標(biāo)移動其他的文本域里,ie會失去所選中的部分,無法對選中的部分加鏈接了,解決辦法就是:利用range的getBookmark和moveToBookmark,然后給iframe的document綁定onbeforedeactivate(getBookmark)、onactivate(moveTo),這2個(gè)事件的大致意思就是,當(dāng)被激活和失去激活狀態(tài)。增加事件之后,就不必保存lastRang或者再其他地方設(shè)置bookmark了,可以讓ie像其他瀏覽器一樣自動保持光標(biāo)位置了 
復(fù)制代碼代碼如下:

if(Util.browser.msie){ 
Util.bind(this.E.ifr_win.document, "beforedeactivate", function(){ 
var Rng = _self.getRange().range; 
_self.rangeBookMark= Rng.getBookmark(); 
}); 
Util.bind(this.E.ifr_win.document, "activate", function(){ 
var Rng = _self.getRange().range; 
Rng.moveToBookmark(_self.rangeBookMark); 
Rng.select(); 
_self.rangeBookMark = null; 
}); 

3. ie中的撤銷與重做 。 當(dāng)iframe外部有彈出窗口、或者修改html撤銷、重做功能將失效。只能歸為ie的bug了。。。。也許ie沒分清iframe和頁面的document,把他們的撤銷、重做混道義了。 
如下: 
復(fù)制代碼代碼如下:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> 
<html> 
<head> 
<title></title> 
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 
<style type="text/css"> 
p{width:600px;text-align: left;text-indent:2em;line-height:20px;font-size:12px} 
textarea{width:600px;height:100px;font-size:12px;overflow:auto} 
</style> 
</head> 
<body> 
<span style="display:block;height:150px; font-size:12px;line-height:150%">信息</span> 
<div id="J_tool"> 
<input type="button" command="Undo" value="撤銷" unselectable="on" /> 
<input type="button" command="Redo" value="重做" unselectable="on" /> 
<input type="button" command="Bold" value="粗體" unselectable="on" /> 
<input type="button" command="Italic" value="斜體" unselectable="on" /> 
</div> 
<br /> 
<input type="button" onclick="changeLayout()" value="點(diǎn)擊下,ie將無法撤銷、重做" /> 
<br /> 
<script type="text/javascript"> 
function changeLayout(){ 
var popwin = document.getElementById('popwin'); 
if(!popwin){ 
popwin = document.createElement('div'); 
popwin.id = 'popwin'; 
popwin.style.cssText = 'display:none;width:300px;height:150px;background-color:#ccc;position:absolute;left:0;top:0px;text-align:center;line-height:150px;'; 
popwin.innerHTML = '改變了layoud渲染,ie將無法撤銷、重做'; 
document.body.appendChild(popwin); 
popwin.onclick= function(){this.style.display = 'none'}; 

popwin.style.display = popwin.style.display == 'none' ? 'block' : 'none'; 

function createEditor(){ 
var iframe = document.createElement('iframe'); 
iframe.id = 'iframe'; 
iframe.frameBorder = 1; 
iframe.width = 400; 
iframe.height = 200; 
document.body.appendChild(iframe); 
return iframe; 

var bind = function(element,eventType,fn,useCapture){ 
useCapture = useCapture || false; 
if(arguments.length < 3){ 
return true 
}; 
if(window.addEventListener){ 
element.addEventListener(eventType, fn, useCapture); 
}else{ 
element.attachEvent('on'+eventType,fn, useCapture); 


//from 司徒正美 
var css = document.defaultView ? function(el,style){ 
return document.defaultView.getComputedStyle(el, null).getPropertyValue(style) 
} : function(el,style){ 
style = style.replace(//-(/w)/g, function($, $1){ 
return $1.toUpperCase(); 
}); 
return el.currentStyle[style]; 

function bindEditor(){ 
var iframe = createEditor(); 
var ifr_win = iframe.contentWindow; 
var ifr_doc = ifr_win.document; 
var editorContent = '<span style="font-family: 黑體; font-weight: bold;">阿四大四大四</span>大<span style="font-style: italic; text-decoration: underline;">四大四大打算</span>打打<span style="font-style: italic; color: #ff0000;">雙打薩斯</span>大師'; 
ifr_doc.designMode='On';//可編輯 
ifr_doc.contentEditable = true; 
ifr_doc.open(); 
ifr_doc.writeln('<html><head><style type="text/css">body{padding:10px;margin:0;font-size:13px;font-family:宋體;text-align:left;overflow:auto;word-wrap: break-word;cursor:text;background-color: transparent; }body,p,font,div,ul,li {line-height: 1.5;}p,font,div,ul,li {line-height: 1.5;margin:0;padding:0}a{color:#548DD4}</style></head><body>'+ editorContent +'</body></html>'); 
ifr_doc.close(); 
var getRange = function(){ 
var range = window.getSelection ? ifr_win.getSelection() : ifr_win.document.selection; 
if (!range) { 
return { 
node : null, 
range : null, 
text : null 
}; 

range = range.createRange ? range.createRange() : range.getRangeAt(0); 
var text = window.getSelection ? range : range.text; 
var rangeNode = null; 
if (range.commonAncestorContainer) { 
rangeNode = range.commonAncestorContainer; 
} else { 
if (range.parentElement) rangeNode = range.parentElement(); 

return { 
node : rangeNode, 
range : range, 
text : text 


var info = document.getElementsByTagName('span')[0]; 
var getStyle = function(node){ 
//console.log(node) 
var html = ''; 
html+= '<span style="font-family:'+ css(node,'font-family') +'">字體:'+ css(node,'font-family') + '</span><br />'; 
html+= '<span style="color:'+ css(node,'color') +'">顏色:'+ css(node,'color') + '</span><br />'; 
html+= '<span style="font-style:'+ css(node,'font-style') +'">斜體:'+ css(node,'font-style') + '</span><br />'; 
html+= '<span style="font-weight:'+ css(node,'font-weight') +'">粗體:'+ css(node,'font-weight') + '</span><br />'; 
html+= '<span style="text-decoration:'+ css(node,'text-decoration') +'">下劃線:'+ css(node,'text-decoration') + '</span><br />'; 
html+= 'tagName:'+ node.tagName + ',style:'+ node.getAttribute('style') +'<br />'; 
info.innerHTML = html; 

//當(dāng)光標(biāo)位置改變時(shí)候執(zhí)行 
var onselectionchange = function(event){ 
var e = event || window.event; 
if(!e.keyCode)e.keyCode = e.which; 
//方向鍵移動光標(biāo),獲取光標(biāo)位置的dom 
if((e.keyCode >= 37 && e.keyCode <= 40 )|| e.type == "click"){ 
var node = getRange().node;//獲取光標(biāo)位置元素 
if(node !== null){ 
while(node.nodeType != 1){ 
node = node.parentNode; 

getStyle(node); 



bind(ifr_doc,'click',onselectionchange,false); 
bind(ifr_doc,'keydown',onselectionchange,false); 
bind(document.getElementById('J_tool'),'click',function(event){ 
event = event || window.event; 
var target = event.srcElement || event.target; 
var command = target.getAttribute('command'); 
var param = target.getAttribute('param') || ''; 
ifr_doc.execCommand(command,false,param); 
return false; 
}) 

window.onload = function(){ 
bindEditor(); 

</script> 
</body> 
</html> 

如何解決呢? 只能依靠javascript模擬撤銷與重做了。網(wǎng)絡(luò)這方面的資源還是不少的,就不在此詳細(xì)說明了 


注:相關(guān)教程知識閱讀請移步到編輯器頻道。
發(fā)表評論 共有條評論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
伊人色综合网| 国产资源在线一区| 午夜影院福利社| 欧美伊人久久大香线蕉综合69| 微拍福利一区二区| 精品在线一区二区三区| 国产经典自拍视频在线观看| 国产精品视频看看| 九九视频在线播放| 国产suv精品一区二区| 51精品国产人成在线观看| 亚洲伦理电影| 免费看涩涩视频软件| 在线永久免费观看黄网站| 欧洲中文在线| 国产成人精品视频免费| 欧美性少妇18aaaa视频| 深夜福利一区二区三区| 欧美日韩中文字幕在线视频| 爱情岛论坛亚洲入口| 久久久欧美精品sm网站| 99久久精品国产精品久久| 青青免费在线视频| 欧美日韩精品二区| 青青草国产在线| 亚洲va韩国va欧美va精品| 久久99久久99小草精品免视看| 欧美日韩国产在线播放| 狠狠操一区二区三区| 国产欧美在线一区| 免费的av在线| jizz亚洲大全| 97香蕉久久夜色精品国产| 亚洲不卡免费视频| 国产在线资源一区| 国产伦精品一区二区三区妓女下载| free性欧美hd另类精品| av在线播放亚洲| 99久久久久免费精品国产| 国语自产精品视频在线看一大j8| 亚洲图片小说网| 一本一道久久a久久综合精品| 99在线|亚洲一区二区| 免费黄色网页| 国产成人无码a区在线观看视频| 男人的天堂av网| 丝袜足脚交91精品| 亚洲精品久久久久中文字幕二区| 伊人久久大香线| 大杳蕉精品视频在线观看| 日韩欧美激情| 在线观看不卡的av| 亚洲h视频在线观看| 中文av字幕一区| 久久久久久久影视| 国产又粗又黄又爽| 国产 porn| 国产高清在线看| 欧美色图天堂网| 蜜臀尤物一区二区三区直播| 中文字幕av久久爽| 亚洲熟女综合色一区二区三区| 麻豆changesxxx国产| 性生活免费网站| 无码一区二区三区在线观看| 亚洲www啪成人一区二区麻豆| 成人h在线观看| jizz国产精品| 亚洲人成电影院色| 日韩美女在线观看一区| 久久精品卡一| 亚洲精品久久久久中文字幕欢迎你| 日韩国产成人无码av毛片| 在线电影一区二区| 性爱在线免费视频| 中文字幕在线不卡一区二区三区| 免费不卡在线观看| 午夜精品久久久久久久久| 椎名由奈av一区二区三区| 亚洲天堂av资源在线观看| gogo高清午夜人体在线| 亚洲欧洲三级| 日本精品一二三区| 九九精品视频在线观看| 亚洲色图综合区| 2023国产精品| 亚洲av少妇一区二区在线观看| 加勒比综合在线| 91亚洲一区| 亚洲精品一卡二卡三卡四卡| 欧美大片在线观看一区| 国产精品成久久久久三级| 亚洲AV无码成人片在线观看| 黄色欧美日韩| 国产精品一二三四五区| 亚洲免费小视频| 中文无码av一区二区三区| 午夜久久久久久久| 99精品一区二区三区的区别| 成人在线小说| 国产精品入口麻豆免费观看| 一区二区三区视频网站| 欧美成人亚洲高清在线观看| 日本妇乱大交xxxxx| 97在线免费| 色av手机在线| 亚洲欧美激情另类| 日本一区美女| 久久精品91久久久久久再现| 中文字幕你懂的| 偷偷www综合久久久久久久| 91综合精品国产丝袜长腿久久| 波多野结衣一区二区三区在线| 免费在线性爱视频| 成人午夜毛片| 天天综合天天做天天综合| 性做久久久久久免费观看| 日本一区二区三区精品| 中文.日本.精品| 热99精品只有里视频最新| 在线精品观看国产| 亚洲黄色片免费看| 朝桐光av在线一区二区三区| 国产精品无码在线播放| 亚洲av成人精品日韩在线播放| 成人直播在线| 成人午夜av在线| 青青草在线视频免费观看| 免费成人动漫| 欧美xxxx精品| 91九色porn| 国产69精品久久久久9999apgf| 国产小视频在线免费观看| 欧美一区二区三区思思人| 永久免费在线看片视频| 精品国产免费久久| 久久五月婷婷丁香社区| 国产精品1区| 日韩一区精品视频| 91p九色成人| 麻豆成人免费视频| 精品资源在线看| xxxx69hd| 中国jizz妇女jizz妇女| 日韩亚洲综合在线| 91 在线视频观看| 国产不卡精品在线| av资源在线观看免费高清| 视频在线精品一区| 国产免费内射又粗又爽密桃视频| 成人激情五月天| 蜜桃久久久久久久| 国产精品综合激情| 欧美国产精品一区二区| 黄色99视频| 丰满大乳少妇在线观看网站| 91精品国产高清久久久久久久久| 国产v日产∨综合v精品视频| 电影天堂国产精品| 久久夜色邦福利网| 国产精品久久久精品| 欧美自拍视频在线观看| 成年在线观看免费人视频| 香蕉在线播放| 超碰在线caoporen| 欧美精品高清| 亚洲奶水xxxx哺乳期| 91动漫在线看| 日韩 国产 一区| 国产精品一区二区免费| 亚洲午夜一区二区三区| 亚洲精品福利在线| 韩国三级成人在线| 国产精品刘玥久久一区| 国产精品区在线| 美女国产一区二区三区| 国语精品中文字幕| 成人午夜在线免费| 欧美日韩精品在线播放| 农民人伦一区二区三区| 日本片在线观看| 亚洲aⅴ日韩av电影在线观看| 无码人妻aⅴ一区二区三区日本| 日韩欧美中文在线观看| 精品少妇一区二区三区| 婷婷伊人综合| 中文字幕一区二区三区免费视频| 亚洲天堂网在线视频| 国产精品老牛影院在线观看| 欧美在线视频观看免费网站| 囯产精品一品二区三区| 亚洲午夜激情免费视频| 一区二区欧美久久| 欧美大荫蒂xxx| 精品一区二区三区国产| 不卡毛片在线看| 久久久久久www| 欧美激情精品久久久久久变态| 亚洲一区二区三区在线免费| 欧美色欧美亚洲另类二区精品| 国产精品偷伦一区二区| 91香蕉视频污| 国产成人精品男人的天堂538| 亚洲精品高清视频在线观看| 青青青免费在线视频| 国产美女高潮视频| 亚洲一区二区在线视频观看| 精品久久久久久久久久久| 四虎在线观看| 九九热精品视频在线观看| 美日韩精品免费| 精品视频在线视频| 天堂а√在线资源在线| 俄罗斯xxxx性全过程| 91麻豆福利| 香蕉国产在线视频| 日韩av在线一区二区三区| 精品孕妇一区二区三区| 最近中文字幕无免费| 91丨九色丨蝌蚪富婆spa| 先锋影音av在线| 欧洲vodafone精品| 黑人精品欧美一区二区蜜桃| 中国色在线观看另类| 成年网站在线视频网站| 欧美性潮喷xxxxx免费视频看| 韩国在线视频一区| 三级无遮挡在线观看| 国产精品乱码人人做人人爱| 免费高潮视频95在线观看网站| xvideos亚洲人网站| 丰满人妻一区二区三区免费视频| 91视频播放| 99精品久久久久久中文字幕| 欧美一区三区三区高中清蜜桃| 亚洲一区中文字幕在线观看| 青青草国产成人av片免费| 色婷婷综合久久久久中文| 免费**毛片在线| 中文人妻av久久人妻18| 国产一区二区三区av电影| 中文字幕亚洲国产| 国产精品美女午夜av| 最近更新的2019中文字幕| 欧美日韩激情视频在线观看| 男人操女人免费| 亚洲美洲欧洲综合国产一区| 法国伦理少妇愉情| 老司机午夜av| 成人精品久久av网站| 成人www视频网站免费观看| 欧美精品一区二区三| 国产高清不卡二三区| 9999精品免费视频| 日韩精品美女| 一区av在线播放| 国产精品视频网址| 国产免费一级片| 欧美aⅴ在线观看| 欧美日韩一区二区三区| 色系网站成人免费| 欧美亚洲爱爱另类综合| 久久97精品| 欧美亚洲色综久久精品国产| 亚洲精品写真福利| 成年在线观看视频| 免费观看一二区视频网站| 欧美少妇在线观看| 扒开腿狂躁女人爽出白浆2| 中文字幕在线网| 91免费公开视频| 日韩高清电影一区| 在线中文字幕av| 国产一区二区三区网站| 国产97人人超碰caoprom| 在线观看国产精品淫| 天堂俺去俺来也www久久婷婷| √天堂8在线网| 2017亚洲天堂| 免费人成在线不卡| 欧美日韩精品免费观看视完整| 国产一区二区精品久久99| 亚洲kkk444kkk在线观看| 国产一二三在线视频| 亚洲精品一区二区在线| 欧美黄色a视频| 1000部国产精品成人观看| 欧美高清不卡在线| 国产欧美日本一区视频| 国产卡1卡2卡三卡在线| 国产情人节一区| 欧美极度另类| 天天天天天天天操| 日韩精品中文字幕在线观看| 精品女厕一区二区三区| 亚洲成人av在线播放| 93在线视频精品免费观看| 尹人成人综合网| 国产一区二区三区四区五区在线| 伊人久久大香线蕉av超碰| 日韩精品――中文字幕| 亚洲国产日日夜夜| 国产一二区在线观看| 久久先锋影音| 国产精品黄视频| 欧美日韩一区在线观看| 五月综合网站| xxxx日本黄色| 日本jizz中国| 日韩va在线观看| 成人免费淫片在线费观看| 免费看美女视频在线网站| 五月开心六月丁香综合色啪| 欧美与欧洲交xxxx免费观看| 欧美亚洲免费电影| 老牛影视一区二区三区| 欧美激情成人在线| 欧美色视频一区| 亚洲三级影院| 欧美黄色录像| 中文亚洲视频在线| 久久久久久噜噜噜久久久精品| 国产精品第一| 亚洲图片123| www.av毛片| 国产交换配乱淫视频免费| 国产mv日韩mv欧美| 日本不卡高清视频一区|