htsign's blog

ノンジャンルで書くつもりだけど技術系が多いんじゃないかと思います

スーパーpre記法で書いたコード部分に行番号を出すようにした

こんなコードをフッタに入れた。

<script src="http://code.jquery.com/jquery-1.10.2.min.js"></script>
<script>
jQuery(function($){
    $("pre.code").each(function(){
        var df = document.createDocumentFragment();
        var ol = $('<ol>').appendTo(df);
        $.each($(this).html().split("\n").filter(function(e, i, arr){
            return i !== arr.length - 1;
        }), function(i){
            $('<li>').html(this).appendTo(ol);
        });
        $(this).empty().append(df);
    });
});
</script>

jQueryで書いてるけど、ES5のメソッド使ってるので結局IE8以前では動きません。

今回はやっつけ実装なので、時間があったらまた見直してみる。

追記 (2014/01/18 13:55)

IE8以下でも動作するようにした。

<script src="http://code.jquery.com/jquery-1.10.2.min.js"></script>
<script>
jQuery(function($){
    $("pre.code").each(function(){
        var df = document.createDocumentFragment();
        var ol = $('<ol>').appendTo(df);
        $.each($(this).html().split("\n").slice(0, -1), function(i){
            $('<li>').html(this).appendTo(ol);
        });
        $(this).empty().append(df);
    });
});
</script>

たぶん動作速度も上がったと思う。体感はできないけど。
どこが変わったかっつーとArray.prototype.filterをやめてArray.prototype.sliceにしただけ。
要は配列の最後の要素が邪魔だっただけなので、無理にfilter使う必要が全くなかった。

追記 2020/07/02

純粋な JavaScript のみで再実装しました。jQueryからの脱却。
処理内容自体は同じです。

<script>
document.addEventListener('DOMContentLoaded', () => {
  document.getElementById('main-inner').querySelectorAll('pre.code').forEach(el => {
    const ol = document.createElement('ol');
    ol.append(...el.innerHTML.split('\n').slice(0, -1)
      .map(s => Object.assign(document.createElement('li'), { innerHTML: s })));
    el.innerHTML = '';
    el.append(ol);
  });
});
</script>