1+ ( function ( ) {
2+
3+ if ( typeof Prism === 'undefined' || typeof document === 'undefined' ) {
4+ return ;
5+ }
6+
7+ // Copied from the markup language definition
8+ var HTML_TAG = / < \/ ? (? ! \d ) [ ^ \s > \/ = $ < % ] + (?: \s (?: \s * [ ^ \s > \/ = ] + (?: \s * = \s * (?: " [ ^ " ] * " | ' [ ^ ' ] * ' | [ ^ \s ' " > = ] + (? = [ \s > ] ) ) | (? = [ \s / > ] ) ) ) + ) ? \s * \/ ? > / g;
9+
10+ // a regex to validate hexadecimal colors
11+ var HEX_COLOR = / ^ # ? ( (?: [ \d a - f ] ) { 3 , 4 } | (?: [ \d a - f ] { 2 } ) { 3 , 4 } ) $ / i;
12+
13+ /**
14+ * Parses the given hexadecimal representation and returns the parsed RGBA color.
15+ *
16+ * If the format of the given string is invalid, `undefined` will be returned.
17+ * Valid formats are: `RGB`, `RGBA`, `RRGGBB`, and `RRGGBBAA`.
18+ *
19+ * Hexadecimal colors are parsed because they are not fully supported by older browsers, so converting them to
20+ * `rgba` functions improves browser compatibility.
21+ *
22+ * @param {string } hex
23+ * @returns {string | undefined }
24+ */
25+ function parseHexColor ( hex ) {
26+ var match = HEX_COLOR . exec ( hex ) ;
27+ if ( ! match ) {
28+ return undefined ;
29+ }
30+ hex = match [ 1 ] ; // removes the leading "#"
31+
32+ // the width and number of channels
33+ var channelWidth = hex . length >= 6 ? 2 : 1 ;
34+ var channelCount = hex . length / channelWidth ;
35+
36+ // the scale used to normalize 4bit and 8bit values
37+ var scale = channelWidth == 1 ? 1 / 15 : 1 / 255 ;
38+
39+ // normalized RGBA channels
40+ var channels = [ ] ;
41+ for ( var i = 0 ; i < channelCount ; i ++ ) {
42+ var int = parseInt ( hex . substr ( i * channelWidth , channelWidth ) , 16 ) ;
43+ channels . push ( int * scale ) ;
44+ }
45+ if ( channelCount == 3 ) {
46+ channels . push ( 1 ) ; // add alpha of 100%
47+ }
48+
49+ // output
50+ var rgb = channels . slice ( 0 , 3 ) . map ( function ( x ) {
51+ return String ( Math . round ( x * 255 ) ) ;
52+ } ) . join ( ',' ) ;
53+ var alpha = String ( Number ( channels [ 3 ] . toFixed ( 3 ) ) ) ; // easy way to round 3 decimal places
54+
55+ return 'rgba(' + rgb + ',' + alpha + ')' ;
56+ }
57+
58+ /**
59+ * Validates the given Color using the current browser's internal implementation.
60+ *
61+ * @param {string } color
62+ * @returns {string | undefined }
63+ */
64+ function validateColor ( color ) {
65+ var s = new Option ( ) . style ;
66+ s . color = color ;
67+ return s . color ? color : undefined ;
68+ }
69+
70+ /**
71+ * An array of function which parse a given string representation of a color.
72+ *
73+ * These parser serve as validators and as a layer of compatibility to support color formats which the browser
74+ * might not support natively.
75+ *
76+ * @type {((value: string) => (string|undefined))[] }
77+ */
78+ var parsers = [
79+ parseHexColor ,
80+ validateColor
81+ ] ;
82+
83+
84+ Prism . hooks . add ( 'wrap' , function ( env ) {
85+ if ( env . type === 'color' || env . classes . indexOf ( 'color' ) >= 0 ) {
86+ var content = env . content ;
87+
88+ // remove all HTML tags inside
89+ var rawText = content . split ( HTML_TAG ) . join ( '' ) ;
90+
91+ var color ;
92+ for ( var i = 0 , l = parsers . length ; i < l && ! color ; i ++ ) {
93+ color = parsers [ i ] ( rawText ) ;
94+ }
95+
96+ if ( ! color ) {
97+ return ;
98+ }
99+
100+ var previewElement = '<span class="inline-color-wrapper"><span class="inline-color" style="background-color:' + color + ';"></span></span>' ;
101+ env . content = previewElement + content ;
102+ }
103+ } ) ;
104+
105+ } ( ) ) ;
0 commit comments