Wednesday, June 13, 2012

Eksperimen Syntax Highlighter

Syntax Highlighter

HAAAAAHHHHHHHHH!!!! Mulai iseng lagi…

jQuery

// Pure jQuery Syntax Highlighter by Taufik Nurrohman
// Still an experimental :)
// https://plus.google.com/108949996304093815163/about

$(function() {
    $('pre').each(function() {
        var list = "(true|false|null|main|in|endif|if|endfor|for|while|finally|var|new|function|do|return|void|else|break|catch|instanceof|with|throw|case|default|try|this|switch|continue|typeof|delete)",
            rep1 = new RegExp(list + " ", "ig"),
            rep2 = new RegExp(list + "( ?)<span", "ig"),
            $this = $(this);
        $this.html($this.html()
        .replace(/(<br>|\n)$/ig, "")
        .replace(/(\t)/g, "    ")
        .replace(/&quot;/ig, "\"")
        .replace(/&#39;|&apos;/ig, "\'")
        .replace(/(.?)'(.*?)'/g, "$1<span class='str'>\'$2\'</span>")
        .replace(/(.?)"(.*?)"/g, "$1<span class='str'>\"$2\"</span>")
        .replace(/(.?)(""|'')/g, "$1<span class='value'>$2</span>")
        .replace(/(#[A-F0-9]{3,6})/ig, "<span class='hex'>$1</span>")
        .replace(/(\d+(?!(.*&lt;)))/g, "<span class='num'>$1</span>")
        .replace(/((#|\.)[\-_A-Z0-9]+)/ig, "<span class='selector'>$1</span>")
        .replace(/(\{|\}|\(|\)|\[|\])/g, "<span class='bracket'>$1</span>")
        .replace(/&lt;(.*?)&gt;/g, "<span class='tag'>&lt;$1&gt;</span>")
        .replace(/&lt;!--([\s\S]*?)--&gt;/gm, "<span class='comment'>&lt;!--$1--&gt;</span>")
        .replace(/\/\*([\s\S]*?)\*\//gm, "<span class='comment'>/*$1*/</span>")
        .replace(/[^\:]\/\/(.*)/g, "<span class='comment'>//$1</span>")
        .replace(/<\/span>\/(.*)\/([gim]+),( ?)<span class='str'>/g, "</span><span class='regexp'>/$1/$2</span>, <span class='str'>")
        .replace(rep1, "<span class='keyword'>$1</span> ")
        .replace(rep2, "<span class='keyword'>$1</span>$2<span")
        .replace(/function<\/span> (.[^<]*)<span/g, "function</span> <span class='name'>$1</span><span")
        .replace(/([\-_A-Z]+)(?=(\s+|)):(.(?!\{)*)/ig, "<span class='attribute'>$1</span>:$2$3")
        .replace(/h<span class='num'>([1-6])<\/span>/ig, "h$1")
        .replace(/!important/ig, "<mark class='important'>!important</mark>")
        .replace(/&lt;!(doctype)(.*)&gt;/ig, "<span class='doctype'>&lt;!$1$2&gt;</span>")
        .replace(/@<span class='attribute'>(import|page|media|charset|keyframes|font-face)<\/span>/ig, "@$1")
        .replace(/(@(import|page|media|charset|keyframes|font-face))/ig, "<span class='keyword'>$1</span>")
        .replace(/<span class='bracket'>\[<\/span>(.*)<span class='bracket'>\]<\/span>/ig, "<span class='array'>[$1]</span>")
        ).find('.str span, .regexp span, .comment span, .doctype span, .hex span, .array span, .url span').contents().unwrap();
        $this.append('<div class="the-num"></div>');

        // Insert the line number
        var num = $this.html().split(/\n|<br>/).length,
            count = 0;
        for (var i = 0; i < num; i++) {
            count = count + 1;
            $this.find('.the-num').append(count + '.<br/>');
        }
        $this.css('padding-left', $this.find('.the-num').outerWidth()+14);

    });
});

CSS

pre {
  background-color:white;
  color:#069;
  padding:0em 1em;
  overflow:auto;
  white-space:pre;
  word-wrap:normal;
  font:bold 12px/1.5em "Consolas","Bitstream Vera Sans Mono","Courier New",Courier,monospace !important;
  position:relative;
  margin:0 0 1em;
}

pre .the-num {
  position:absolute;
  top:0;
  bottom:0;
  left:0;
  padding:0 1em;
  color:#999;
  background-color:#eee;
  border-right:2px solid #ccc;
}

pre .bracket   {color:darkblue;}
pre .tag,
pre .tag .keyword,
pre .tag .attribute {color:blue;}
pre .selector  {color:blue;}
pre .attribute,
pre .regexp    {color:darkorange;}
pre .str       {color:green;}
pre .tag .str  {color:brown;}
pre .keyword   {color:darkred;}
pre .comment   {font-style:italic;color:#999;}
pre .num,
pre .hex       {color:darkviolet;}
pre .name,
pre .important,
pre .array     {color:red;}
pre .important {background-color:yellow;}
pre .doctype   {color:magenta;}

Lihat Demo


Lainnya

Labels: , , , ,

47 Comments:

At Wednesday, June 13, 2012 at 5:04:00 PM GMT+7, Blogger Putra said...

Wah keyen, tambah satu lagi pak, double clik selection :D #benar begitu :/
pokoknya yang di double clik jadi keseleksi semua :)

 
At Wednesday, June 13, 2012 at 6:06:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Alam Perwira Bisa, tapi markup HTML-nya harus dimodifikasi lagi (pakai snippet kode yang pernah Saya tuliskan di sini).
Mengingat nomor urut baris kode berada di dalam tag <pre>, jadi saat tag PRE diklik ganda, nomor indikator baris kode di dalamnya malah ikut terseleksi. Solusinya adalah dengan membungkus elemen baru di dalam tag <pre> sebelum kita menyisipkan bar angka di bawahnya. Seperti ini:

$this.wrapInner('<div class="selectable"></div>').append('<div class="the-num"></div>');

Sehingga markupnya akan berubah menjadi seperti ini:

<pre>
<div class='selectable'>
...
...
...
</div>
<div class='the-num'> ... </div>
</pre>


Setelah itu cukup targetkan elemen .selectable sebagai daerah seleksi dan lupakan elemen .the-num:

$('pre').each(function() {
...
...

$this.wrapInner('<div class="selectable"></div>').append('<div class="the-num"></div>');

// Insert the line number
var num = $this.html().split(/\n|<br>/).length,
count = 0;
for (var i = 0; i < num; ++i) {
count = count + 1;
$this.find('.the-num').append(count + '.<br/>');
}
$this.css('padding-left', $this.find('.the-num').outerWidth() + 14);
}).attr('title', 'Klik ganda untuk menyeleksi semua kode!').find('.selectable').on("dblclick", function() {
var refNode = $(this)[0];
if ($.browser.msie) {
var range = document.body.createTextRange();
range.moveToElementText(refNode);
range.select();
} else if ($.browser.mozilla || $.browser.opera) {
var selection = window.getSelection();
var range = document.createRange();
range.selectNodeContents(refNode);
selection.removeAllRanges();
selection.addRange(range);
} else if ($.browser.safari) {
var selection = window.getSelection();
selection.setBaseAndExtent(refNode, 0, refNode, 1);
}
});


Demo: http://jsfiddle.net/tovic/7rKM8/5/

 
At Wednesday, June 13, 2012 at 6:48:00 PM GMT+7, Blogger Putra said...

@Taufik Nurrohman Alhamdulillah. Kesampaian juga make syntax higlighter :) thankyu pak Taufik. Baikk dehh <3
btw, gak nyangka jadi member aktif yeah.. =D

 
At Wednesday, June 13, 2012 at 7:31:00 PM GMT+7, Blogger Rosyd Aqbar said...

Untuk pemasanganya masih agak bingung nih bang Taufik, Bisa di jelasin gk ?
Syntax Highlighter cukup menarik bagi saya dan harus saya pelajari :D :-bd

 
At Wednesday, June 13, 2012 at 8:11:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Buka(n) Master ? Kalau bisa jangan memakai yang ini soalnya kurang akurat (cuma eksperimen). Saya membuat ini cuma untuk main-main saja :p
Lebih baik gunakan versi yang asli, yang lebih akurat. Cek di sini: Klik!
Rata-rata cara pemasangannya sama: CSS di dalam tag <style>, JavaScript di dalam tag <script> :W

 
At Wednesday, June 13, 2012 at 8:41:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Spenza-Sumpiuh Seperti yang Saya katakan ke mas Bukan Master di bawah, ada resikonya menggunakan ini karena Saya tidak mengetesnya lebih jauh dan ini hanya sebagai percobaan saja yang suatu saat mungkin akan Saya kembangkan lagi. Lebih baik gunakan versi yang sudah terkenal, bukan versi percobaan. Tapi kalau mau memasang highlighter buatan Saya bisa dengan cara meletakkan kode di dalam tag <style> untuk CSS kemudian letakkan di atas </head>, dan JQuery bisa diletakkan di dalam tag <script> kemudian letakkan di atas </body>. Kode di atas setidaknya baru cocok untuk tipe bahasa yang sederhana seperti CSS, JavaScript dan HTML. Selain itu tampilannya biasanya akan tampak berantakan dari segi warna. Hanya warnanya saja yang berantakan, tapi tidak akan merusak komposisi halaman. Bisa dilihat contohnya di sini:

http://4.bp.blogspot.com/-btFN1sI_Rnk/T9iX-_Nu5fI/AAAAAAAADXA/0HDv3pDM3Tc/s1600/tak-konsisten.png

Gambar di atas Saya ambil dari blognya mas Alam Perwira.
Kadang-kadang warnanya tidak konsisten :)

 
At Wednesday, June 13, 2012 at 10:39:00 PM GMT+7, Blogger Beben Koben said...

Udah baca komentar balasan saya blon!!!
gak usah capek bikin syntax highlighter...Ni syntaclet.com
wekekekkk :p

 
At Thursday, June 14, 2012 at 7:41:00 AM GMT+7, Blogger Taufik Nurrohman said...

@Beben Koben Buat sendiri lebih seru WEEEKEKEKKK!!!! :p
WEEEEEEEEEEEEEEEEEEEEEEKKKKKKKKKKKKKKKKK!!!!!!

 
At Thursday, June 14, 2012 at 1:15:00 PM GMT+7, Blogger Rosyd Aqbar said...

Sebenarnya saya sudah pasang, tapi fungsinya gk optimal, kadang muncul kadang enggak

 
At Thursday, June 14, 2012 at 4:34:00 PM GMT+7, Blogger uki said...

HUhahahha.... akhirnya dapat juga,siap-siap pake di blog akh...
Tq :D

 
At Thursday, June 14, 2012 at 5:20:00 PM GMT+7, Blogger uki said...

@Uqhi•° Ou iya,jika di template udah ada prenya,apakah harus di hapus ?

 
At Thursday, June 14, 2012 at 5:27:00 PM GMT+7, Blogger uki said...

knp di saya munculnya ini ?
Template Anda tidak dapat diparse karena tidak well-formed. Harap pastikan bahwa semua elemen XML ditutup dengan benar.
Pesan error XML: Element type "span" must be followed by either attribute specifications, ">" or "/>"

 
At Thursday, June 14, 2012 at 6:26:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Buka(n) Master ? Hmmm... Mungkin harus nunggu sampai loading halamannya selesai :\
Kalau yang dimaksud kode yang di atas, cukup ganti $(window).load(function() { dengan $(function() {

 
At Thursday, June 14, 2012 at 6:29:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Uqhi•° Nggak usah. Itu sudah otomatis menyeleksi tag <pre> =D

 
At Thursday, June 14, 2012 at 6:34:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Uqhi•° Jangan lupa sisipkan komentar //<![CDATA[ di dalam tag <script> seperti ini supaya Blogger tidak menolak:

<script type="text/javascript">
//<![CDATA[
...
//]]>
</script>


Selengkapnya: Penolakan-Penolakan Blogger terhadap JavaScript dan URL

 
At Thursday, June 14, 2012 at 7:58:00 PM GMT+7, Blogger uki said...

@Taufik Nurrohman Oke di coba , kang taufik

 
At Friday, June 15, 2012 at 3:08:00 AM GMT+7, Blogger Beben Koben said...

@Taufik Nurrohman yo wis wekkk wekkk deh!

 
At Friday, June 22, 2012 at 9:18:00 PM GMT+7, Blogger uki said...

ouiya kang taufik,kan biasanya tuh ada yang masang anti klik kanan dan CTRL+U dan sebagainya,cara buat supaya hanya di bagian blockquote yang bisa di copy gitu gmn ?

 
At Saturday, June 23, 2012 at 9:47:00 PM GMT+7, Blogger Bakteri said...

Coba ngetest dulu ea kak Taufic ^_^ belajar dulu agh JQuery

 
At Tuesday, June 26, 2012 at 11:36:00 AM GMT+7, Blogger Muhammad Irham said...

kalo yang dipakai kang taufik tutornya bijimane? ;)

 
At Saturday, June 30, 2012 at 6:52:00 PM GMT+7, Blogger Rosyd Aqbar said...

Om, Saya mengalami error nih, Saat di Double Click gk bisa ke Highlight :(
gimana nih :(

 
At Thursday, July 5, 2012 at 1:32:00 PM GMT+7, Blogger Bakteri said...

Bg Taufik Kalau yang ada toolbars nya itu gimana ea contohnya gini http://1.bp.blogspot.com/_7so4C0dWMLE/Sa7ofCq86DI/AAAAAAAAAFk/TE0y5fAJdcQ/s400/old.PNG
tolong donk ..! :P

 
At Sunday, July 8, 2012 at 12:50:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Muhammad Irham http://softwaremaniacs.org/soft/highlight/en/

 
At Sunday, July 8, 2012 at 12:56:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Buka(n) Master ? Mungkin itu pakai versi yang lama. Kalau versi yang baru bisa di dobel-klik. Coba cek situs http://tympanus.net/codrops
Dia juga make SyntaxHighlighter dari AlexGorbatchev.

 
At Sunday, July 8, 2012 at 12:59:00 PM GMT+7, Blogger Taufik Nurrohman said...

@edinofri Itu SyntaxHighlighter versi lama. Dulu dikasih toolbar soalnya kode yang sudah dikenai SyntaxHighlighter tidak bisa disalin (Baris-baris nomor ikut tersalin). Kalau versi yang sekarang sudah tidak ada toolbarnya.

 
At Sunday, July 8, 2012 at 3:23:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Uqhi•° Pakai saja .hover()
Pertama-tama set tag <body> dengan atribut berupa oncontextmenu='return false;' Ini adalah dasar untuk menonaktifkan klik kanan ⇒ baca di sini

Setelah itu kita gunakan .hover() untuk melepas atribut oncontextmenu saat pointer memasuki area <blockquote>, dan akan mengeset ulang atribut oncontextmenu saat pointer keluar dari <blockquote>:

$(function() {
$('body').attr('oncontextmenu', 'return false;'); // Set atribut klik kanan dengan nilai 'false'
// Saat pointer memasuki blockquote, hapus atribut klik kanan
// sebaliknya saat keluar, set kembali atribut klik kanan dengan nilai 'false'
$('blockquote').hover(function() {
$('body').removeAttr('oncontextmenu');
}, function() {
$('body').attr('oncontextmenu', 'return false;');
});
});


Saat pointer berada di luar area blockquote, klik kanan tidak bisa dilakukan karena atribut oncontextmenu='return false;' melarang kita melakukan aksi klik kanan, sebaliknya saat pointer memasuki daerah blockquote, klik kanan bisa dilakukan karena atribut oncontextmenu='return false;' sudah terhapus saat pointer masuk.

 
At Tuesday, July 10, 2012 at 9:58:00 AM GMT+7, Blogger Bakteri said...

Makasih ea Bg Taufik :-bd Banyak dapet pelajaran dari blog akang terutama dalam hal JQuery

 
At Wednesday, July 11, 2012 at 9:36:00 PM GMT+7, Blogger uki said...

@Taufik NurrohmanKok saya masih tdk bisa ya ?

 
At Wednesday, July 11, 2012 at 10:40:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Uqhi•° Tetooooooottt!!!! Anda belum beruntung.

 
At Thursday, July 12, 2012 at 1:03:00 PM GMT+7, Blogger uki said...

@Taufik Nurrohman Auu...... :'(
oiyua,.... script di atas di taruh di atas </head> kan ?

 
At Sunday, July 15, 2012 at 3:16:00 PM GMT+7, Blogger Putra said...

ada problem mas. Waktu ak doble clik, trus saya copy, pas dipaste hasilnya gak ada enternya, gak ada ganti baris :'(

 
At Sunday, July 15, 2012 at 4:02:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Alam Perwira Saya coba yang tanpa dobel-klik jadi, tapi yang memakai dobel-klik tidak jadi. Saya coba ubah karakter \n menjadi <br> dan karakter \s menjadi &nbsp; tetep nggak jadi. Mending jangan pakai dobel-klik, pakai cara biasa saja:

Demo: http://jsfiddle.net/tovic/7rKM8/12/embedded/result,js,css,html/

Oya, kode di atas sudah pernah Saya perbaharui pada CSS dan sedikit pada JQuery.

 
At Sunday, July 15, 2012 at 4:18:00 PM GMT+7, Blogger Putra said...

@Alam Perwira saya lepas saja deh doblecliknya. trus kalau semisal thnum(penomoran)nya dihilangkan caranya gmn? :\

 
At Sunday, July 15, 2012 at 6:39:00 PM GMT+7, Blogger Taufik Nurrohman said...

@Alam Perwira hapus kode ini:

$this.append('<div class="the-num"></div>');

// Insert the line number
var num = $this.html().split(/\n|<br>/).length,
count = 0;
for (var i = 0; i < num; i++) {
count = count + 1;
$this.find('.the-num').append(count + '.<br/>');
}
$this.css('padding-left', $this.find('.the-num').outerWidth()+14);


Demo: http://jsfiddle.net/tovic/7rKM8/13/

 
At Tuesday, December 18, 2012 at 11:26:00 PM GMT+7, Blogger Unknown said...

oia bang, pertanyaan saya hampir sama seperti @edinofri , cuman yang saya mo tanyain gimana caranya nerapin disetiap nomornya/garis baru warnanya berubah-ubah di tutor syntax versi abang tofik??, contoh gambar

http://3.bp.blogspot.com/-b08njTy7qpo/UGfSPb1tUhI/AAAAAAAACII/otkMgoYp79c/s1600/syntax+highlighter.PNG

 
At Wednesday, December 19, 2012 at 8:06:00 PM GMT+7, Blogger Taufik Nurrohman said...

/2012/04/make-automatic-numbering-system-on-each.html

 
At Tuesday, September 17, 2013 at 9:20:00 PM GMT+7, Blogger Unknown said...

makasih sebelumnya atas trik nya kang, trik diatas berhasil saya praktekan pada pointer pre dan code, nah yang ingin saya tanyakan, jika ingin menambahkan fungsion selain .hover gimana caranya kang ....? misal pada halaman comen tetap bisa di copy gitu ..?

 
At Thursday, June 26, 2014 at 4:11:00 AM GMT+7, Anonymous Anonymous said...

wah ada profesor nih :D eksperimennya berhasil \o/
makasih kang...

 
At Thursday, November 27, 2014 at 1:29:00 AM GMT+7, Blogger Ressa said...

bagus nih , kode pemanggil untuk postingnya apa kang ?

 
At Thursday, February 5, 2015 at 8:53:00 PM GMT+7, Blogger Satriyo Katrox said...

mantap nih..inovasi baru syntax..tapi buat yang malas kaya saya cuma pake blockquote

salam admin satriyoku

 
At Sunday, May 21, 2017 at 4:40:00 PM GMT+7, Blogger ApiIslam said...

bagus bangett mas...

cara agar bisa menyorot sebagian script penting di dalam tag pre gimana mas?

 
At Sunday, May 21, 2017 at 8:36:00 PM GMT+7, Blogger Taufik Nurrohman said...

Eksperimen ini sudah tidak diperbaharui. Coba versi yang lebih stabil di sini → https://github.com/tovic/generic-syntax-highlighter

Untuk menandai kode yang penting bisa memakai elemen HTML <mark>.

 
At Saturday, April 25, 2020 at 7:31:00 PM GMT+7, Blogger Mas Kolektor said...

gan, agar numbering mengikuti jumlah baris dari isi pre yang di text wrapping gimana ya gan ? krn sudah coba edit css "white space:pre-wrap + word-wrap:break-word" numberingnya tidak mau otomatis mengikuti jumlah baris, mohon bantuannya gan :D

 
At Monday, April 27, 2020 at 4:12:00 PM GMT+7, Blogger Taufik Nurrohman said...

Iya nggak bisa karena di sini Saya pakai float. Bakalan beda ceritanya kalau tiap baris dipisahkan oleh elemen <div>.

 
At Saturday, May 2, 2020 at 1:32:00 PM GMT+7, Blogger Mas Kolektor said...

sip gan, jadi makin ribet ya kalo gitu, btw #OOT ada artikel yang membahas double click select didalam element div class atau div id kah gan ? kalo ada boleh lihat artikelnya ?

 
At Saturday, May 2, 2020 at 5:37:00 PM GMT+7, Blogger Taufik Nurrohman said...

/2013/01/javascript-seleksi-teks-otomatis.html

 
At Thursday, June 4, 2020 at 9:51:00 PM GMT+7, Blogger Zona Kode Web said...

ada solusi buat max-height tapi background dari penomoran gak ngikut sampai scroll mentok kebawah min? backgroundnya kepotong

 

Post a Comment

<< Home