输入框跟随文字内容适配宽实现示例


Posted in Javascript onAugust 14, 2022

实现源码

// 常见一个辅助元素
const fakeEle = document.createElement('div');
// 隐藏辅助元素
fakeEle.style.position = 'absolute';
fakeEle.style.left = '-9999px';
fakeEle.style.visibility = 'hidden';
fakeEle.style.whiteSpace = 'nowrap';
// 获取输入框元素的样式
const textboxEle = document.getElementById('textbox');
const styles = window.getComputedStyle(textboxEle);
// 将输入框的字体样式赋给辅助元素
fakeEle.style.font = styles.font;
// 将辅助元素添加到页面
document.body.appendChild(fakeEle);
const setWidth = function () {
    const string = textboxEle.value || textboxEle.getAttribute('placeholder') || '';
    fakeEle.innerHTML = string.replace(/\s/g, ` `);
    // 获取辅助元素的样式
    const fakeEleStyles = window.getComputedStyle(fakeEle);
    // 将辅助元素的宽度赋给输入框元素
    textboxEle.style.width = fakeEleStyles.width;
};
setWidth();
// 监听输入框元素内容变化,输入框宽度跟随文字内容数量适配
textboxEle.addEventListener('input', function (e) {
    setWidth();
});

大概思路

其实核心点就是,如何获取输入框元素内文字内容的宽度值?

直接通过输入框元素肯定是无法获取到其文字内容宽度的,我们需要跳出输入框的限制,将文字内容独立出来。

首先,我们肯定是能够拿到输入框的文字内容的,使用 input.value 即可获取文字内容。

OK,文字内容有了,如何计算文字内容的宽度呢?

文字内容宽度

实现方案其实有 2 种,一种是使用 Canvas 的能力,另一种是使用辅助的 div 元素。

可能大部分同学还不是很了解 Canvas,所以本文就使用 div 元素的方式进行讲解。

首先,先定义好最基础的 HTML 和 CSS,代码如下:

<input id="textbox" type="text" />
input {
  padding: 8px;
}

此时,我们会得到一个最基础的输入框元素,没有任何文字内容。当我们往输入框元素内输入内容时,输入框元素的宽度也不会跟随变化。

然后通过 JavaScript 创建一个辅助的 div 元素,我们先将它添加到 body 元素内。

需要注意的是,文字内容的宽度会各被字体样式、大小、行间距等等因素所影响。本文作为讲解,暂时不考虑这么多影响因素,但会通过影响因素之一 “字体” 相关做个相关示例,提供各位同学作为参考。

const fakeEle = document.createElement('div');
const textboxEle = document.getElementById('textbox');
// 获取输入框元素样式
const styles = window.getComputedStyle(textboxEle);
// 将输入框元素的 font 属性赋给辅助的 div 元素
fakeEle.style.font = styles.font;
document.body.appendChild(fakeEle);

监听输入框元素的 input 事件,将文字内容同步给 div 辅助元素。

然后再反向的,获取 div 辅助元素的宽度,赋值给输入框元素,这样是不是就实现了啦了?

const setWidth = function () {
  const string = textboxEle.value || '';
  fakeEle.innerHTML = string;
  // 获取辅助元素的样式
  const fakeEleStyles = window.getComputedStyle(fakeEle);
  // 将辅助元素的宽度赋给输入框元素
  textboxEle.style.width = fakeEleStyles.width;
};
textboxEle.addEventListener('input', function (e) {
  setWidth();
});

我们来看看效果。

输入框跟随文字内容适配宽实现示例

当我们在输入框元素内随便输入一个内容,会发现输入框就撑满了整个页面。

输入框跟随文字内容适配宽实现示例

这是因为 div 辅助元素是块级元素,宽度默认是 100% 所导致的。那如何要获取文字内容宽度的话,要将它设置为行内元素嘛?

答案是不需要的,只要给 div 辅助元素添加绝对定位,使其脱离正常文档流即可。

// ...
fakeEle.style.position = 'absolute';
// ...

输入框跟随文字内容适配宽实现示例

输入框跟随文字内容适配宽实现示例

此时,我们会发现已经基本实现了我们想要的效果。

是的,我们已经解决了最核心的问题,但仍然还存在一些问题,需要我们进行处理。

细节处理

比如,输入多个空格的时候,宽度计算就错误了。

输入框跟随文字内容适配宽实现示例

这就需要我们将空格进行一下处理,将它替换成 &nbsp 即可,代码如下:

// fakeEle.innerHTML = string;
fakeEle.innerHTML = string.replace(/\s/g, ` `);

还有,辅助元素不应该出现在界面上,所以我们要将他隐藏掉。

