contentEditable实现div可编辑,控制插入节点(兼容IE)

实现可文字编辑也可插入节点的功能
展示如下:
在这里插入图片描述
html5中contentEditable属性规定是否可编辑元素的内容,给需要编辑的节点添加contentEditable=“true”。
兼容性:
在这里插入图片描述
当点击Button时在编辑框内增加节点:
在这里插入图片描述
一开始div中加的span标签,发现有几个缺陷:

  1. 点删除键时span不会删除整个,而是一个一个删除span里的字符
  2. 当有连续的span时,光标会超出容器宽度在容器外面闪烁

针对以上第一个问题试了以下两种方法:

  1. <span contentEditable="false"></span>
  2. 设置css user-modify:设置css user-modify: read-only

两种方法都能解决无法删除整个节点的问题,但光标超出容器依然在╮( ̄▽  ̄)╭
各种翻找资料后找到一个解决办法:
加input节点,并且设置disabled

var inp = document.createElement("input");
inp.setAttribute("value", value);
inp.setAttribute("data-code", code);
inp.setAttribute("disabled", 'true');
inp.style.width = this.input_resize(value) + 'px';
range.insertNode(inp);

input是不会自适应文本内容的,于是就有了input_resize去计算宽度,

input_resize(html) {
        inputResizeDom.innerHTML = html;
        inputResizeDom.style.fontSize = '16px';
        return inputResizeDom.getBoundingClientRect().width.toFixed(4);
    }

方法是给另一个节点填充相同的内容,然后取这个节点的宽度作为input节点的宽度,需要注意的是,计算宽度的节点和 input的font-sizefont-family是相同的。

说到这个,不知道大家有木有注意到range.insertNode(inp)这么一句,他的作用是在存储的光标位置处添加节点,Range对象API
Range对象初始化:

//ie 9以下
var docSelection = document.selection;
//chrome opera safari兼容
var winSelection = window.getSelection;
handleBlur() {
    if(!docSelection && winSelection){
        sel = window.getSelection();
        hasRange = sel.getRangeAt && sel.rangeCount;
        if(hasRange){
            range = sel.getRangeAt(0);
            range.deleteContents();
        }
    }
}
handleKeyUp() {
    //ie获取光标定位
    if(docSelection){
        range = document.selection.createRange();
    }
},

为什么在ie浏览器下要在keyup触发方法中重置range,这就是有些坑了,chrome中blur事件触发时range记录光标在容器中的位置,但是在IE中记录的是blur时点击的元素(就是容器以外的元素),于是我在keyup事件中对range做一个存储。
顺便说一下,ie对onInput事件兼容性不是很好,慎重使用昂~。
点击按钮时触发操作:

selectLabel(value,code,event){
    var target = event.currentTarget;
     if(!$(target).hasClass('disabled')){
         if(docSelection && document.selection.type != "Control"){
             // IE9以下
             let html = `<input value=${value} data-code=${code} disabled="true" style="width: ${this.input_resize(value) + 'px'}"/>`
             range.pasteHTML(html);
         }else if(winSelection && hasRange){
             var inp = document.createElement("input");
             inp.setAttribute("value", value);
             inp.setAttribute("data-code", code);
             inp.setAttribute("disabled", 'true');
             inp.style.width = this.input_resize(value) + 'px';
             range.insertNode(inp);
         }
         $(target).addClass('disabled')
         this.setFocus($('#contentSms'))
     }
}

几个用到的资料:
contentEditable API
光标的使用

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值