How to create a "Line Counter" in a texbox

Asked

Viewed 148 times

-1

I wish I could count the lines Visual Code, Atom or any such publisher.

Follow an example image
inserir a descrição da imagem aqui

Details: My project runs in c# form, one of the Forms would have a txtbox with the line counter.

I’ll say thank you! Edit : I got it, I used the library https://sourceforge.net/projects/bsfccontrollibr/ and changed the project properties to . lib and compiled

2 answers

3

TLN.js / TLN.css

const TLN = {
    eventList: {},
    update_line_numbers: function(ta, el) {
        let lines = ta.value.split("\n").length;
        let child_count = el.children.length;
        let difference = lines - child_count;

        if(difference > 0) {
            let frag = document.createDocumentFragment();
            while(difference > 0) {
                let line_number = document.createElement("span");
                line_number.className = "tln-line";
                frag.appendChild(line_number);
                difference--;
            }
            el.appendChild(frag);
        }
        while(difference < 0) {
            el.removeChild(el.firstChild);
            difference++;
        }
    },
    append_line_numbers: function(id) {
        let ta = document.getElementById(id);
        if(ta == null) {
            return console.warn("[tln.js] Couldn't find textarea of id '"+id+"'");
        }
        if(ta.className.indexOf("tln-active") != -1) {
            return console.warn("[tln.js] textarea of id '"+id+"' is already numbered");
        }
        ta.classList.add("tln-active");
        ta.style = {};

        let el = document.createElement("div");
        ta.parentNode.insertBefore(el, ta);
        el.className = "tln-wrapper";
        TLN.update_line_numbers(ta, el);
        TLN.eventList[id] = [];

        const __change_evts = [
            "propertychange", "input", "keydown", "keyup"
        ];
        const __change_hdlr = function(ta, el) {
            return function(e) {
                if((+ta.scrollLeft==10 && (e.keyCode==37||e.which==37
                    ||e.code=="ArrowLeft"||e.key=="ArrowLeft"))
                || e.keyCode==36||e.which==36||e.code=="Home"||e.key=="Home"
                || e.keyCode==13||e.which==13||e.code=="Enter"||e.key=="Enter"
                || e.code=="NumpadEnter")
                    ta.scrollLeft = 0;
                TLN.update_line_numbers(ta, el);
            }
        }(ta, el);
        for(let i = __change_evts.length - 1; i >= 0; i--) {
            ta.addEventListener(__change_evts[i], __change_hdlr);
            TLN.eventList[id].push({
                evt: __change_evts[i],
                hdlr: __change_hdlr
            });
        }

        const __scroll_evts = [ "change", "mousewheel", "scroll" ];
        const __scroll_hdlr = function(ta, el) {
            return function() {  el.scrollTop = ta.scrollTop;  }
        }(ta, el);
        for(let i = __scroll_evts.length - 1; i >= 0; i--) {
            ta.addEventListener(__scroll_evts[i], __scroll_hdlr);
            TLN.eventList[id].push({
                evt: __scroll_evts[i],
                hdlr: __scroll_hdlr
            });
        }
    },
    remove_line_numbers: function(id) {
        let ta = document.getElementById(id);
        if(ta == null) {
            return console.warn("[tln.js] Couldn't find textarea of id '"+id+"'");
        }
        if(ta.className.indexOf("tln-active") == -1) {
            return console.warn("[tln.js] textarea of id '"+id+"' isn't numbered");
        }
        ta.classList.remove("tln-active");

        ta.previousSibling.remove();

        if(!TLN.eventList[id]) return;
        for(let i = TLN.eventList[id].length - 1; i >= 0; i--) {
            const evt = TLN.eventList[id][i];
            ta.removeEventListener(evt.evt, evt.hdlr);
        }
        delete TLN.eventList[id];
    }
}
.tln-active, .tln-wrapper, .tln-line {
    margin: 0;
    border: 0;
    padding: 0;
    outline: 0;
    box-sizing: border-box;
    vertical-align: middle;
    list-style: none;
}
.tln-active {
    display: inline-block;
    padding: 10px;
    width: calc(100% - 48px);
    height: 100%;
    font-size: 16px;
    line-height: 1.5;
    font-family: "Roboto Mono", monospace;
    word-break: break-all;
    border: 1px solid #aeaeae;
    background-color: #fff;
    resize: none;
    overflow-wrap: normal;
    overflow-x: auto;
    white-space: pre;
}
.tln-wrapper {
    width: 48px;
    padding: 11px 5px 35px;
    height: 100%;
    word-break: break-all;
    overflow: hidden;
    display: inline-block;
    counter-reset: line;
    background: #ebebe4;
}
.tln-line {
    width: 100%;
    display: block;
    text-align: right;
    line-height: 1.5;
    font-size: 16px;
    color: #aeaeae;
}
.tln-line::before {
    counter-increment: line;
    content: counter(line);
    font-size: 16px;
    user-select: none;
    color: #545454;
}
<h1> Example </h1>
    <button onclick="TLN.append_line_numbers('test')"> NUMBERIFY! </button>
    <button onclick="TLN.remove_line_numbers('test')"> UN-NUMBERIFY! </button>
    <div id="wrapper">
        <textarea id="test" class="banana-cake"></textarea>
    </div>
    <label>
        Width:
        <input oninput="wrapper.style.width=this.value+'px';" type="range" value="500" min="100" max="700" />
    </label>
    <label>
        Height:
        <input oninput="wrapper.style.height=this.value+'px';" type="range" value="500" min="100" max="700" />
    </label>

This code was not made by me, but I use a modified version of it. Follow the git where I found this code.

https://github.com/MatheusAvellar/textarea-line-numbers

  • Hi, how could I import this js to my project ?

  • Describe more about this project of yours, because VS is an IDE for development, when it leaves a more detailed question as I left an answer bearing in mind that I would be setting up a website.. Obs: I’m also new in programming and just like you do my projects, and only now I’m coming here to see if I help people but without more details I can give you an incoherent solution.

  • I forgot to mark, the project is the win c# form

  • @Rafaelsene. Add the winform tag to the question.

2


Use the library Able Opus C# there you will find the component NumberedRTBwhich is a RichTextBox with a numbered panel next to:

NumberedRTB

To use it just instantiate it in run-time or else add it in design-time via Toolbox.

To instantiate in Runtime:

using System;
using System.IO;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

// Para ter acesso ao controle insira o namespace
using AboControls.UserControls;



namespace WindowsFormsApp1
{
    public partial class Form1 : Form
    {
        // Crie uma instância do componente
        public NumberedRTB textBox1 = new NumberedRTB();

        public Form1()
        {           
            InitializeComponent();

            // Adicione o controle no Form
            this.Controls.Add(textBox1);

        }
    }
}
  • hello Helped me a lot by taking the question how would I make the "import" for my existing project ?

  • @Fullstack-Overkill: Compile the library and then add it as reference

Browser other questions tagged

You are not signed in. Login or sign up in order to post.