Javascript 使 html 文本输入字段随着我的输入而增长?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/7168727/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-24 01:08:54  来源:igfitidea点击:

make html text input field grow as I type?

javascriptjqueryhtmlcss

提问by Stann

I can set initial text input size in css, like so:

我可以在 css 中设置初始文本输入大小,如下所示:

width: 50px;

But I would like it to grow when I type until it reaches for example 200px. Can this be done in straight css, html, preferably without javascript?

但我希望它在我输入时增长,直到达到例如 200px。这可以在直接的 css、html 中完成,最好没有 javascript 吗?

Do post your js/jquery solutions too of course, but if this is doable without them - that be great.

当然也要发布您的 js/jquery 解决方案,但是如果没有它们也可以这样做 - 那就太好了。

my try here:

我在这里尝试:

http://jsfiddle.net/jszjz/2/

http://jsfiddle.net/jszjz/2/

回答by Joe

Here is an example with only CSS and Content Editable:

这是一个只有 CSS 和Content Editable的示例:

jsFiddle Example

jsFiddle 示例

CSS

CSS

span 
{
    border: solid 1px black;
}
div 
{
    max-width: 200px;   
}

HTML

HTML

<div>
    <span contenteditable="true">sdfsd</span>
</div>

回答by Paul

I just wrote this for you, I hope you like it :) No guarantees that it's cross-browser, but I think it is :)

我只是为你写的,我希望你喜欢它 :) 不能保证它是跨浏览器的,但我认为它是 :)

