博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
vue-textarea 自适应高度
阅读量:4447 次
发布时间:2019-06-07

本文共 3287 字,大约阅读时间需要 10 分钟。

需求简介

一个搜索页面,上面输入框,下面列表展示搜索到的结果。

重点是:产品要求搜索框默认显示一行,当输入的文字超过一行时,输入框的高度会随着改变,直到输入完毕。

解决思路设想

本想利用textarea实现,但textarea不支持自适应高度,而是定好高度或者是行数之后,超出部分就会显示滚动条。只能另想。

根据需求,首先想到了张鑫旭一文提到的文字多字号自动变小的技巧,但仔细一琢磨,不行。这个是根据内容元素的个数,进行处理,而这儿是输入框,没有内容元素。

后面想到可以利用html属性contenteditable="true",加在div上让其可编辑来模拟自适应高度。可是需要在vue中双向绑定实现,这个不是很好处理。

后面想到利用textarea的row属性,根据输入内容的长度控制row的值,为1-n行,但这个似乎不是很智能,因为多少个字体一行不一定,英文、中文、数字的宽度不一致,而且row属性在每个浏览器中的表现不一致。

最后利用textarea,监听change事件,让其高度=其滚动条高度,来达到高度自适应。

没想到最后还是利用了textarea。

实现

参考:

util.js

/*** 文本框根据输入内容自适应高度* @param       {HTMLElement}   输入框元素* @param       {Number}        设置光标与输入框保持的距离(默认0)* @param       {Number}        设置最大高度(可选)* @callback    {Function}      设置回调函数(可选)*/export const autoTextarea = function (elem, extra, maxHeight, callback) {  extra = extra || 0;  var isFirefox = !!document.getBoxObjectFor || 'mozInnerScreenX' in window,    isOpera = !!window.opera && !!window.opera.toString().indexOf('Opera'),    addEvent = function (type, callback) {      elem.addEventListener ?        elem.addEventListener(type, callback, false) :        elem.attachEvent('on' + type, callback);    },    getStyle = elem.currentStyle ? function (name) {      var val = elem.currentStyle[name];      if (name === 'height' && val.search(/px/i) !== 1) {        var rect = elem.getBoundingClientRect();        return rect.bottom - rect.top -          parseFloat(getStyle('paddingTop')) -          parseFloat(getStyle('paddingBottom')) + 'px';      };      return val;    } : function (name) {      return getComputedStyle(elem, null)[name];    },    minHeight = parseFloat(getStyle('height'));  elem.style.resize = 'none';  var change = function () {    var scrollTop, height,      padding = 0,      style = elem.style;    if (elem._length === elem.value.length) return;    elem._length = elem.value.length;    if (!isFirefox && !isOpera) {      padding = parseInt(getStyle('paddingTop')) + parseInt(getStyle('paddingBottom'));    };    scrollTop = document.body.scrollTop || document.documentElement.scrollTop;    elem.style.height = minHeight + 'px';    if (elem.scrollHeight > minHeight) {      if (maxHeight && elem.scrollHeight > maxHeight) {        height = maxHeight - padding;        style.overflowY = 'auto';      } else {        height = elem.scrollHeight - padding;        style.overflowY = 'hidden';      };      style.height = height + extra + 'px';      scrollTop += parseInt(style.height) - elem.currHeight;      document.body.scrollTop = scrollTop;      document.documentElement.scrollTop = scrollTop;      elem.currHeight = parseInt(style.height);      callback(parseInt(style.height));    };  };  addEvent('propertychange', change);  addEvent('input', change);  addEvent('focus', change);  change();};export const debounce = function (func, delay) {  let timer;  return function (...args) {    if (timer) {      clearTimeout(timer);    }    timer = setTimeout(() => {      func.apply(this, args);    }, delay || 500);  }}

说明:由于下面是列表,需要计算高度,为了避免重新再去获取高度,所以加了个回调方法,把高度回调出去。

vue-search.vue

补充div模拟textarea自适应

转载于:https://www.cnblogs.com/EnSnail/p/10770173.html

你可能感兴趣的文章
HDU 1195 Open the Lock(BFS)
查看>>
Struts2的crud
查看>>
java上传文件
查看>>
大学生对技术网站需求的调查问卷结果分析
查看>>
测试一
查看>>
vertx的HttpServer模块
查看>>
as3事件流机制彻底理解
查看>>
Selenium webdriver操作日历控件
查看>>
Pascal程序练习-与7无关的数
查看>>
Linux:cut命令...未完待续
查看>>
微信小程序从零开始开发步骤(一)搭建开发环境
查看>>
SQL*Net more data to client
查看>>
Tcpdump使用方法总结
查看>>
PX4地面站QGroundControl在ubuntu下的安装
查看>>
react实现svg实线、虚线、方形进度条
查看>>
正则表达式高级用法【原】
查看>>
深入理解JavaScript系列(33):设计模式之策略模式
查看>>
关于户口
查看>>
Web
查看>>
函数名应用,闭包,装饰器初识
查看>>