Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/471.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php &引用;“聪明的”;文本区域自动缩进_Php_Javascript_Jquery - Fatal编程技术网

Php &引用;“聪明的”;文本区域自动缩进

Php &引用;“聪明的”;文本区域自动缩进,php,javascript,jquery,Php,Javascript,Jquery,我正在尝试制作一个自动缩进文本区域,到目前为止,它可以使用以下代码。我遇到的问题是,我目前正在阻止按enter键以计算行中的制表符,然后插入换行符的默认操作 这是可行的,但我希望有textarea的默认操作,如果按住enter键,它不会滚动textarea,直到插入符号到达最下面一行,然后滚动条保持插入符号在最下面一行。如果在文本区域的任何地方使用插入符号,下面的当前代码将使其保持在视野范围内,但它会导致插入符号上方的内容向上滚动,这是一种折衷,因为插入符号不再消失。如果没有其他解决方案,这将很

我正在尝试制作一个自动缩进文本区域,到目前为止,它可以使用以下代码。我遇到的问题是,我目前正在阻止按enter键以计算行中的制表符,然后插入换行符的默认操作

这是可行的,但我希望有textarea的默认操作,如果按住enter键,它不会滚动textarea,直到插入符号到达最下面一行,然后滚动条保持插入符号在最下面一行。如果在文本区域的任何地方使用插入符号,下面的当前代码将使其保持在视野范围内,但它会导致插入符号上方的内容向上滚动,这是一种折衷,因为插入符号不再消失。如果没有其他解决方案,这将很好,但我希望有其他想法

    var start = this.selectionStart-1;
    var end = this.selectionEnd;
    var sT = this.scrollTop;
    var sH = this.scrollHeight;
    var vH = $(this).height();

    var x = (sH - sT) - vH;

    // Check if hitting enter on the first line as no newline will be found
    if (this.value.lastIndexOf('\n',start)==-1)
     var startSubstr = 0;
    else 
     var startSubstr = this.value.lastIndexOf('\n',start)+1;

    var endFirst = end - startSubstr;

    var valueToScan = this.value.substr(startSubstr,endFirst);
    var count = 0;

    // Count only \t at the beginning of the line, none in the code   
    while (valueToScan.indexOf('\t')!=-1) {
     if (valueToScan.indexOf('\t')!=0)
      break;
     count++;
     valueToScan = valueToScan.substr(valueToScan.indexOf('\t')+1);
    }

    // Command to isert the newline, and then add the \t's found in previously  
    $(this).insertAtCaret('\n');
    for (var i=0;i<count;count--) {
     $(this).insertAtCaret('\t');
    }  

    var sH = this.scrollHeight;
    this.scrollTop = (sH - x) - vH;
我希望它将您带到与“示例内容”相同的标签距离,以使您的代码更易于阅读。我目前拥有该功能,但问题是我正在拦截enter键,这意味着我必须提供该功能。我很难复制在光标到达底部边框之前不滚动文本框的确切功能。因此,如果您在textarea的顶部按住enter键,光标只会向下滚动textarea,移动任何文本,直到它到达底部边框,然后textarea的滚动条将跟随光标。有道理吗

编辑2更新的标记,以指示代码与PHP兼容

我一直在做这个,而这个职位一直坐着。我想,当我有机会时,我将探索的另一个选项是,不阻止enter,只允许默认的操作,即点击enter,并读取字符串,从
lastIndexOf('\n')-1
到任何
\t
的最新
\n
。我想这会给我想要的字符串,但不会搞乱textarea的行为。将在测试后再次更新

编辑3已解决,根据我以前的更新,我决定在按下键后扫描字符串,保留自然行为(下面为感兴趣的人添加了更改的部分),唯一剩下的问题是,如果按住enter键,它将不会从enter键的原点计算缩进,这对我来说很好。我要把这个给你http://stackoverflow.com/users/15066/matyr“>玛蒂尔,虽然在他回答之前我就知道了,但他仍然是最接近的

if (this.value.lastIndexOf('\n',start-2)==-1) {
 var startSubstr = 0;
} else {
 var startSubstr = this.value.lastIndexOf('\n',start-1)+1;
}    
var valueToScan = this.value.substr(startSubstr,start);

您是否注意到堆栈溢出文本区域如何处理代码?如果键入:

function example(whatever) {
    Example Stuff // And then hit enter here
}
起初,什么也不会发生。然后,当您缩进(通过键入或单击101010按钮)时,它会在代码上放置不同的背景。然后,在您等待片刻之后,它会对代码进行语法着色。但是如果你再开始打字,它会回到黑/白状态