(function(){
    var min = 100, max = 300, pad_right = 5, input = document.getElementById('adjinput');

    input.style.width = min+'px';
    input.onkeypress = input.onkeydown = input.onkeyup = function(){
        var input = this;
        setTimeout(function(){
            var tmp = document.createElement('div');
            tmp.style.padding = '0';
            if(getComputedStyle)
                tmp.style.cssText = getComputedStyle(input, null).cssText;
            if(input.currentStyle)
                tmp.style.cssText = input.currentStyle.cssText;
            tmp.style.width = '';
            tmp.style.position = 'absolute';
            tmp.innerHTML = input.value.replace(/&/g, "&amp;")
                                       .replace(/</g, "&lt;")
                                       .replace(/>/g, "&gt;")
                                       .replace(/"/g, "&quot;")
                                       .replace(/'/g, "&#039;")
                                       .replace(/ /g, '&nbsp;');
            input.parentNode.appendChild(tmp);
            var width = tmp.clientWidth+pad_right+1;
            tmp.parentNode.removeChild(tmp);
            if(min <= width && width <= max)
                input.style.width = width+'px';
        }, 1);
    }
})();

JSFiddle

JSFiddle

回答by muffs

How about programmatically modifying the size attribute on the input?

如何以编程方式修改输入的 size 属性?

Semantically (imo), this solution is better than the accepted solution because it still uses input fields for user input but it does introduce a little bit of jQuery. Soundcloud does something similar to this for their tagging.

在语义上 (imo),这个解决方案比公认的解决方案更好,因为它仍然使用输入字段作为用户输入,但它确实引入了一点点 jQuery。Soundcloud 为他们的标签做了类似的事情。

<input size="1" />

$('input').on('keydown', function(evt) {
    var $this = $(this),
        size = parseInt($this.attr('size'), 10),
        isValidKey = (evt.which >= 65 && evt.which <= 90) || // a-zA-Z
                     (evt.which >= 48 && evt.which <= 57) || // 0-9
                     evt.which === 32;

    if ( evt.which === 8 && size > 0 ) {
        // backspace
        $this.attr('size', size - 1);
    } else if ( isValidKey ) {
        // all other keystrokes
        $this.attr('size', size + 1);
    }
});

http://jsfiddle.net/Vu9ZT/

http://jsfiddle.net/Vu9ZT/

回答by lastmjs

If you set the span to display: inline-block, automatic horizontal and vertical resizing works very well:

如果您将 span 设置为 display: inline-block,自动水平和垂直调整大小效果很好:

<span contenteditable="true" 
      style="display: inline-block;
             border: solid 1px black;
             min-width: 50px; 
             max-width: 200px">
</span>

回答by cmpolis

From: Is there a jQuery autogrow plugin for text fields?

来自:是否有用于文本字段的 jQuery 自动增长插件?



See a demo here: http://jsbin.com/ahaxe

在此处查看演示:http: //jsbin.com/ahaxe

The plugin:

插件:

(function($){

    $.fn.autoGrowInput = function(o) {

        o = $.extend({
            maxWidth: 1000,
            minWidth: 0,
            comfortZone: 70
        }, o);

        this.filter('input:text').each(function(){

            var minWidth = o.minWidth || $(this).width(),
                val = '',
                input = $(this),
                testSubject = $('<tester/>').css({
                    position: 'absolute',
                    top: -9999,
                    left: -9999,
                    width: 'auto',
                    fontSize: input.css('fontSize'),
                    fontFamily: input.css('fontFamily'),
                    fontWeight: input.css('fontWeight'),
                    letterSpacing: input.css('letterSpacing'),
                    whiteSpace: 'nowrap'
                }),
                check = function() {

                    if (val === (val = input.val())) {return;}

                    // Enter new content into testSubject
                    var escaped = val.replace(/&/g, '&amp;').replace(/\s/g,'&nbsp;').replace(/</g, '&lt;').replace(/>/g, '&gt;');
                    testSubject.html(escaped);

                    // Calculate new width + whether to change
                    var testerWidth = testSubject.width(),
                        newWidth = (testerWidth + o.comfortZone) >= minWidth ? testerWidth + o.comfortZone : minWidth,
                        currentWidth = input.width(),
                        isValidWidthChange = (newWidth < currentWidth && newWidth >= minWidth)
                                             || (newWidth > minWidth && newWidth < o.maxWidth);

                    // Animate width
                    if (isValidWidthChange) {
                        input.width(newWidth);
                    }

                };

            testSubject.insertAfter(input);

            $(this).bind('keyup keydown blur update', check);

        });

        return this;

    };

})(jQuery);

回答by Seth

A couple of things come to mind:

我想到了几件事:

Use an onkeydownhandler in your text field, measure the text*, and increase the text box size accordingly.

onkeydown在文本字段中使用处理程序,测量文本*,并相应地增加文本框大小。

Attach a :focuscss class to your text box with a larger width. Then your box will be larger when focused. That's not exactly what you're asking for, but similar.

:focuscss 类附加到具有较大宽度的文本框。那么你的盒子在聚焦时会更大。这不完全是你所要求的,但相似。

* It's not straightforward to measure text in javascript. Check out this questionfor some ideas.

* 在 javascript 中测量文本并不简单。查看这个问题以获得一些想法。

回答by Pantelis

Here you can try something like this

在这里你可以尝试这样的事情

EDIT: REVISED EXAMPLE (added one new solution) http://jsfiddle.net/jszjz/10/

编辑:修改后的例子(添加了一个新的解决方案) http://jsfiddle.net/jszjz/10/

Code explanation

代码说明

var jqThis = $('#adjinput'), //object of the input field in jQuery
    fontSize = parseInt( jqThis.css('font-size') ) / 2, //its font-size
    //its min Width (the box won't become smaller than this
    minWidth= parseInt( jqThis.css('min-width') ), 
    //its maxWidth (the box won't become bigger than this)
    maxWidth= parseInt( jqThis.css('max-width') );

jqThis.bind('keydown', function(e){ //on key down
   var newVal = (this.value.length * fontSize); //compute the new width

   if( newVal  > minWidth && newVal <= maxWidth ) //check to see if it is within Min and Max
       this.style.width = newVal + 'px'; //update the value.
});

and the css is pretty straightforward too

而且css也很简单

#adjinput{
    max-width:200px !important;
    width:40px;
    min-width:40px;
    font-size:11px;
}

EDIT: Another solution is to havethe user type what he wants and on blur (focus out), grab the string (in the same font size) place it in a div - count the div's width - and then with a nice animate with a cool easing effect update the input fields width. The only drawback is that the input field will remain "small" while the user types. Or you can add a timeout : ) you can check such a kind of solution on the fiddle above too!

编辑:另一种解决方案是让用户输入他想要的内容并在模糊(聚焦)上,抓住字符串(以相同的字体大小)将其放在一个 div 中 - 计算 div 的宽度 - 然后用一个很酷的动画缓动效果更新输入字段宽度。唯一的缺点是当用户键入时,输入字段将保持“小”。或者您可以添加超时:) 您也可以在上面的小提琴上检查这种解决方案!