// ...
fakeEle.style.left = '-9999px';
fakeEle.style.visibility = 'hidden';
fakeEle.style.whiteSpace = 'nowrap';
// ...

还有一些其它小细节,有兴趣的话,自己尝试一下吧。

以上就是输入框跟随文字内容适配宽实现示例的详细内容,更多关于输入框文字内容宽度适配的资料请关注三水点靠木其它相关文章!

Javascript 相关文章推荐
jquery.lazyload  实现图片延迟加载jquery插件
Feb 06 Javascript
extjs render 用法介绍
Sep 11 Javascript
Js类的静态方法与实例方法区分及jQuery拓展的两种方法
Jun 03 Javascript
详解基于webpack和vue.js搭建开发环境
Apr 05 Javascript
详解JavaScript中return的用法
May 08 Javascript
原生JS实现循环Nodelist Dom列表的4种方式示例
Feb 11 Javascript
js中el表达式的使用和非空判断方法
Mar 28 Javascript
妙用缓存调用链实现JS方法的重载
Apr 30 Javascript
小程序图片长按识别功能的实现方法
Aug 30 Javascript
vue中进入详情页记住滚动位置的方法(keep-alive)
Sep 21 Javascript
Vue-cli3.x + axios 跨域方案踩坑指北
Jul 04 Javascript
JavaScript交换变量常用4种方法解析
Sep 02 Javascript
JS开发前端团队展示控制器来为成员引流
Aug 14 #Javascript
JS实现页面炫酷的时钟特效示例
Rust中的Struct使用示例详解
Aug 14 #Javascript
使用Cargo工具高效创建Rust项目
Aug 14 #Javascript
JS实现刷新网页后之前浏览位置保持不变示例详解
Aug 14 #Javascript
vue本地构建热更新卡顿的问题“75 advanced module optimization”完美解决方案
Aug 05 #Vue.js
Vue深入理解插槽slot的使用
Aug 05 #Vue.js
You might like
php获取服务器操作系统相关信息的方法
2016/10/08 PHP
PHP实现会员账号单唯一登录的方法分析
2019/03/07 PHP
php中yar框架实例用法讲解
2020/12/27 PHP
javascript sudoku 数独智力游戏生成代码
2010/03/27 Javascript
javascript检测浏览器flash版本的实现代码
2011/12/06 Javascript
HTML5之lang属性与dir属性的详解
2013/06/19 Javascript
JS获取随机数函数可自定义最小值最大值
2014/05/08 Javascript
基于jQuery实现咖啡订单管理简单应用
2017/02/10 Javascript
jQuery实现简单的计时器功能实例分析
2017/08/29 jQuery
解决Linux无法正常安装与卸载Node.js的方法
2018/01/19 Javascript
vue将时间戳转换成自定义时间格式的方法
2018/03/02 Javascript
vue2 全局变量的设置方法
2018/03/09 Javascript
详解swipe使用及竖屏页面滚动方法
2018/06/28 Javascript
Node.js折腾记一:读指定文件夹,输出该文件夹的文件树详解
2019/04/20 Javascript
vue fetch中的.then()的正确使用方法
2020/04/17 Javascript
vue中使用带隐藏文本信息的图片、图片水印的方法
2020/04/24 Javascript
html+vue.js 实现漂亮分页功能可兼容IE
2020/11/07 Javascript
python实现基于两张图片生成圆角图标效果的方法
2015/03/26 Python
使用Python通过win32 COM实现Word文档的写入与保存方法
2018/05/08 Python
python随机数分布random测试
2018/08/27 Python
Python实现统计英文文章词频的方法分析
2019/01/28 Python
Python中的异常处理try/except/finally/raise用法分析
2019/02/28 Python
python 调用pyautogui 实时获取鼠标的位置、移动鼠标的方法
2019/08/27 Python
matplotlib基础绘图命令之bar的使用方法
2020/08/13 Python
matplotlib绘制多子图共享鼠标光标的方法示例
2021/01/08 Python
比利时的在线灯具店:Lampen24.be
2019/07/01 全球购物
学生自我鉴定
2013/12/18 职场文书
学生打架检讨书大全
2014/01/23 职场文书
环保倡议书怎么写
2014/05/16 职场文书
校庆活动策划方案
2014/06/05 职场文书
2015年师德师风自我评价范文
2015/03/05 职场文书
职业规划从高考志愿专业选择开始
2019/08/08 职场文书
话题作文之生命的旋律
2019/12/17 职场文书
解决Go gorm踩过的坑
2021/04/30 Golang
Go语言读取txt文档的操作方法
2022/01/22 Golang
Flink 侧流输出源码示例解析
2022/09/23 Servers