我认为类似的方法可能适合你。与其尝试将所有内容都绑定到enter keypress事件,您应该做的是:

  • 连接一个普通的onKeySomething事件,但不要只查找“enter”;每次按键后:

    1A。将一些全局变量(如计时器)设置为新日期()

    1B。setTimeout(X,timeoutFunction),其中X是用户停止键入后要等待的时间长度

  • 创建timeoutFunction;此函数应检查全局“timer”变量,如果new Date()-timer>X trigger actualFunction()

  • 然后,actualFunction可以解析textarea的内容,以您喜欢的方式缩进内容,并且任何东西都不会中断用户的正常工作流程


  • 我知道这不是“真实”IDE的行为方式,但考虑到JS和web的局限性,这可能是最好的方法。

    对文本框进行子类化并手动处理WndProc如何?这将使您获得更细粒度的控制,并将处理typematic键重复(按键和类似事件仅在按住键时触发一次)

    公共类MyTextBox:System.Windows.Forms.TextBox
    {
    受保护的覆盖无效WndProc(参考消息m)
    {
    //让O/S先处理键
    基准WndProc(参考m);
    //然后,如果是返回键,则添加选项卡
    int numTabs=3;//TODO:在此处插入您自己的值
    常量int WM_CHAR=0x0102;
    如果(m.Msg==WM_CHAR&&(CHAR)m.WParam=='\r')
    {
    m、 WParam=new IntPtr('\t');//回收m,因为base已经使用它了
    对于(int i=0;i
    我想要文本区域的默认操作

    如何绑定到
    keyup
    而不是
    keydown
    /
    keypress
    并在本机换行符后插入选项卡

    滚动条保持插入符号在底行

    您可以通过还原
    scrollTop
    来保留滚动位置

    <!DOCTYPE html>
    <title>autoindent example</title>
    <textarea id="TA" rows="8"></textarea>
    <script>
    document.getElementById('TA').addEventListener('keyup', function(v){
      if(v.keyCode != 13 || v.shiftKey || v.ctrlKey || v.altKey || v.metaKey)
        return;
      var val = this.value, pos = this.selectionStart;
      var line = val.slice(val.lastIndexOf('\n', pos - 2) + 1, pos - 1);
      var indent = /^\s*/.exec(line)[0];
      if(!indent) return;
      var st = this.scrollTop;
      this.value = val.slice(0, pos) + indent + val.slice(this.selectionEnd);
      this.selectionStart = this.selectionEnd = pos + indent.length;
      this.scrollTop = st;
    }, false);
    </script>
    <p>(not considering IE here)
    
    
    自动缩进示例
    document.getElementById('TA')。addEventListener('keyup',函数(v){
    if(v.keyCode!=13 | | v.shiftKey | | v.ctrlKey | | v.altKey | v.metaKey)
    返回;
    var val=this.value,pos=this.selectionStart;
    变量行=val.slice(val.lastIndexOf('\n',位置-2)+1,位置-1);
    var indent=/^\s*/.exec(行)[0];
    如果(!缩进)返回;
    var st=this.scrollTop;
    this.value=val.slice(0,pos)+缩进+val.slice(this.selectionEnd);
    this.selectionStart=this.selectionEnd=pos+indent.length;
    this.scrollTop=st;
    },假);
    (此处不考虑IE)
    
    我知道这不是一个直截了当的答案,但网上有一些例子可以帮助你实现这一点




    如果我有更多的时间,我肯定会尝试一下,但不幸的是我没有。该项目的目的是能够直接在文本区域中编码,并在用户完成后清理代码。澄清,*而不是
    public class MyTextBox : System.Windows.Forms.TextBox
    {
        protected override void WndProc(ref Message m)
        {
            // Let the O/S handle the key first
            base.WndProc(ref m);
    
            // Then, if it's the return key, append tabs
            int numTabs = 3;                 // TODO: insert your own value here
            const int WM_CHAR = 0x0102;
            if(m.Msg == WM_CHAR && (char)m.WParam == '\r')
            {
                m.WParam = new IntPtr('\t'); // Recycle m since base is done with it
                for (int i = 0; i < numTabs; i++)
                    WndProc(ref m);
            }
        }
    }
    
    <!DOCTYPE html>
    <title>autoindent example</title>
    <textarea id="TA" rows="8"></textarea>
    <script>
    document.getElementById('TA').addEventListener('keyup', function(v){
      if(v.keyCode != 13 || v.shiftKey || v.ctrlKey || v.altKey || v.metaKey)
        return;
      var val = this.value, pos = this.selectionStart;
      var line = val.slice(val.lastIndexOf('\n', pos - 2) + 1, pos - 1);
      var indent = /^\s*/.exec(line)[0];
      if(!indent) return;
      var st = this.scrollTop;
      this.value = val.slice(0, pos) + indent + val.slice(this.selectionEnd);
      this.selectionStart = this.selectionEnd = pos + indent.length;
      this.scrollTop = st;
    }, false);
    </script>
    <p>(not considering IE here)