回答by b0rgBart3

I know this is a seriously old post - but my answer might be useful to others anyway, so here goes. I found that if my CSS style definition for the contenteditable div has a min-height of 200 instead of a height of 200 , then the div scales automatically.

我知道这是一个非常古老的帖子 - 但无论如何我的回答可能对其他人有用,所以这里是。我发现如果 contenteditable div 的 CSS 样式定义的 min-height 为 200 而不是高度 200 ,则 div 会自动缩放。

回答by ceving

If you are just interested in growing, you can update the widthto scrollWidth, whenever the content of the inputelement changes.

如果你只是兴趣越来越大,你可以更新widthscrollWidth,无论何时的内容input元素的变化。

document.querySelectorAll('input[type="text"]').forEach(function(node) {
  node.onchange = node.oninput = function() {
    node.style.width = node.scrollWidth+'px';
  };
});

But this will not shrink the element.

但这不会缩小元素。

回答by Kevin Douglas

Which approach you use, of course, depends on what your end goal is. If you want to submit the results with a form then using native form elements means you don't have to use scripting to submit. Also, if scripting is turned off then the fallback still works without the fancy grow-shrink effects. If you want to get the plain text out of a contenteditableelement you can always also use scripting like node.textContentto strip out the html that the browsers insert in the user input.

当然,您使用哪种方法取决于您的最终目标是什么。如果您想使用表单提交结果,那么使用原生表单元素意味着您不必使用脚本来提交。此外,如果脚本关闭,则回退仍然有效,没有花哨的增长收缩效果。如果您想从contenteditable元素中获取纯文本,您也可以始终使用像node.textContent这样的脚本来去除浏览器在用户输入中插入的 html。

This version uses native form elements with slight refinements on some of the previous posts.

此版本使用原生表单元素,对之前的一些帖子略有改进。

It allows the content to shrink as well.

它也允许内容缩小。

Use this in combination with CSS for better control.

将此与 CSS 结合使用以获得更好的控制。

<html>

<textarea></textarea>
<br>
<input type="text">


<style>

textarea {
  width: 300px;
  min-height: 100px;
}

input {
  min-width: 300px;
}


<script>

document.querySelectorAll('input[type="text"]').forEach(function(node) {
  var minWidth = parseInt(getComputedStyle(node).minWidth) || node.clientWidth;
  node.style.overflowX = 'auto'; // 'hidden'
  node.onchange = node.oninput = function() {
    node.style.width = minWidth + 'px';
    node.style.width = node.scrollWidth + 'px';
  };
});

You can use something similar with <textarea> elements

您可以使用与 <textarea> 元素类似的东西

document.querySelectorAll('textarea').forEach(function(node) {
  var minHeight = parseInt(getComputedStyle(node).minHeight) || node.clientHeight;
  node.style.overflowY = 'auto'; // 'hidden'
  node.onchange = node.oninput = function() {
    node.style.height = minHeight + 'px';
    node.style.height = node.scrollHeight + 'px';
  };
});

This doesn't flicker on Chrome, results may vary on other browsers, so test.

这不会在 Chrome 上闪烁,结果在其他浏览器上可能会有所不同,因此请进行测试。