I am integrating the Quill editor into our application, and have been asked to implement line-numbering in code blocks. Following from this discussion, I used
.ql-code-block-container {
counter-reset: line;
padding-left: 0;
}
.ql-code-block:before {
counter-increment: line;
content: counter(line);
display: inline-block;
border-right: 1px solid #ddd;
padding: 0 .5em;
margin-right: .5em;
color: #EEE;
}
This works well but for one issue in Chrome. I can add some text, which appears in Dev-tools as:
<div class="ql-code-block-container" spellcheck="false">
<div class="ql-code-block">Here</div>
<div class="ql-code-block">is</div>
<div class="ql-code-block">some</div>
<div class="ql-code-block">text</div>
</div>
and Crome renders as
But if I highlight and delete the middle two lines, Dev-tools shows
<div class="ql-code-block-container" spellcheck="false">
<div class="ql-code-block">Here</div>
<div class="ql-code-block">text</div>
</div>
while Chrome renders it as
If I add a new line of text, it seems to recalculate the counters correctly. I suspect this is a Chrome bug (it refreshes fine in FireFox), but is there any general way to force a browser to refresh its CSS counter calculations when content changes?
You can try to toggle counterReset in javascript to force chrome to refresh. Take a look a this example :
function remove() {
console.log("remove")
var els = document.getElementsByClassName("ql-code-block");
removeCodeBlocElement(els[1])
}
function removeCodeBlocElement(element) {
var elementContainer = element.closest(".ql-code-block-container");
element.remove();
elementContainer.style.counterReset = "none"
//using setTimeout to disable browser property optimisation
setTimeout(() => {
elementContainer.style.counterReset = "";
}, 0);
}
.ql-code-block-container {
counter-reset: line;
padding-left: 0;
}
.ql-code-block:before {
counter-increment: line;
content: counter(line);
display: inline-block;
border-right: 1px solid #ddd;
padding: 0 .5em;
margin-right: .5em;
}
<div class="ql-code-block-container" spellcheck="false">
<div class="ql-code-block">Here</div>
<div class="ql-code-block" id="remove">is</div>
<div class="ql-code-block">some</div>
<div class="ql-code-block">text</div>
</div>
<button onclick="remove()">Remove</button>
Edit : If you have any events on your ql-code-block
, you can also use innerHTML and avoid a possible flickering counter number
function remove() {
var elements = document.getElementsByClassName("ql-code-block");
var element = elements[1];
var elementContainer = element.closest(".ql-code-block-container");
element.remove();
//using innerHTML removes all events from child elements
elementContainer.innerHTML = elementContainer.innerHTML;
}
.ql-code-block-container {
counter-reset: line;
padding-left: 0;
}
.ql-code-block:before {
counter-increment: line;
content: counter(line);
display: inline-block;
border-right: 1px solid #ddd;
padding: 0 .5em;
margin-right: .5em;
}
<div class="ql-code-block-container" spellcheck="false">
<div class="ql-code-block">Here</div>
<div class="ql-code-block" id="remove">is</div>
<div class="ql-code-block">some</div>
<div class="ql-code-block">text</div>
</div>
<button onclick="remove()">Remove using InnerHTML</button>