10. html/シンタックスハイライト/SyntaxHighlighter/全角文字を強調表示する

 
 さてまだ前回の続きだ。
10.1 何がしたいか
10.2 キーワードの登録
10.3 全角文字を検出する関数を記述
10.4 ハイライトさせる処理を追加
10.5 スタイルシートの定義
10.6 確認

10.1 何がしたいか

 ここは説明書きが多いので、今まで <pre> タグと <span> タグと CSS とを駆使して
ServerTokens ProductOnly <span class="in">← クライアントに返信するヘッダ内の apache の情報を最小限にする         ※1</span>
ServerSignature Off      <span class="in">← サーバエラー発生時にブラウザにサーバアドレス・ポート番号を表示しない ※2</span>
HostnameLookups On       <span class="in">← クライアントのIPアドレスをドメイン名を変換してログに記録する         ※3</span>

 てな風に記述したら、下記のように表示されるようにして

ServerTokens ProductOnly ← クライアントに返信するヘッダ内の apache の情報を最小限にする        ※1
ServerSignature Off      ← サーバエラー発生時にブラウザにサーバアドレス・ポート番号を表示しない ※2
HostnameLookups On       ← クライアントのIPアドレスをドメイン名を変換してログに記録する        ※3
 例題に説明をつけるようにしていたのだが。  SyntaxHighlighter を使用すると、例文内のタグがエスケープされるために、下記のように表示されるようになっちゃったのです。
ServerTokens ProductOnly ← クライアントに返信するヘッダ内の apache の情報を最小限にする        ※1
ServerSignature Off      ← サーバエラー発生時にブラウザにサーバアドレス・ポート番号を表示しない ※2
HostnameLookups On       ← クライアントのIPアドレスをドメイン名を変換してログに記録する        ※3

 なんとか今までのような表記ができんかいなと「11.9 キーワードをテンポラリに定義する」という形にしたのですが。

 これではアルファベット表記のものは強調表示できますが、全角文字はキーワードとして引っかからないのだ。
 そこで思いついたのが、正規表現で全角文字を検出できたら、それをタグ付けできんかいな・・・と。

10.2 キーワードの登録

 プロパティ名を zenkaku としておきます。ここは既に定義されている変数名やプロパティ名と重複していなければなんでもよいです。  すべての言語に適用できるように shCore.js を編集します。
		/** Gets or sets light mode. Equavalent to turning off gutter and toolbar. */
		'light' : false,

		'html-script' : false

    

		/** Gets or sets light mode. Equavalent to turning off gutter and toolbar. */
		'light' : false,

		/*	全角を強調表示するか	*/
		'zenkaku' : true,

		'html-script' : false

 デフォルトで全角を強調表示にして、「zenkaku: false;」と記述すれば全角文字でも強調表示しないようにしました。

10.3 全角文字を検出する関数を記述

 shCore.js が続きます。  全角文字を検出するってのが難問でした。

 が参考になりました。結局、UTF-8 でないとだめなのですが

	/** Common regular expressions. */
	regexLib : {
		multiLineCComments			: /¥/¥*[¥s¥S]*?¥*¥//gm,
		singleLineCComments			: /¥/¥/.*$/gm,
		singleLinePerlComments		: /#.*$/gm,
		doubleQuotedString			: /"([^¥¥"¥n]|¥¥.)*"/g,
		singleQuotedString			: /'([^¥¥'¥n]|¥¥.)*'/g,
		multiLineDoubleQuotedString	: new XRegExp('"([^¥¥¥¥"]|¥¥¥¥.)*"', 'gs'),
		multiLineSingleQuotedString	: new XRegExp("'([^¥¥¥¥']|¥¥¥¥.)*'", 'gs'),
		xmlComments					: /(&lt;|<)!--[¥s¥S]*?--(&gt;|>)/gm,
		url							: /¥w+:¥/¥/[¥w-.¥/?%&=:@;]*/g,

		/** <?= ?> tags. */
		phpScriptTags 				: { left: /(&lt;|<)¥?=?/g, right: /¥?(&gt;|>)/g },

		/** <%= %> tags. */
		aspScriptTags				: { left: /(&lt;|<)%=?/g, right: /%(&gt;|>)/g },

		/** <script></script> tags. */
		scriptScriptTags			: { left: /(&lt;|<)¥s*script.*?(&gt;|>)/gi, right: /(&lt;|<)¥/¥s*script¥s*(&gt;|>)/gi }
	},

    

	/** Common regular expressions. */
	regexLib : {
		multiLineCComments			: /¥/¥*[¥s¥S]*?¥*¥//gm,
		singleLineCComments			: /¥/¥/.*$/gm,
		singleLinePerlComments		: /#.*$/gm,
		doubleQuotedString			: /"([^¥¥"¥n]|¥¥.)*"/g,
		singleQuotedString			: /'([^¥¥'¥n]|¥¥.)*'/g,
		multiLineDoubleQuotedString	: new XRegExp('"([^¥¥¥¥"]|¥¥¥¥.)*"', 'gs'),
		multiLineSingleQuotedString	: new XRegExp("'([^¥¥¥¥']|¥¥¥¥.)*'", 'gs'),
		xmlComments					: /(&lt;|<)!--[¥s¥S]*?--(&gt;|>)/gm,
		url							: /¥w+:¥/¥/[¥w-.¥/?%&=:@;]*/g,

		zenkakuString				: /[′-※]|[℁-⇿]|[①-⓪]|[■-◯]|[、-㿿]|[一-龠][!-○]/gm,

		/** <?= ?> tags. */
		phpScriptTags 				: { left: /(&lt;|<)¥?=?/g, right: /¥?(&gt;|>)/g },

		/** <%= %> tags. */
		aspScriptTags				: { left: /(&lt;|<)%=?/g, right: /%(&gt;|>)/g },

		/** <script></script> tags. */
		scriptScriptTags			: { left: /(&lt;|<)¥s*script.*?(&gt;|>)/gi, right: /(&lt;|<)¥/¥s*script¥s*(&gt;|>)/gi }
	},

 「/[′-※]|[℁-⇿]|[①-⓪]|[■-◯]|[、-㿿]|[一-龠][!-○]/gm」の箇所がみそで、まだ漏れがあるかもしれません。
 漏れがあったら追加していこうと思います。

10.4 ハイライトさせる処理を追加

 まだ、shCore.js を修正します。
	init: function(params)
	{
		this.id = guid();

		// register this instance in the highlighters list
		storeHighlighter(this);

		// local params take precedence over defaults
		this.params = merge(sh.defaults, params || {})

		// process light mode
		if (this.getParam('light') == true)
			this.params.toolbar = this.params.gutter = false;
	},

    

	init: function(params)
	{
		this.id = guid();

		// register this instance in the highlighters list
		storeHighlighter(this);

		// local params take precedence over defaults
		this.params = merge(sh.defaults, params || {})

		//	全角強調表示であれば
		if (this.params.zenkaku == true)
		{
			if (this.regexList != null)
			{
				this.regexList.push({ regex: SyntaxHighlighter.regexLib.zenkakuString,		css: 'zenkaku' });
			}
			else
			{
				this.regexList =
					[
						{ regex: SyntaxHighlighter.regexLib.zenkakuString,		css: 'zenkaku' }
					];
			}
		}

		// process light mode
		if (this.getParam('light') == true)
			this.params.toolbar = this.params.gutter = false;
	},

 1659~1673行を追加しています。

10.5 スタイルシートの定義

 スタイルシートに zenkaku のプロパティを定義します。
.syntaxhighlighter .zenkaku
{
    color: #00C000 !important;
    font-weight: bold !important;
	font-family: monospace !important;
}

 フォントや色はもちろんお好みで・・・。

10.6 確認

 さてその結果
<pre class="brush: html;">
ServerTokens ProductOnly ← クライアントに返信するヘッダ内の apache の情報を最小限にする         ※1
ServerSignature Off      ← サーバエラー発生時にブラウザにサーバアドレス・ポート番号を表示しない ※2
HostnameLookups On       ← クライアントのIPアドレスをドメイン名を変換してログに記録する         ※3
</pre>

 と記述して

ServerTokens ProductOnly ← クライアントに返信するヘッダ内の apache の情報を最小限にする         ※1
ServerSignature Off      ← サーバエラー発生時にブラウザにサーバアドレス・ポート番号を表示しない ※2
HostnameLookups On       ← クライアントのIPアドレスをドメイン名を変換してログに記録する         ※3

 てな感じで表示されるようになりました。

 これに前項の keyword2 をからめて

ServerTokens ProductOnly ← クライアントに返信するヘッダ内の apache の情報を最小限にする         ※1
ServerSignature Off      ← サーバエラー発生時にブラウザにサーバアドレス・ポート番号を表示しない ※2
HostnameLookups On       ← クライアントのIPアドレスをドメイン名を変換してログに記録する         ※3

 ほぼ思い通りになりました。

 で、以下で全角コードの確認なのだ。

○◎△▽▲▼□■◇◆
⓪①②③④⑤⑥⑦⑧⑨⑩⑪⑫⑬⑭⑮⑯⑰⑱⑲⑳㉑㉒㉓㉔㉕
↑→↓←
略