Cambiar do deseño da paxina de Inicio a CSS vainilla sen bootstrap.

This commit is contained in:
Laegnur 2024-09-20 14:24:47 +02:00
parent b25e0b12c6
commit c625004522
Signed by: laegnur
GPG key ID: F8FE83A0B2D932A3
190 changed files with 2727 additions and 137584 deletions

View file

Before

Width:  |  Height:  |  Size: 11 KiB

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 22 KiB

View file

@ -0,0 +1,49 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg xmlns="http://www.w3.org/2000/svg" xmlns:svg="http://www.w3.org/2000/svg" width="519.99939" height="381.21799" viewBox="0 0 137.58317 100.86392" version="1.1" id="svg1">
<defs id="defs1"></defs>
<g id="Capa_1" transform="matrix(0.80698679,0,0,0.80698679,-171.40399,-289.27384)">
<g id="g224">
<g id="g176">
<path class="st0" d="m 262.02,378.78 c -0.68,3.06 -2.09,5.83 -4.23,8.31 -2.14,2.48 -4.64,4.54 -7.5,6.17 -2.86,1.63 -5.88,2.75 -9.08,3.37 -3.2,0.61 -6.22,0.55 -9.08,-0.2 -0.95,2.38 -1.73,4.45 -2.35,6.22 -0.62,1.77 -0.85,2.92 -0.71,3.47 v 0.61 c 0,0.41 0.1,0.82 0.31,1.22 0.14,0.34 0.07,0.68 -0.2,1.02 -0.27,0.34 -0.65,0.34 -1.12,0 -0.2,-0.14 -0.53,-0.44 -0.97,-0.92 -0.44,-0.48 -0.83,-1.12 -1.17,-1.94 -0.34,-0.82 -0.56,-1.79 -0.66,-2.91 -0.1,-1.12 0.05,-2.46 0.46,-4.03 0.14,-0.68 0.36,-1.44 0.66,-2.29 0.31,-0.85 0.66,-1.82 1.07,-2.91 -0.95,-0.88 -1.79,-2.11 -2.5,-3.67 -0.71,-1.56 -0.87,-3.6 -0.46,-6.12 0.34,-2.24 1.21,-4.3 2.6,-6.17 1.39,-1.87 2.89,-3.47 4.49,-4.79 1.6,-1.33 3.08,-2.4 4.44,-3.21 1.36,-0.82 2.21,-1.29 2.55,-1.43 0.61,-0.27 1.31,-0.46 2.09,-0.56 0.78,-0.1 1.38,-0.05 1.78,0.15 0.34,0.14 0.61,0.6 0.82,1.38 0.2,0.78 -0.04,1.92 -0.71,3.42 -0.95,2.18 -1.97,4.39 -3.06,6.63 -0.95,1.97 -1.97,4.18 -3.06,6.63 -1.09,2.45 -2.11,4.86 -3.06,7.24 l 1.63,0.31 c 2.24,0.27 4.5,-0.02 6.78,-0.87 2.28,-0.85 4.4,-2.06 6.38,-3.62 1.97,-1.56 3.69,-3.37 5.15,-5.41 1.46,-2.04 2.53,-4.15 3.21,-6.32 0.54,-1.7 0.61,-3.54 0.2,-5.51 -0.41,-1.97 -1.24,-3.77 -2.5,-5.41 -1.26,-1.63 -2.92,-3.01 -5,-4.13 -2.08,-1.12 -4.5,-1.75 -7.29,-1.89 -2.31,-0.07 -4.73,0.25 -7.24,0.97 -2.52,0.71 -4.93,1.77 -7.24,3.16 -2.31,1.39 -4.35,3.04 -6.12,4.95 -1.77,1.9 -3.06,4.01 -3.88,6.32 -0.2,0.75 -0.24,1.46 -0.1,2.14 0.14,0.68 0.36,1.28 0.66,1.79 0.3,0.51 0.65,0.95 1.02,1.33 0.37,0.37 0.66,0.6 0.87,0.66 l 0.2,0.1 h 0.1 v 0.1 c 0,0.14 -0.04,0.27 -0.1,0.41 -0.07,0.14 -0.14,0.27 -0.2,0.41 -0.14,0.14 -0.24,0.27 -0.31,0.41 -0.75,0.82 -1.46,1.26 -2.14,1.33 -0.68,0.07 -1.29,-0.03 -1.84,-0.31 -0.61,-0.27 -1.19,-0.75 -1.73,-1.43 -0.82,-1.09 -1.21,-2.26 -1.17,-3.52 0.03,-1.26 0.29,-2.46 0.76,-3.62 0.48,-1.16 1.04,-2.21 1.68,-3.16 0.65,-0.95 1.17,-1.67 1.58,-2.14 0.88,-0.88 2.12,-2.04 3.72,-3.47 1.6,-1.43 3.55,-2.8 5.87,-4.13 2.31,-1.33 4.91,-2.43 7.8,-3.31 2.89,-0.88 6.07,-1.26 9.54,-1.12 3.81,0.14 7.02,0.8 9.64,1.99 2.62,1.19 4.67,2.72 6.17,4.59 1.5,1.87 2.45,4 2.86,6.38 0.4,2.37 0.3,4.82 -0.31,7.33 z m -33.97,1.63 c -0.48,0.75 -0.85,1.6 -1.12,2.55 -0.27,0.95 -0.41,1.92 -0.41,2.91 0,0.99 0.15,1.96 0.46,2.91 0.31,0.95 0.83,1.84 1.58,2.65 0.82,-1.97 1.68,-4.04 2.6,-6.22 0.92,-2.17 1.75,-4.15 2.5,-5.92 0.88,-2.11 1.8,-4.11 2.75,-6.02 0.14,-0.2 0.24,-0.44 0.31,-0.71 0.14,-0.48 0.07,-0.68 -0.2,-0.61 -0.07,0 -0.41,0.24 -1.02,0.71 -0.61,0.48 -1.36,1.11 -2.24,1.89 -0.88,0.78 -1.8,1.68 -2.75,2.7 -0.96,1.02 -1.78,2.08 -2.46,3.16 z" id="path148" style="fill:#00a099"></path>
<path class="st0" d="m 275.58,395.1 c 0.14,0.07 0.29,0.25 0.46,0.56 0.17,0.31 -0.05,0.83 -0.66,1.58 -1.16,1.43 -2.31,2.67 -3.47,3.72 -1.16,1.06 -1.9,1.75 -2.24,2.09 -0.95,0.68 -1.75,1.07 -2.4,1.17 -0.65,0.1 -1.14,0.12 -1.48,0.05 -0.61,0 -1.11,-0.17 -1.48,-0.51 -0.37,-0.34 -0.65,-0.78 -0.82,-1.33 -0.17,-0.54 -0.25,-1.1 -0.25,-1.68 0,-0.58 0.03,-1.14 0.1,-1.68 0,-0.14 0.03,-0.34 0.1,-0.61 0.07,-0.27 0.13,-0.54 0.2,-0.82 0.07,-0.27 0.13,-0.54 0.2,-0.82 v 0.1 c 0.34,-1.29 0.82,-2.74 1.43,-4.33 0.61,-1.6 1.46,-3.42 2.55,-5.46 0.07,-0.27 0.2,-0.54 0.41,-0.82 0.13,-0.27 0.31,-0.56 0.51,-0.87 0.2,-0.31 0.41,-0.63 0.61,-0.97 -0.68,0.14 -1.33,0.24 -1.94,0.31 -0.61,0.07 -1.19,0.14 -1.73,0.2 -0.34,0.07 -0.65,0.1 -0.92,0.1 -0.27,0 -0.58,0.04 -0.92,0.1 -0.48,1.7 -1.05,3.26 -1.73,4.69 -0.68,1.43 -1.38,2.7 -2.09,3.83 -0.71,1.12 -1.41,2.09 -2.09,2.91 -0.68,0.82 -1.22,1.46 -1.63,1.94 -0.41,0.41 -0.71,0.54 -0.92,0.41 -0.13,0 -0.27,-0.07 -0.41,-0.2 -0.27,-0.27 -0.34,-0.51 -0.2,-0.71 0,-0.14 0.07,-0.27 0.2,-0.41 0.75,-0.82 1.85,-2.24 3.32,-4.28 1.47,-2.04 2.7,-4.62 3.72,-7.75 0.07,-0.07 0.1,-0.17 0.1,-0.31 h -0.1 c -0.27,0.07 -0.6,0.12 -0.97,0.15 -0.37,0.04 -0.76,0.02 -1.17,-0.05 -0.68,-0.07 -1.28,-0.24 -1.79,-0.51 -0.51,-0.27 -0.8,-0.75 -0.87,-1.43 0,-1.02 0.2,-1.87 0.61,-2.55 0.41,-0.68 0.88,-1.22 1.43,-1.63 0.54,-0.41 1.1,-0.7 1.68,-0.87 0.58,-0.17 1,-0.29 1.27,-0.36 h 0.1 c 0.68,-0.14 1.21,-0.07 1.58,0.2 0.37,0.27 0.63,0.61 0.76,1.02 0.2,0.48 0.27,1.02 0.2,1.63 0,0.34 -0.07,0.85 -0.2,1.53 l -0.1,0.61 c 1.22,-0.14 2.45,-0.37 3.67,-0.71 1.22,-0.34 2.07,-0.58 2.55,-0.71 h 0.2 0.51 c 0.34,0.14 0.78,0.34 1.33,0.61 0.54,0.27 1.04,0.61 1.48,1.02 0.44,0.41 0.77,0.85 0.97,1.33 0.2,0.48 0.17,0.99 -0.1,1.53 -0.48,0.88 -1.27,2.26 -2.4,4.13 -1.12,1.87 -2.13,3.79 -3.01,5.76 -0.14,0.27 -0.34,0.75 -0.61,1.43 -0.54,1.16 -0.97,2.14 -1.28,2.96 -0.31,0.82 -0.39,1.29 -0.25,1.43 0.2,0 0.37,-0.03 0.51,-0.1 0.34,-0.14 0.82,-0.44 1.43,-0.92 0.61,-0.48 1.24,-1.04 1.89,-1.68 0.65,-0.65 1.29,-1.31 1.94,-1.99 0.65,-0.68 1.14,-1.26 1.48,-1.73 l 0.2,-0.2 c 0.16,-0.13 0.33,-0.17 0.53,-0.1 z m -17.03,-13.36 c 0,-0.07 0.17,-0.36 0.51,-0.87 0.34,-0.51 0.88,-1 1.63,-1.48 l 1.22,-0.71 -1.43,0.51 c -0.41,0.14 -0.75,0.34 -1.02,0.61 -0.27,0.2 -0.53,0.46 -0.76,0.77 -0.24,0.31 -0.39,0.66 -0.46,1.07 l -0.1,0.92 z m 3.77,-1.94 c -0.14,0.14 -0.31,0.34 -0.51,0.61 -0.2,0.27 -0.39,0.58 -0.56,0.92 -0.17,0.34 -0.25,0.66 -0.25,0.97 0,0.31 0.1,0.53 0.31,0.66 0.41,0.27 0.92,0.38 1.53,0.31 0.34,-1.29 0.47,-2.14 0.41,-2.55 0,-0.27 -0.07,-0.53 -0.2,-0.77 -0.15,-0.23 -0.39,-0.28 -0.73,-0.15 z" id="path150" style="fill:#00a099"></path>
<path class="st0" d="m 275.38,391.84 c 0.88,-1.43 1.87,-2.79 2.96,-4.08 1.09,-1.29 2.14,-2.38 3.16,-3.26 1.02,-0.88 1.99,-1.51 2.91,-1.89 0.92,-0.37 1.68,-0.36 2.29,0.05 0.61,0.41 1.17,0.8 1.68,1.17 0.51,0.38 0.93,0.7 1.27,0.97 0.41,0.27 0.78,0.55 1.12,0.82 0.14,-0.41 0.31,-0.78 0.51,-1.12 0.13,-0.34 0.25,-0.68 0.36,-1.02 0.1,-0.34 0.15,-0.65 0.15,-0.92 0,-0.07 0.03,-0.14 0.1,-0.2 l 0.2,-0.2 c 0.2,0 0.48,0.1 0.82,0.31 0.41,0.2 0.85,0.51 1.33,0.92 0.47,0.41 0.92,0.87 1.33,1.38 0.41,0.51 0.68,1.04 0.82,1.58 0.14,0.54 0.03,1.12 -0.31,1.73 -0.41,0.75 -1,1.9 -1.79,3.47 -0.78,1.57 -1.55,3.15 -2.29,4.74 -0.75,1.6 -1.36,3.03 -1.84,4.28 -0.48,1.26 -0.61,1.96 -0.41,2.09 0.14,0.14 0.51,-0.02 1.12,-0.46 0.61,-0.44 1.31,-1.02 2.09,-1.73 0.78,-0.71 1.53,-1.46 2.24,-2.24 0.71,-0.78 1.27,-1.44 1.68,-1.99 0,-0.07 0.07,-0.14 0.2,-0.2 0.2,-0.2 0.41,-0.24 0.61,-0.1 0.14,0.07 0.27,0.25 0.41,0.56 0.13,0.31 -0.1,0.83 -0.71,1.58 -1.16,1.43 -2.31,2.67 -3.47,3.72 -1.16,1.05 -1.9,1.75 -2.24,2.09 -0.95,0.68 -1.73,1.07 -2.35,1.17 -0.61,0.1 -1.09,0.12 -1.43,0.05 -1.22,-0.2 -1.99,-0.75 -2.29,-1.63 -0.31,-0.88 -0.39,-1.9 -0.25,-3.06 0.13,-1.16 0.46,-2.38 0.97,-3.67 0.51,-1.29 0.97,-2.41 1.38,-3.37 -0.75,0.88 -1.62,1.89 -2.6,3.01 -0.99,1.12 -1.97,2.21 -2.96,3.26 -0.99,1.05 -1.87,2.01 -2.65,2.86 -0.78,0.85 -1.28,1.41 -1.48,1.68 -0.41,0.47 -1.19,0.54 -2.35,0.2 -1.16,-0.34 -2.04,-0.88 -2.65,-1.63 -0.61,-0.68 -0.78,-2 -0.51,-3.98 0.28,-1.98 1.24,-4.29 2.87,-6.94 z m 3.67,7.75 c 0.61,-0.41 1.51,-1.27 2.7,-2.6 1.19,-1.33 2.36,-2.7 3.52,-4.13 1.36,-1.7 2.86,-3.5 4.49,-5.41 -0.95,-0.61 -1.89,-0.71 -2.8,-0.31 -0.91,0.4 -1.68,0.99 -2.29,1.73 -0.61,0.75 -1.55,2.01 -2.81,3.77 -1.26,1.77 -2.33,3.61 -3.21,5.51 -0.34,0.61 -0.46,1.04 -0.36,1.28 0.1,0.24 0.22,0.36 0.36,0.36 0.14,0 0.24,-0.03 0.31,-0.1 0.05,0 0.09,-0.03 0.09,-0.1 z" id="path152" style="fill:#00a099"></path>
<path class="st0" d="m 296.29,403.06 c -0.34,-0.48 -0.49,-1.16 -0.46,-2.04 0.04,-0.88 0.17,-1.87 0.41,-2.96 0.24,-1.09 0.56,-2.24 0.97,-3.47 0.41,-1.22 0.85,-2.45 1.33,-3.67 1.09,-2.79 2.45,-5.81 4.08,-9.08 0.07,-0.13 0.1,-0.22 0.1,-0.25 0,-0.03 0.03,-0.12 0.1,-0.25 0,-0.07 0.07,-0.14 0.2,-0.2 0.2,-0.07 0.51,-0.07 0.92,0 0.41,0.2 0.83,0.51 1.28,0.92 0.44,0.41 0.83,0.87 1.17,1.38 0.34,0.51 0.56,1.07 0.66,1.68 0.1,0.61 0.02,1.16 -0.25,1.63 -0.41,0.88 -1.12,2.16 -2.14,3.83 -1.02,1.67 -1.9,3.49 -2.65,5.46 -0.34,0.54 -0.55,1.02 -0.61,1.43 -0.48,1.16 -0.83,2.14 -1.07,2.96 -0.24,0.82 -0.29,1.29 -0.15,1.43 h 0.41 c 0.34,-0.13 0.8,-0.46 1.38,-0.97 0.58,-0.51 1.19,-1.09 1.84,-1.73 0.65,-0.65 1.26,-1.31 1.84,-1.99 0.58,-0.68 1.07,-1.26 1.48,-1.73 l 0.2,-0.2 c 0.07,-0.07 0.24,-0.1 0.51,-0.1 0.2,0.07 0.37,0.27 0.51,0.61 0.14,0.34 -0.1,0.88 -0.71,1.63 -1.02,1.36 -2.09,2.57 -3.21,3.62 -1.12,1.06 -1.89,1.75 -2.29,2.09 -0.88,0.68 -1.63,1.07 -2.24,1.17 -0.61,0.1 -1.09,0.12 -1.43,0.05 h -0.1 c -0.27,0 -0.54,-0.1 -0.82,-0.31 -0.58,-0.23 -0.99,-0.54 -1.26,-0.94 z M 307.3,374.8 c 0.75,0.34 1.43,0.99 2.04,1.94 0.61,0.95 0.65,1.94 0.1,2.96 -0.14,0.27 -0.24,0.51 -0.31,0.71 -0.07,0.2 -0.27,0.58 -0.61,1.12 -0.14,0.27 -0.44,0.41 -0.92,0.41 -0.2,0 -0.41,-0.07 -0.61,-0.2 -0.14,-0.14 -0.41,-0.39 -0.82,-0.76 -0.41,-0.37 -0.78,-0.7 -1.12,-0.97 -0.54,-0.41 -0.78,-0.85 -0.71,-1.33 0.27,-0.48 0.56,-1.05 0.87,-1.73 0.31,-0.68 0.63,-1.36 0.97,-2.04 0,-0.07 0.07,-0.14 0.2,-0.2 0.21,-0.15 0.51,-0.11 0.92,0.09 z" id="path154" style="fill:#00a099"></path>
<path class="st0" d="m 308.02,391.84 c 0.88,-1.43 1.87,-2.79 2.96,-4.08 1.09,-1.29 2.14,-2.38 3.16,-3.26 1.02,-0.88 1.99,-1.51 2.91,-1.89 0.92,-0.37 1.68,-0.36 2.29,0.05 0.61,0.41 1.17,0.8 1.68,1.17 0.51,0.38 0.93,0.7 1.27,0.97 0.41,0.27 0.78,0.55 1.12,0.82 0.14,-0.41 0.31,-0.78 0.51,-1.12 0.13,-0.34 0.25,-0.68 0.36,-1.02 0.1,-0.34 0.15,-0.65 0.15,-0.92 0,-0.07 0.03,-0.14 0.1,-0.2 l 0.2,-0.2 c 0.2,0 0.48,0.1 0.82,0.31 0.41,0.2 0.85,0.51 1.33,0.92 0.47,0.41 0.92,0.87 1.33,1.38 0.41,0.51 0.68,1.04 0.82,1.58 0.14,0.54 0.03,1.12 -0.31,1.73 -0.41,0.75 -1,1.9 -1.79,3.47 -0.78,1.57 -1.55,3.15 -2.29,4.74 -0.75,1.6 -1.36,3.03 -1.84,4.28 -0.48,1.26 -0.61,1.96 -0.41,2.09 0.14,0.14 0.51,-0.02 1.12,-0.46 0.61,-0.44 1.31,-1.02 2.09,-1.73 0.78,-0.71 1.53,-1.46 2.24,-2.24 0.71,-0.78 1.27,-1.44 1.68,-1.99 0,-0.07 0.07,-0.14 0.2,-0.2 0.2,-0.2 0.41,-0.24 0.61,-0.1 0.14,0.07 0.27,0.25 0.41,0.56 0.13,0.31 -0.1,0.83 -0.71,1.58 -1.16,1.43 -2.31,2.67 -3.47,3.72 -1.16,1.05 -1.9,1.75 -2.24,2.09 -0.95,0.68 -1.73,1.07 -2.35,1.17 -0.61,0.1 -1.09,0.12 -1.43,0.05 -1.22,-0.2 -1.99,-0.75 -2.29,-1.63 -0.31,-0.88 -0.39,-1.9 -0.25,-3.06 0.13,-1.16 0.46,-2.38 0.97,-3.67 0.51,-1.29 0.97,-2.41 1.38,-3.37 -0.75,0.88 -1.62,1.89 -2.6,3.01 -0.99,1.12 -1.97,2.21 -2.96,3.26 -0.99,1.05 -1.87,2.01 -2.65,2.86 -0.78,0.85 -1.28,1.41 -1.48,1.68 -0.41,0.47 -1.19,0.54 -2.35,0.2 -1.16,-0.34 -2.04,-0.88 -2.65,-1.63 -0.61,-0.68 -0.78,-2 -0.51,-3.98 0.28,-1.98 1.23,-4.29 2.87,-6.94 z m 3.67,7.75 c 0.61,-0.41 1.51,-1.27 2.7,-2.6 1.19,-1.33 2.36,-2.7 3.52,-4.13 1.36,-1.7 2.86,-3.5 4.49,-5.41 -0.95,-0.61 -1.89,-0.71 -2.8,-0.31 -0.91,0.4 -1.68,0.99 -2.29,1.73 -0.61,0.75 -1.55,2.01 -2.81,3.77 -1.26,1.77 -2.33,3.61 -3.21,5.51 -0.34,0.61 -0.46,1.04 -0.36,1.28 0.1,0.24 0.22,0.36 0.36,0.36 0.14,0 0.24,-0.03 0.31,-0.1 0.05,0 0.09,-0.03 0.09,-0.1 z" id="path156" style="fill:#00a099"></path>
<path class="st0" d="m 356.16,393.37 c -0.75,0.88 -1.63,1.9 -2.65,3.06 -1.02,1.16 -2.02,2.28 -3.01,3.37 -0.99,1.09 -1.91,2.06 -2.75,2.91 -0.85,0.85 -1.41,1.38 -1.68,1.58 -0.41,0.34 -1.14,0.36 -2.19,0.05 -1.05,-0.31 -1.89,-0.83 -2.5,-1.58 -0.61,-0.68 -0.76,-2 -0.46,-3.98 0.31,-1.97 1.28,-4.28 2.91,-6.94 0.88,-1.43 1.85,-2.79 2.91,-4.08 1.05,-1.29 2.11,-2.38 3.16,-3.26 1.05,-0.88 2.04,-1.51 2.96,-1.89 0.92,-0.37 1.68,-0.36 2.29,0.05 1.16,0.75 2.07,1.39 2.75,1.94 0.68,0.54 1.09,0.88 1.22,1.02 1.09,-2.04 2.11,-4.03 3.06,-5.97 0.95,-1.94 1.79,-3.74 2.5,-5.41 0.71,-1.67 1.31,-3.13 1.79,-4.39 0.47,-1.26 0.85,-2.26 1.12,-3.01 0.27,-0.75 0.53,-1.46 0.76,-2.14 0.24,-0.68 0.46,-1.46 0.66,-2.35 v -0.2 l 0.31,-0.2 c 0.07,0 0.34,0.07 0.82,0.2 0.95,0.61 1.72,1.19 2.29,1.73 0.58,0.54 0.98,1.12 1.22,1.73 0.24,0.61 0.27,1.29 0.1,2.04 -0.17,0.75 -0.56,1.67 -1.17,2.75 -0.34,0.75 -1,2.14 -1.99,4.18 -0.99,2.04 -1.99,4.15 -3.01,6.32 -1.22,2.59 -2.55,5.34 -3.98,8.26 -1.16,2.52 -2.14,4.73 -2.96,6.63 -0.75,1.7 -1.39,3.23 -1.94,4.59 -0.54,1.36 -0.75,2.11 -0.61,2.24 0.2,0.14 0.61,-0.02 1.22,-0.46 0.61,-0.44 1.29,-1.02 2.04,-1.73 0.75,-0.71 1.5,-1.46 2.24,-2.24 0.75,-0.78 1.33,-1.44 1.73,-1.99 l 0.2,-0.2 c 0.13,-0.14 0.31,-0.17 0.51,-0.1 0.14,0.07 0.29,0.25 0.46,0.56 0.17,0.31 -0.09,0.83 -0.76,1.58 -1.16,1.43 -2.3,2.67 -3.42,3.72 -1.12,1.05 -1.89,1.75 -2.3,2.09 -0.88,0.68 -1.65,1.07 -2.29,1.17 -0.65,0.1 -1.14,0.12 -1.48,0.05 -1.16,-0.2 -1.9,-0.75 -2.24,-1.63 -0.34,-0.88 -0.43,-1.9 -0.25,-3.06 0.17,-1.16 0.49,-2.38 0.97,-3.67 0.49,-1.27 0.96,-2.39 1.44,-3.34 z m -9.18,4.79 c -0.34,0.61 -0.46,1.04 -0.36,1.28 0.1,0.24 0.22,0.36 0.36,0.36 0.14,0 0.24,-0.03 0.31,-0.1 0.07,0 0.14,-0.03 0.2,-0.1 0.54,-0.41 1.41,-1.27 2.6,-2.6 1.19,-1.33 2.36,-2.7 3.52,-4.13 1.36,-1.7 2.79,-3.5 4.28,-5.41 -0.95,-0.61 -1.85,-0.71 -2.7,-0.31 -0.85,0.41 -1.58,0.99 -2.19,1.73 -0.27,0.41 -0.66,0.94 -1.17,1.58 -0.51,0.65 -1.04,1.38 -1.58,2.19 -0.54,0.82 -1.11,1.7 -1.68,2.65 -0.59,0.96 -1.12,1.91 -1.59,2.86 z" id="path158" style="fill:#00a099"></path>
<path class="st0" d="m 364.62,400.81 c -0.27,-1.22 -0.29,-2.46 -0.05,-3.72 0.24,-1.26 0.61,-2.46 1.12,-3.62 0.51,-1.16 1.07,-2.19 1.68,-3.11 0.61,-0.92 1.19,-1.68 1.73,-2.29 0.88,-0.95 1.73,-1.79 2.55,-2.5 0.82,-0.71 1.5,-1.28 2.04,-1.68 0.68,-0.47 1.29,-0.85 1.84,-1.12 1.43,-0.82 2.52,-0.95 3.26,-0.41 0.54,0.41 1,0.78 1.38,1.12 0.37,0.34 0.73,0.65 1.07,0.92 l 0.1,0.1 c 0.07,0.14 0.17,0.31 0.31,0.51 0.14,0.2 0.2,0.48 0.2,0.82 0,1.5 -0.37,2.89 -1.12,4.18 -0.75,1.29 -1.7,2.45 -2.86,3.47 -1.36,1.22 -2.81,2.07 -4.33,2.55 -1.53,0.48 -2.7,0.58 -3.52,0.31 -0.54,1.22 -0.82,2.21 -0.82,2.96 0,0.75 0.07,1.36 0.2,1.84 0.2,0.54 0.48,0.95 0.82,1.22 0.82,0.55 1.73,0.63 2.75,0.26 1.02,-0.37 2,-0.93 2.96,-1.68 0.95,-0.75 1.87,-1.55 2.75,-2.4 0.88,-0.85 1.63,-1.55 2.24,-2.09 0.14,-0.14 0.31,-0.24 0.51,-0.31 0.48,-0.14 0.78,-0.1 0.92,0.1 0.14,0.07 0.2,0.17 0.2,0.31 0,0.34 -0.14,0.65 -0.41,0.92 -1.77,1.84 -3.28,3.4 -4.54,4.69 -1.26,1.29 -2.16,2.01 -2.7,2.14 -1.84,0.61 -3.37,0.88 -4.59,0.82 -1.22,-0.07 -2.23,-0.32 -3.01,-0.77 -0.78,-0.44 -1.38,-0.98 -1.79,-1.63 -0.41,-0.65 -0.71,-1.24 -0.92,-1.79 v -0.12 z m 13.16,-10.3 c 0.88,-1.02 1.46,-1.8 1.73,-2.35 0.27,-0.54 0.36,-0.92 0.25,-1.12 -0.1,-0.2 -0.27,-0.31 -0.51,-0.31 -0.24,0 -0.39,0 -0.46,0 -0.54,0.14 -1.16,0.41 -1.84,0.82 -0.55,0.34 -1.17,0.83 -1.89,1.48 -0.71,0.65 -1.45,1.45 -2.19,2.4 -0.34,0.48 -0.65,0.92 -0.92,1.33 -0.27,0.41 -0.55,0.82 -0.82,1.22 0.47,0.07 1.14,0 1.99,-0.2 0.85,-0.2 1.79,-0.71 2.8,-1.53 0.27,-0.2 0.53,-0.41 0.76,-0.61 0.24,-0.2 0.49,-0.47 0.77,-0.82 z" id="path160" style="fill:#00a099"></path>
<path class="st0" d="m 250.03,427.45 c 5.1,0.48 9.52,0.24 13.26,-0.71 3.74,-0.95 6.82,-2.16 9.23,-3.62 2.41,-1.46 4.16,-2.97 5.25,-4.54 1.09,-1.56 1.56,-2.72 1.43,-3.47 -0.41,-1.5 -2.06,-2.65 -4.95,-3.47 -2.89,-0.82 -6.89,-0.82 -11.99,0 -2.52,0.41 -4.86,1.12 -7.04,2.14 -2.18,1.02 -4.08,2.23 -5.71,3.62 -1.63,1.39 -2.92,2.87 -3.88,4.44 -0.95,1.57 -1.5,3.1 -1.63,4.59 -0.14,1.5 -0.04,2.72 0.31,3.67 0.34,0.95 0.9,1.79 1.68,2.5 0.78,0.71 1.82,1.38 3.11,1.99 1.29,0.61 2.82,1.26 4.59,1.94 2.31,0.95 4.45,1.75 6.43,2.4 1.97,0.65 3.43,1.48 4.39,2.5 2.31,-0.48 4.1,-0.78 5.35,-0.92 1.26,-0.13 2.4,-0.27 3.42,-0.41 0.41,0 0.75,0.04 1.02,0.1 0.61,0.14 0.78,0.44 0.51,0.92 -0.34,0.41 -0.63,0.8 -0.87,1.17 -0.24,0.38 -0.94,0.66 -2.09,0.87 -1.29,0.14 -2.48,0.31 -3.57,0.51 -1.09,0.2 -2.21,0.38 -3.37,0.51 v 0.41 c 0,0.75 -0.22,1.58 -0.66,2.5 -0.44,0.92 -1.11,1.84 -1.99,2.75 -0.88,0.92 -2.01,1.79 -3.37,2.6 -1.36,0.82 -2.96,1.46 -4.79,1.94 -2.58,0.75 -4.81,1.09 -6.68,1.02 -1.87,-0.07 -3.37,-0.41 -4.49,-1.02 -1.12,-0.61 -1.85,-1.39 -2.19,-2.35 -0.34,-0.95 -0.27,-1.94 0.2,-2.96 0.27,-0.61 0.95,-1.24 2.04,-1.89 1.09,-0.65 2.4,-1.26 3.93,-1.84 1.53,-0.58 3.23,-1.12 5.1,-1.63 1.87,-0.51 3.79,-0.97 5.76,-1.38 -1.09,-0.61 -2.64,-1.33 -4.64,-2.14 -2.01,-0.82 -4.54,-1.87 -7.6,-3.16 -6.53,-2.58 -9.38,-6.59 -8.57,-12.04 0.2,-1.22 0.76,-2.74 1.68,-4.54 0.92,-1.8 2.29,-3.6 4.13,-5.41 1.84,-1.8 4.15,-3.45 6.94,-4.95 2.79,-1.5 6.08,-2.58 9.89,-3.26 3.47,-0.61 6.51,-0.78 9.13,-0.51 2.62,0.27 4.85,0.77 6.68,1.48 1.83,0.71 3.26,1.62 4.28,2.7 1.02,1.09 1.67,2.14 1.94,3.16 0.61,2.18 0.49,4.39 -0.36,6.63 -0.85,2.24 -3.08,4.66 -6.68,7.24 -2.18,1.63 -4.37,2.89 -6.58,3.77 -2.21,0.88 -4.23,1.53 -6.07,1.94 -2.18,0.48 -4.25,0.75 -6.22,0.82 -0.82,0 -1.58,-0.27 -2.29,-0.82 -0.71,-0.54 -1.34,-1.16 -1.89,-1.84 -0.54,-0.68 -1,-1.36 -1.38,-2.04 -0.38,-0.68 -0.63,-1.19 -0.76,-1.53 0,-0.07 0.07,-0.17 0.2,-0.31 0.07,0 0.17,-0.03 0.31,-0.1 h 0.12 z m -6.01,23.77 c 1.29,0.13 2.7,0.03 4.23,-0.31 1.53,-0.34 2.99,-0.8 4.39,-1.38 1.39,-0.58 2.67,-1.24 3.82,-1.99 1.16,-0.75 2.04,-1.49 2.65,-2.24 -3.81,0.82 -6.72,1.58 -8.72,2.29 -2.01,0.71 -3.49,1.34 -4.44,1.89 -1.15,0.68 -1.8,1.26 -1.93,1.74 z" id="path162" style="fill:#00a099"></path>
<path class="st0" d="m 273.08,445.81 c -0.27,-1.22 -0.29,-2.46 -0.05,-3.72 0.24,-1.26 0.61,-2.46 1.12,-3.62 0.51,-1.16 1.07,-2.19 1.68,-3.11 0.61,-0.92 1.19,-1.68 1.73,-2.29 0.88,-0.95 1.73,-1.79 2.55,-2.5 0.82,-0.71 1.5,-1.28 2.04,-1.68 0.68,-0.47 1.29,-0.85 1.84,-1.12 1.43,-0.82 2.52,-0.95 3.26,-0.41 0.54,0.41 1,0.78 1.38,1.12 0.37,0.34 0.73,0.65 1.07,0.92 l 0.1,0.1 c 0.07,0.14 0.17,0.31 0.31,0.51 0.14,0.2 0.2,0.48 0.2,0.82 0,1.5 -0.37,2.89 -1.12,4.18 -0.75,1.29 -1.7,2.45 -2.86,3.47 -1.36,1.22 -2.81,2.07 -4.33,2.55 -1.53,0.48 -2.7,0.58 -3.52,0.31 -0.54,1.22 -0.82,2.21 -0.82,2.96 0,0.75 0.07,1.36 0.2,1.84 0.2,0.54 0.48,0.95 0.82,1.22 0.82,0.55 1.73,0.63 2.75,0.26 1.02,-0.37 2,-0.93 2.96,-1.68 0.95,-0.75 1.87,-1.55 2.75,-2.4 0.88,-0.85 1.63,-1.55 2.24,-2.09 0.14,-0.14 0.31,-0.24 0.51,-0.31 0.48,-0.14 0.78,-0.1 0.92,0.1 0.14,0.07 0.2,0.17 0.2,0.31 0,0.34 -0.14,0.65 -0.41,0.92 -1.77,1.84 -3.28,3.4 -4.54,4.69 -1.26,1.29 -2.16,2.01 -2.7,2.14 -1.84,0.61 -3.37,0.88 -4.59,0.82 -1.22,-0.07 -2.23,-0.32 -3.01,-0.77 -0.78,-0.44 -1.38,-0.98 -1.79,-1.63 -0.41,-0.65 -0.71,-1.24 -0.92,-1.79 v -0.12 z m 13.16,-10.3 c 0.88,-1.02 1.46,-1.8 1.73,-2.35 0.27,-0.54 0.36,-0.92 0.25,-1.12 -0.1,-0.2 -0.27,-0.31 -0.51,-0.31 -0.24,0 -0.39,0 -0.46,0 -0.54,0.14 -1.16,0.41 -1.84,0.82 -0.55,0.34 -1.17,0.83 -1.89,1.48 -0.71,0.65 -1.45,1.45 -2.19,2.4 -0.34,0.48 -0.65,0.92 -0.92,1.33 -0.27,0.41 -0.55,0.82 -0.82,1.22 0.47,0.07 1.14,0 1.99,-0.2 0.85,-0.2 1.79,-0.71 2.8,-1.53 0.27,-0.2 0.53,-0.41 0.76,-0.61 0.24,-0.2 0.49,-0.47 0.77,-0.82 z" id="path164" style="fill:#00a099"></path>
<path class="st0" d="m 303.99,438.47 c -0.68,0.14 -1.17,0.25 -1.48,0.36 -0.31,0.1 -1.11,0.32 -2.4,0.66 0.34,1.16 0.59,2.33 0.76,3.52 0.17,1.19 0.1,2.28 -0.2,3.26 -0.31,0.99 -0.94,1.84 -1.89,2.55 -0.95,0.71 -2.38,1.17 -4.28,1.38 -1.57,0.07 -2.96,-0.04 -4.18,-0.31 -1.02,-0.2 -1.95,-0.6 -2.81,-1.17 -0.85,-0.58 -1.27,-1.44 -1.27,-2.6 0,-0.95 0.54,-1.94 1.63,-2.96 0.48,-0.61 0.95,-1.36 1.43,-2.24 0.48,-0.88 0.92,-1.79 1.33,-2.7 0.41,-0.91 0.76,-1.78 1.07,-2.6 0.31,-0.82 0.56,-1.39 0.76,-1.73 -0.34,-1.29 -0.31,-2.53 0.1,-3.72 0.41,-1.19 1.02,-2.24 1.84,-3.16 0.82,-0.92 1.73,-1.68 2.75,-2.29 1.02,-0.61 2,-1.02 2.96,-1.22 1.36,-0.27 2.58,-0.42 3.67,-0.46 1.09,-0.03 2,-0.02 2.75,0.05 0.07,0 0.13,0.04 0.2,0.1 0.2,0.2 0.31,0.34 0.31,0.41 0,0.14 -0.02,0.25 -0.05,0.36 -0.04,0.1 -0.22,0.29 -0.56,0.56 -0.68,0.48 -1.46,1.07 -2.35,1.79 -0.88,0.71 -1.7,1.5 -2.45,2.35 -0.75,0.85 -1.38,1.75 -1.89,2.7 -0.51,0.95 -0.76,1.9 -0.76,2.86 0.07,0.48 0.17,1.04 0.31,1.68 0.14,0.65 0.27,1.28 0.41,1.89 0.47,-0.13 0.85,-0.24 1.12,-0.31 0.27,-0.07 0.54,-0.14 0.82,-0.2 0.27,-0.07 0.58,-0.14 0.92,-0.2 0.34,-0.07 0.82,-0.17 1.43,-0.31 h 0.61 c 0.48,0 0.71,0.17 0.71,0.51 0,0.41 -0.19,0.7 -0.56,0.87 -0.37,0.13 -0.63,0.25 -0.76,0.32 z m -13.16,4.69 c -0.68,0.48 -1.16,0.92 -1.43,1.33 -0.27,0.34 -0.41,0.71 -0.41,1.12 0,0.41 0.31,0.78 0.92,1.12 0.88,0.34 1.73,0.51 2.55,0.51 0.68,0 1.38,-0.19 2.09,-0.56 0.71,-0.37 1.24,-1.14 1.58,-2.3 0.14,-0.27 0.2,-0.58 0.2,-0.92 0,-0.75 -0.14,-1.67 -0.41,-2.75 -1.09,0.34 -2.08,0.71 -2.96,1.12 -0.87,0.41 -1.59,0.86 -2.13,1.33 z m 2.76,-6.93 c -0.2,0.41 -0.51,0.99 -0.92,1.73 -0.41,0.75 -0.78,1.6 -1.12,2.55 0.54,-0.27 1.1,-0.54 1.68,-0.82 0.58,-0.27 1.24,-0.54 1.99,-0.82 -0.34,-0.75 -0.63,-1.26 -0.87,-1.53 -0.24,-0.26 -0.49,-0.64 -0.76,-1.11 z" id="path166" style="fill:#00a099"></path>
<path class="st0" d="m 303.68,445.81 c -0.27,-1.22 -0.29,-2.46 -0.05,-3.72 0.24,-1.26 0.61,-2.46 1.12,-3.62 0.51,-1.16 1.07,-2.19 1.68,-3.11 0.61,-0.92 1.19,-1.68 1.73,-2.29 0.88,-0.95 1.73,-1.79 2.55,-2.5 0.82,-0.71 1.5,-1.28 2.04,-1.68 0.68,-0.47 1.29,-0.85 1.84,-1.12 1.43,-0.82 2.52,-0.95 3.26,-0.41 0.54,0.41 1,0.78 1.38,1.12 0.37,0.34 0.73,0.65 1.07,0.92 l 0.1,0.1 c 0.07,0.14 0.17,0.31 0.31,0.51 0.14,0.2 0.2,0.48 0.2,0.82 0,1.5 -0.37,2.89 -1.12,4.18 -0.75,1.29 -1.7,2.45 -2.86,3.47 -1.36,1.22 -2.81,2.07 -4.33,2.55 -1.53,0.48 -2.7,0.58 -3.52,0.31 -0.54,1.22 -0.82,2.21 -0.82,2.96 0,0.75 0.07,1.36 0.2,1.84 0.2,0.54 0.48,0.95 0.82,1.22 0.82,0.55 1.73,0.63 2.75,0.26 1.02,-0.37 2,-0.93 2.96,-1.68 0.95,-0.75 1.87,-1.55 2.75,-2.4 0.88,-0.85 1.63,-1.55 2.24,-2.09 0.14,-0.14 0.31,-0.24 0.51,-0.31 0.48,-0.14 0.78,-0.1 0.92,0.1 0.14,0.07 0.2,0.17 0.2,0.31 0,0.34 -0.14,0.65 -0.41,0.92 -1.77,1.84 -3.28,3.4 -4.54,4.69 -1.26,1.29 -2.16,2.01 -2.7,2.14 -1.84,0.61 -3.37,0.88 -4.59,0.82 -1.22,-0.07 -2.23,-0.32 -3.01,-0.77 -0.78,-0.44 -1.38,-0.98 -1.79,-1.63 -0.41,-0.65 -0.71,-1.24 -0.92,-1.79 v -0.12 z m 13.16,-10.3 c 0.88,-1.02 1.46,-1.8 1.73,-2.35 0.27,-0.54 0.36,-0.92 0.25,-1.12 -0.1,-0.2 -0.27,-0.31 -0.51,-0.31 -0.24,0 -0.39,0 -0.46,0 -0.54,0.14 -1.16,0.41 -1.84,0.82 -0.55,0.34 -1.17,0.83 -1.89,1.48 -0.71,0.65 -1.45,1.45 -2.19,2.4 -0.34,0.48 -0.65,0.92 -0.92,1.33 -0.27,0.41 -0.55,0.82 -0.82,1.22 0.47,0.07 1.14,0 1.99,-0.2 0.85,-0.2 1.79,-0.71 2.8,-1.53 0.27,-0.2 0.53,-0.41 0.76,-0.61 0.24,-0.2 0.49,-0.47 0.77,-0.82 z" id="path168" style="fill:#00a099"></path>
<path class="st0" d="m 335.91,406.34 c 0.41,0.27 0.88,0.61 1.43,1.02 0.54,0.41 1.02,0.88 1.43,1.43 0.41,0.54 0.68,1.12 0.82,1.73 0.13,0.61 0.03,1.22 -0.31,1.84 -1.43,3.54 -2.99,7.02 -4.69,10.46 -1.7,3.43 -3.43,6.92 -5.2,10.46 v 0.1 c -1.16,2.45 -2.14,4.62 -2.96,6.53 -0.75,1.63 -1.39,3.15 -1.94,4.54 -0.54,1.39 -0.75,2.16 -0.61,2.29 0.2,0.14 0.61,-0.02 1.22,-0.46 0.61,-0.44 1.29,-1 2.04,-1.68 0.75,-0.68 1.5,-1.41 2.24,-2.19 0.75,-0.78 1.33,-1.48 1.73,-2.09 l 0.2,-0.2 c 0.07,-0.07 0.24,-0.1 0.51,-0.1 0.14,0.07 0.29,0.27 0.46,0.61 0.17,0.34 -0.09,0.88 -0.76,1.63 -1.16,1.36 -2.29,2.58 -3.42,3.67 -1.12,1.09 -1.89,1.77 -2.29,2.04 -0.95,0.68 -1.73,1.09 -2.35,1.22 -0.61,0.13 -1.09,0.13 -1.43,0 -1.22,-0.2 -2,-0.73 -2.35,-1.58 -0.34,-0.85 -0.44,-1.85 -0.31,-3.01 0.14,-1.16 0.44,-2.36 0.92,-3.62 0.48,-1.26 0.95,-2.36 1.43,-3.31 0.47,-1.09 0.97,-2.21 1.48,-3.37 0.51,-1.16 1,-2.28 1.48,-3.37 0.47,-1.09 0.9,-2.06 1.28,-2.91 0.37,-0.85 0.66,-1.48 0.87,-1.89 1.84,-4.08 3.26,-7.33 4.28,-9.74 1.02,-2.41 1.77,-4.23 2.24,-5.46 0.27,-0.68 0.51,-1.39 0.71,-2.14 0.2,-0.75 0.44,-1.53 0.71,-2.35 v -0.2 l 0.31,-0.2 c 0.22,-0.01 0.49,0.09 0.83,0.3 z" id="path170" style="fill:#00a099"></path>
<path class="st0" d="m 346.11,406.34 c 0.41,0.27 0.88,0.61 1.43,1.02 0.54,0.41 1.02,0.88 1.43,1.43 0.41,0.54 0.68,1.12 0.82,1.73 0.13,0.61 0.03,1.22 -0.31,1.84 -1.43,3.54 -2.99,7.02 -4.69,10.46 -1.7,3.43 -3.43,6.92 -5.2,10.46 v 0.1 c -1.16,2.45 -2.14,4.62 -2.96,6.53 -0.75,1.63 -1.39,3.15 -1.94,4.54 -0.54,1.39 -0.75,2.16 -0.61,2.29 0.2,0.14 0.61,-0.02 1.22,-0.46 0.61,-0.44 1.29,-1 2.04,-1.68 0.75,-0.68 1.5,-1.41 2.24,-2.19 0.75,-0.78 1.33,-1.48 1.73,-2.09 l 0.2,-0.2 c 0.07,-0.07 0.24,-0.1 0.51,-0.1 0.14,0.07 0.29,0.27 0.46,0.61 0.17,0.34 -0.09,0.88 -0.76,1.63 -1.16,1.36 -2.29,2.58 -3.42,3.67 -1.12,1.09 -1.89,1.77 -2.29,2.04 -0.95,0.68 -1.73,1.09 -2.35,1.22 -0.61,0.13 -1.09,0.13 -1.43,0 -1.22,-0.2 -2,-0.73 -2.35,-1.58 -0.34,-0.85 -0.44,-1.85 -0.31,-3.01 0.14,-1.16 0.44,-2.36 0.92,-3.62 0.48,-1.26 0.95,-2.36 1.43,-3.31 0.47,-1.09 0.97,-2.21 1.48,-3.37 0.51,-1.16 1,-2.28 1.48,-3.37 0.47,-1.09 0.9,-2.06 1.28,-2.91 0.37,-0.85 0.66,-1.48 0.87,-1.89 1.84,-4.08 3.26,-7.33 4.28,-9.74 1.02,-2.41 1.77,-4.23 2.24,-5.46 0.27,-0.68 0.51,-1.39 0.71,-2.14 0.2,-0.75 0.44,-1.53 0.71,-2.35 v -0.2 l 0.31,-0.2 c 0.22,-0.01 0.49,0.09 0.83,0.3 z" id="path172" style="fill:#00a099"></path>
<path class="st0" d="m 340.6,445.81 c -0.27,-1.22 -0.29,-2.46 -0.05,-3.72 0.24,-1.26 0.61,-2.46 1.12,-3.62 0.51,-1.16 1.07,-2.19 1.68,-3.11 0.61,-0.92 1.19,-1.68 1.73,-2.29 0.88,-0.95 1.73,-1.79 2.55,-2.5 0.82,-0.71 1.5,-1.28 2.04,-1.68 0.68,-0.47 1.29,-0.85 1.84,-1.12 1.43,-0.82 2.52,-0.95 3.26,-0.41 0.54,0.41 1,0.78 1.38,1.12 0.37,0.34 0.73,0.65 1.07,0.92 l 0.1,0.1 c 0.07,0.14 0.17,0.31 0.31,0.51 0.14,0.2 0.2,0.48 0.2,0.82 0,1.5 -0.37,2.89 -1.12,4.18 -0.75,1.29 -1.7,2.45 -2.86,3.47 -1.36,1.22 -2.81,2.07 -4.33,2.55 -1.53,0.48 -2.7,0.58 -3.52,0.31 -0.54,1.22 -0.82,2.21 -0.82,2.96 0,0.75 0.07,1.36 0.2,1.84 0.2,0.54 0.48,0.95 0.82,1.22 0.82,0.55 1.73,0.63 2.75,0.26 1.02,-0.37 2,-0.93 2.96,-1.68 0.95,-0.75 1.87,-1.55 2.75,-2.4 0.88,-0.85 1.63,-1.55 2.24,-2.09 0.14,-0.14 0.31,-0.24 0.51,-0.31 0.48,-0.14 0.78,-0.1 0.92,0.1 0.14,0.07 0.2,0.17 0.2,0.31 0,0.34 -0.14,0.65 -0.41,0.92 -1.77,1.84 -3.28,3.4 -4.54,4.69 -1.26,1.29 -2.16,2.01 -2.7,2.14 -1.84,0.61 -3.37,0.88 -4.59,0.82 -1.22,-0.07 -2.23,-0.32 -3.01,-0.77 -0.78,-0.44 -1.38,-0.98 -1.79,-1.63 -0.41,-0.65 -0.71,-1.24 -0.92,-1.79 v -0.12 z m 13.16,-10.3 c 0.88,-1.02 1.46,-1.8 1.73,-2.35 0.27,-0.54 0.36,-0.92 0.25,-1.12 -0.1,-0.2 -0.27,-0.31 -0.51,-0.31 -0.24,0 -0.39,0 -0.46,0 -0.54,0.14 -1.16,0.41 -1.84,0.82 -0.55,0.34 -1.17,0.83 -1.89,1.48 -0.71,0.65 -1.45,1.45 -2.19,2.4 -0.34,0.48 -0.65,0.92 -0.92,1.33 -0.27,0.41 -0.55,0.82 -0.82,1.22 0.47,0.07 1.14,0 1.99,-0.2 0.85,-0.2 1.79,-0.71 2.8,-1.53 0.27,-0.2 0.53,-0.41 0.76,-0.61 0.24,-0.2 0.49,-0.47 0.77,-0.82 z" id="path174" style="fill:#00a099"></path>
</g>
<g id="g222">
<path class="st0" d="m 213.08,472.79 c 0.18,-0.37 0.43,-0.68 0.74,-0.92 0.31,-0.24 0.68,-0.41 1.1,-0.53 0.42,-0.11 0.88,-0.17 1.39,-0.17 0.39,0 0.77,0.04 1.16,0.11 0.38,0.07 0.73,0.21 1.04,0.42 0.31,0.21 0.55,0.49 0.75,0.86 0.19,0.37 0.29,0.85 0.29,1.44 v 4.66 c 0,0.43 0.21,0.65 0.63,0.65 0.12,0 0.24,-0.02 0.34,-0.07 v 0.9 c -0.12,0.02 -0.24,0.04 -0.33,0.05 -0.1,0.01 -0.22,0.02 -0.37,0.02 -0.27,0 -0.49,-0.04 -0.65,-0.11 -0.16,-0.07 -0.29,-0.18 -0.38,-0.31 -0.09,-0.13 -0.15,-0.3 -0.18,-0.48 -0.03,-0.19 -0.04,-0.39 -0.04,-0.62 h -0.03 c -0.19,0.28 -0.39,0.54 -0.59,0.76 -0.2,0.22 -0.42,0.41 -0.66,0.55 -0.24,0.15 -0.52,0.26 -0.83,0.34 -0.31,0.08 -0.68,0.12 -1.11,0.12 -0.41,0 -0.79,-0.05 -1.15,-0.14 -0.36,-0.1 -0.67,-0.25 -0.94,-0.46 -0.27,-0.21 -0.48,-0.48 -0.63,-0.8 -0.15,-0.32 -0.23,-0.71 -0.23,-1.15 0,-0.61 0.14,-1.09 0.41,-1.44 0.27,-0.35 0.63,-0.61 1.08,-0.79 0.45,-0.18 0.95,-0.31 1.51,-0.38 0.56,-0.07 1.13,-0.14 1.71,-0.21 0.23,-0.02 0.42,-0.05 0.59,-0.08 0.17,-0.03 0.31,-0.09 0.43,-0.18 0.11,-0.08 0.2,-0.2 0.26,-0.35 0.06,-0.15 0.09,-0.34 0.09,-0.58 0,-0.36 -0.06,-0.66 -0.18,-0.89 -0.12,-0.23 -0.28,-0.42 -0.49,-0.55 -0.21,-0.14 -0.45,-0.23 -0.73,-0.28 -0.28,-0.05 -0.58,-0.08 -0.89,-0.08 -0.68,0 -1.24,0.16 -1.67,0.48 -0.43,0.32 -0.66,0.84 -0.68,1.56 h -1.07 c 0.02,-0.53 0.13,-0.97 0.31,-1.35 z m 5.36,2.62 c -0.07,0.12 -0.2,0.22 -0.39,0.27 -0.19,0.06 -0.36,0.1 -0.51,0.12 -0.45,0.08 -0.92,0.15 -1.4,0.21 -0.48,0.06 -0.92,0.16 -1.32,0.28 -0.4,0.12 -0.72,0.3 -0.98,0.54 -0.25,0.23 -0.38,0.56 -0.38,0.99 0,0.27 0.05,0.51 0.16,0.72 0.11,0.21 0.25,0.39 0.43,0.54 0.18,0.15 0.39,0.27 0.63,0.35 0.24,0.08 0.48,0.12 0.73,0.12 0.41,0 0.8,-0.06 1.17,-0.19 0.37,-0.13 0.7,-0.31 0.98,-0.54 0.28,-0.24 0.5,-0.53 0.66,-0.87 0.16,-0.34 0.25,-0.72 0.25,-1.16 v -1.39 h -0.03 z" id="path178" style="fill:#00a099"></path>
<path class="st0" d="m 222.67,471.43 v 1.67 h 0.03 c 0.25,-0.61 0.65,-1.08 1.22,-1.42 0.56,-0.33 1.2,-0.5 1.91,-0.5 0.67,0 1.25,0.12 1.74,0.37 0.49,0.25 0.9,0.59 1.23,1.01 0.33,0.42 0.57,0.92 0.73,1.48 0.16,0.56 0.24,1.15 0.24,1.78 0,0.63 -0.08,1.21 -0.24,1.78 -0.16,0.56 -0.4,1.05 -0.73,1.48 -0.33,0.43 -0.74,0.76 -1.23,1 -0.49,0.24 -1.07,0.37 -1.74,0.37 -0.32,0 -0.63,-0.04 -0.95,-0.12 -0.32,-0.08 -0.61,-0.2 -0.88,-0.36 -0.27,-0.16 -0.51,-0.36 -0.72,-0.59 -0.21,-0.23 -0.37,-0.52 -0.48,-0.83 h -0.03 v 4.9 h -1.07 v -12 h 0.97 z m 5.87,3.04 c -0.11,-0.45 -0.28,-0.85 -0.51,-1.2 -0.23,-0.35 -0.53,-0.64 -0.89,-0.86 -0.36,-0.22 -0.8,-0.33 -1.31,-0.33 -0.59,0 -1.08,0.1 -1.48,0.31 -0.4,0.2 -0.71,0.48 -0.95,0.82 -0.24,0.34 -0.41,0.74 -0.5,1.19 -0.1,0.45 -0.14,0.93 -0.14,1.43 0,0.45 0.05,0.9 0.16,1.35 0.11,0.45 0.28,0.85 0.53,1.2 0.24,0.35 0.56,0.64 0.95,0.86 0.39,0.22 0.87,0.33 1.44,0.33 0.51,0 0.95,-0.11 1.31,-0.33 0.36,-0.22 0.66,-0.51 0.89,-0.86 0.23,-0.35 0.4,-0.75 0.51,-1.2 0.11,-0.45 0.16,-0.9 0.16,-1.35 0,-0.45 -0.06,-0.92 -0.17,-1.36 z" id="path180" style="fill:#00a099"></path>
<path class="st0" d="m 231.66,472.79 c 0.18,-0.37 0.43,-0.68 0.74,-0.92 0.31,-0.24 0.68,-0.41 1.1,-0.53 0.42,-0.11 0.88,-0.17 1.39,-0.17 0.39,0 0.77,0.04 1.16,0.11 0.38,0.07 0.73,0.21 1.04,0.42 0.31,0.21 0.55,0.49 0.75,0.86 0.19,0.37 0.29,0.85 0.29,1.44 v 4.66 c 0,0.43 0.21,0.65 0.63,0.65 0.12,0 0.24,-0.02 0.34,-0.07 v 0.9 c -0.12,0.02 -0.24,0.04 -0.33,0.05 -0.1,0.01 -0.22,0.02 -0.37,0.02 -0.27,0 -0.49,-0.04 -0.65,-0.11 -0.16,-0.07 -0.29,-0.18 -0.38,-0.31 -0.09,-0.13 -0.15,-0.3 -0.18,-0.48 -0.03,-0.19 -0.04,-0.39 -0.04,-0.62 h -0.03 c -0.19,0.28 -0.39,0.54 -0.59,0.76 -0.2,0.22 -0.42,0.41 -0.66,0.55 -0.24,0.15 -0.52,0.26 -0.83,0.34 -0.31,0.08 -0.68,0.12 -1.11,0.12 -0.41,0 -0.79,-0.05 -1.15,-0.14 -0.36,-0.1 -0.67,-0.25 -0.94,-0.46 -0.27,-0.21 -0.48,-0.48 -0.63,-0.8 -0.15,-0.32 -0.23,-0.71 -0.23,-1.15 0,-0.61 0.14,-1.09 0.41,-1.44 0.27,-0.35 0.63,-0.61 1.08,-0.79 0.45,-0.18 0.95,-0.31 1.51,-0.38 0.56,-0.07 1.13,-0.14 1.71,-0.21 0.23,-0.02 0.42,-0.05 0.59,-0.08 0.17,-0.03 0.31,-0.09 0.43,-0.18 0.11,-0.08 0.2,-0.2 0.26,-0.35 0.06,-0.15 0.09,-0.34 0.09,-0.58 0,-0.36 -0.06,-0.66 -0.18,-0.89 -0.12,-0.23 -0.28,-0.42 -0.49,-0.55 -0.21,-0.14 -0.45,-0.23 -0.73,-0.28 -0.28,-0.05 -0.58,-0.08 -0.89,-0.08 -0.68,0 -1.24,0.16 -1.67,0.48 -0.43,0.32 -0.66,0.84 -0.68,1.56 h -1.07 c 0.02,-0.53 0.13,-0.97 0.31,-1.35 z m 5.36,2.62 c -0.07,0.12 -0.2,0.22 -0.39,0.27 -0.19,0.06 -0.36,0.1 -0.51,0.12 -0.45,0.08 -0.92,0.15 -1.4,0.21 -0.48,0.06 -0.92,0.16 -1.32,0.28 -0.4,0.12 -0.72,0.3 -0.98,0.54 -0.25,0.23 -0.38,0.56 -0.38,0.99 0,0.27 0.05,0.51 0.16,0.72 0.11,0.21 0.25,0.39 0.43,0.54 0.18,0.15 0.39,0.27 0.63,0.35 0.24,0.08 0.48,0.12 0.73,0.12 0.41,0 0.8,-0.06 1.17,-0.19 0.37,-0.13 0.7,-0.31 0.98,-0.54 0.28,-0.24 0.5,-0.53 0.66,-0.87 0.16,-0.34 0.25,-0.72 0.25,-1.16 v -1.39 h -0.03 z" id="path182" style="fill:#00a099"></path>
<path class="st0" d="m 241.25,471.43 v 2.06 h 0.03 c 0.27,-0.71 0.69,-1.26 1.27,-1.65 0.57,-0.38 1.25,-0.56 2.05,-0.53 v 1.07 c -0.49,-0.02 -0.93,0.04 -1.33,0.2 -0.4,0.15 -0.74,0.37 -1.03,0.65 -0.29,0.28 -0.51,0.62 -0.67,1.01 -0.16,0.39 -0.24,0.82 -0.24,1.28 v 4.67 h -1.07 v -8.77 h 0.99 z" id="path184" style="fill:#00a099"></path>
<path class="st0" d="m 249.1,471.43 v 0.9 h -1.79 v 5.92 c 0,0.35 0.05,0.63 0.14,0.82 0.1,0.2 0.34,0.31 0.72,0.33 0.31,0 0.61,-0.02 0.92,-0.05 v 0.9 c -0.16,0 -0.32,0.01 -0.48,0.02 -0.16,0.01 -0.32,0.02 -0.48,0.02 -0.71,0 -1.21,-0.14 -1.5,-0.42 -0.28,-0.28 -0.42,-0.79 -0.41,-1.54 v -6 h -1.53 v -0.9 h 1.53 v -2.63 h 1.07 v 2.63 z" id="path186" style="fill:#00a099"></path>
<path class="st0" d="m 250.87,472.79 c 0.18,-0.37 0.43,-0.68 0.74,-0.92 0.31,-0.24 0.68,-0.41 1.1,-0.53 0.42,-0.11 0.88,-0.17 1.39,-0.17 0.39,0 0.77,0.04 1.16,0.11 0.38,0.07 0.73,0.21 1.04,0.42 0.31,0.21 0.55,0.49 0.75,0.86 0.19,0.37 0.29,0.85 0.29,1.44 v 4.66 c 0,0.43 0.21,0.65 0.63,0.65 0.12,0 0.24,-0.02 0.34,-0.07 v 0.9 c -0.12,0.02 -0.24,0.04 -0.33,0.05 -0.1,0.01 -0.22,0.02 -0.37,0.02 -0.27,0 -0.49,-0.04 -0.65,-0.11 -0.16,-0.07 -0.29,-0.18 -0.38,-0.31 -0.09,-0.13 -0.15,-0.3 -0.18,-0.48 -0.03,-0.19 -0.04,-0.39 -0.04,-0.62 h -0.03 c -0.19,0.28 -0.39,0.54 -0.59,0.76 -0.2,0.22 -0.42,0.41 -0.66,0.55 -0.24,0.15 -0.52,0.26 -0.83,0.34 -0.31,0.08 -0.68,0.12 -1.11,0.12 -0.41,0 -0.79,-0.05 -1.15,-0.14 -0.36,-0.1 -0.67,-0.25 -0.94,-0.46 -0.27,-0.21 -0.48,-0.48 -0.63,-0.8 -0.15,-0.32 -0.23,-0.71 -0.23,-1.15 0,-0.61 0.14,-1.09 0.41,-1.44 0.27,-0.35 0.63,-0.61 1.08,-0.79 0.45,-0.18 0.95,-0.31 1.51,-0.38 0.56,-0.07 1.13,-0.14 1.71,-0.21 0.23,-0.02 0.42,-0.05 0.59,-0.08 0.17,-0.03 0.31,-0.09 0.43,-0.18 0.11,-0.08 0.2,-0.2 0.26,-0.35 0.06,-0.15 0.09,-0.34 0.09,-0.58 0,-0.36 -0.06,-0.66 -0.18,-0.89 -0.12,-0.23 -0.28,-0.42 -0.49,-0.55 -0.21,-0.14 -0.45,-0.23 -0.73,-0.28 -0.28,-0.05 -0.58,-0.08 -0.89,-0.08 -0.68,0 -1.24,0.16 -1.67,0.48 -0.43,0.32 -0.66,0.84 -0.68,1.56 h -1.07 c 0.02,-0.53 0.13,-0.97 0.31,-1.35 z m 5.36,2.62 c -0.07,0.12 -0.2,0.22 -0.39,0.27 -0.19,0.06 -0.36,0.1 -0.51,0.12 -0.45,0.08 -0.92,0.15 -1.4,0.21 -0.48,0.06 -0.92,0.16 -1.32,0.28 -0.4,0.12 -0.72,0.3 -0.98,0.54 -0.25,0.23 -0.38,0.56 -0.38,0.99 0,0.27 0.05,0.51 0.16,0.72 0.11,0.21 0.25,0.39 0.43,0.54 0.18,0.15 0.39,0.27 0.63,0.35 0.24,0.08 0.48,0.12 0.73,0.12 0.41,0 0.8,-0.06 1.17,-0.19 0.37,-0.13 0.7,-0.31 0.98,-0.54 0.28,-0.24 0.5,-0.53 0.66,-0.87 0.16,-0.34 0.25,-0.72 0.25,-1.16 v -1.39 h -0.03 z" id="path188" style="fill:#00a099"></path>
<path class="st0" d="m 260.46,471.43 v 1.48 h 0.05 c 0.28,-0.54 0.66,-0.97 1.11,-1.28 0.46,-0.31 1.04,-0.46 1.76,-0.46 0.58,0 1.1,0.14 1.57,0.43 0.47,0.28 0.78,0.71 0.94,1.29 0.26,-0.58 0.65,-1.01 1.16,-1.29 0.51,-0.28 1.05,-0.43 1.63,-0.43 1.94,0 2.91,1.03 2.91,3.08 v 5.95 h -1.07 v -5.9 c 0,-0.72 -0.15,-1.28 -0.46,-1.66 -0.31,-0.38 -0.84,-0.57 -1.62,-0.57 -0.46,0 -0.85,0.09 -1.16,0.26 -0.31,0.18 -0.55,0.41 -0.73,0.71 -0.18,0.29 -0.31,0.63 -0.38,1.01 -0.07,0.38 -0.11,0.77 -0.11,1.18 v 4.96 H 265 v -5.95 c 0,-0.29 -0.03,-0.58 -0.09,-0.84 -0.06,-0.27 -0.16,-0.5 -0.31,-0.7 -0.15,-0.2 -0.33,-0.35 -0.57,-0.47 -0.24,-0.12 -0.53,-0.17 -0.87,-0.17 -0.45,0 -0.85,0.08 -1.18,0.25 -0.33,0.17 -0.61,0.39 -0.82,0.68 -0.21,0.29 -0.37,0.63 -0.47,1.02 -0.1,0.39 -0.15,0.82 -0.15,1.28 v 4.9 h -1.07 v -8.77 h 0.99 z" id="path190" style="fill:#00a099"></path>
<path class="st0" d="m 274.43,477.31 c 0.11,0.41 0.28,0.79 0.52,1.11 0.24,0.33 0.54,0.6 0.9,0.82 0.36,0.21 0.8,0.32 1.31,0.32 0.78,0 1.39,-0.2 1.84,-0.61 0.45,-0.41 0.75,-0.95 0.92,-1.63 h 1.07 c -0.23,1 -0.64,1.77 -1.25,2.31 -0.61,0.54 -1.46,0.82 -2.58,0.82 -0.69,0 -1.29,-0.12 -1.79,-0.37 -0.5,-0.24 -0.92,-0.58 -1.23,-1 -0.32,-0.42 -0.55,-0.92 -0.71,-1.48 -0.15,-0.56 -0.23,-1.15 -0.23,-1.78 0,-0.58 0.08,-1.14 0.23,-1.7 0.15,-0.56 0.39,-1.05 0.71,-1.49 0.32,-0.44 0.73,-0.79 1.23,-1.05 0.5,-0.27 1.1,-0.4 1.79,-0.4 0.7,0 1.3,0.14 1.8,0.43 0.5,0.29 0.9,0.65 1.22,1.11 0.32,0.46 0.54,0.99 0.67,1.58 0.14,0.59 0.19,1.2 0.17,1.81 h -6.75 c -0.01,0.38 0.05,0.78 0.16,1.2 z m 5.3,-3.28 c -0.13,-0.37 -0.31,-0.71 -0.55,-0.99 -0.24,-0.29 -0.53,-0.52 -0.87,-0.7 -0.34,-0.18 -0.73,-0.26 -1.16,-0.26 -0.44,0 -0.83,0.09 -1.17,0.26 -0.34,0.17 -0.63,0.41 -0.87,0.7 -0.24,0.29 -0.43,0.62 -0.57,1 -0.14,0.38 -0.24,0.77 -0.28,1.16 h 5.68 c -0.01,-0.4 -0.08,-0.79 -0.21,-1.17 z" id="path192" style="fill:#00a099"></path>
<path class="st0" d="m 283.51,471.43 v 1.51 h 0.03 c 0.2,-0.53 0.57,-0.96 1.09,-1.28 0.52,-0.32 1.09,-0.48 1.72,-0.48 0.61,0 1.12,0.08 1.54,0.24 0.41,0.16 0.75,0.38 1,0.67 0.25,0.29 0.42,0.64 0.53,1.06 0.1,0.42 0.15,0.89 0.15,1.41 v 5.64 h -1.07 v -5.47 c 0,-0.37 -0.03,-0.72 -0.1,-1.05 -0.07,-0.33 -0.19,-0.6 -0.36,-0.84 -0.17,-0.24 -0.4,-0.42 -0.69,-0.56 -0.29,-0.14 -0.65,-0.2 -1.08,-0.2 -0.43,0 -0.81,0.08 -1.15,0.23 -0.33,0.15 -0.62,0.36 -0.85,0.63 -0.23,0.27 -0.41,0.58 -0.54,0.95 -0.13,0.37 -0.2,0.77 -0.21,1.2 v 5.12 h -1.07 v -8.77 h 1.06 z" id="path194" style="fill:#00a099"></path>
<path class="st0" d="m 295.07,471.43 v 0.9 h -1.79 v 5.92 c 0,0.35 0.05,0.63 0.14,0.82 0.1,0.2 0.34,0.31 0.72,0.33 0.31,0 0.61,-0.02 0.92,-0.05 v 0.9 c -0.16,0 -0.32,0.01 -0.48,0.02 -0.16,0.01 -0.32,0.02 -0.48,0.02 -0.71,0 -1.21,-0.14 -1.5,-0.42 -0.28,-0.28 -0.42,-0.79 -0.41,-1.54 v -6 h -1.53 v -0.9 h 1.53 v -2.63 h 1.07 v 2.63 z" id="path196" style="fill:#00a099"></path>
<path class="st0" d="m 302.1,471.55 c 0.52,0.25 0.95,0.58 1.3,1 0.35,0.42 0.62,0.91 0.8,1.47 0.18,0.56 0.27,1.16 0.27,1.79 0,0.63 -0.09,1.23 -0.27,1.79 -0.18,0.56 -0.45,1.05 -0.8,1.47 -0.35,0.42 -0.78,0.75 -1.3,0.99 -0.52,0.24 -1.11,0.37 -1.78,0.37 -0.67,0 -1.26,-0.12 -1.78,-0.37 -0.52,-0.24 -0.95,-0.57 -1.3,-0.99 -0.35,-0.42 -0.62,-0.91 -0.8,-1.47 -0.18,-0.56 -0.27,-1.16 -0.27,-1.79 0,-0.63 0.09,-1.23 0.27,-1.79 0.18,-0.56 0.45,-1.05 0.8,-1.47 0.35,-0.42 0.78,-0.75 1.3,-1 0.52,-0.25 1.11,-0.37 1.78,-0.37 0.67,0 1.26,0.12 1.78,0.37 z m -3.12,0.85 c -0.38,0.21 -0.71,0.5 -0.96,0.85 -0.25,0.35 -0.45,0.75 -0.58,1.2 -0.13,0.45 -0.2,0.9 -0.2,1.37 0,0.47 0.06,0.92 0.2,1.37 0.13,0.45 0.32,0.85 0.58,1.2 0.25,0.35 0.58,0.63 0.96,0.85 0.39,0.21 0.83,0.32 1.34,0.32 0.51,0 0.96,-0.11 1.34,-0.32 0.38,-0.22 0.71,-0.5 0.96,-0.85 0.25,-0.35 0.45,-0.75 0.58,-1.2 0.13,-0.45 0.2,-0.9 0.2,-1.37 0,-0.47 -0.07,-0.92 -0.2,-1.37 -0.13,-0.45 -0.32,-0.85 -0.58,-1.2 -0.25,-0.35 -0.58,-0.63 -0.96,-0.85 -0.39,-0.22 -0.83,-0.32 -1.34,-0.32 -0.51,0 -0.95,0.11 -1.34,0.32 z" id="path198" style="fill:#00a099"></path>
<path class="st0" d="m 311.12,473.14 c -0.12,-0.24 -0.29,-0.44 -0.5,-0.6 -0.21,-0.16 -0.45,-0.27 -0.72,-0.35 -0.27,-0.07 -0.56,-0.11 -0.87,-0.11 -0.24,0 -0.48,0.03 -0.72,0.08 -0.24,0.05 -0.47,0.14 -0.67,0.25 -0.2,0.12 -0.37,0.28 -0.49,0.47 -0.12,0.19 -0.19,0.43 -0.19,0.71 0,0.24 0.06,0.44 0.18,0.6 0.12,0.17 0.27,0.3 0.45,0.42 0.18,0.11 0.38,0.21 0.59,0.28 0.21,0.07 0.41,0.13 0.59,0.18 l 1.43,0.32 c 0.31,0.04 0.61,0.13 0.91,0.25 0.3,0.12 0.57,0.27 0.8,0.47 0.23,0.19 0.42,0.43 0.57,0.71 0.15,0.28 0.22,0.62 0.22,1 0,0.48 -0.11,0.88 -0.32,1.22 -0.22,0.33 -0.49,0.61 -0.82,0.82 -0.33,0.21 -0.71,0.36 -1.13,0.45 -0.42,0.09 -0.83,0.14 -1.24,0.14 -1.03,0 -1.87,-0.24 -2.51,-0.73 -0.64,-0.49 -1.01,-1.27 -1.1,-2.35 h 1.07 c 0.05,0.73 0.31,1.27 0.79,1.64 0.48,0.37 1.08,0.55 1.79,0.55 0.26,0 0.53,-0.03 0.81,-0.08 0.28,-0.06 0.54,-0.15 0.77,-0.29 0.24,-0.14 0.43,-0.31 0.59,-0.52 0.15,-0.21 0.23,-0.47 0.23,-0.77 0,-0.26 -0.05,-0.48 -0.16,-0.66 -0.11,-0.17 -0.25,-0.32 -0.43,-0.44 -0.18,-0.12 -0.39,-0.22 -0.62,-0.3 -0.23,-0.08 -0.47,-0.15 -0.71,-0.2 l -1.38,-0.31 c -0.35,-0.09 -0.67,-0.2 -0.97,-0.31 -0.29,-0.12 -0.55,-0.27 -0.77,-0.44 -0.22,-0.18 -0.39,-0.39 -0.52,-0.65 -0.12,-0.25 -0.19,-0.57 -0.19,-0.94 0,-0.44 0.1,-0.82 0.3,-1.14 0.2,-0.32 0.46,-0.57 0.77,-0.76 0.32,-0.19 0.67,-0.33 1.06,-0.42 0.39,-0.09 0.78,-0.14 1.16,-0.14 0.44,0 0.85,0.06 1.23,0.17 0.38,0.11 0.71,0.29 1,0.53 0.29,0.24 0.52,0.53 0.69,0.88 0.17,0.35 0.27,0.77 0.29,1.24 h -1.07 c 0,-0.34 -0.07,-0.63 -0.19,-0.87 z" id="path200" style="fill:#00a099"></path>
<path class="st0" d="m 322.46,471.43 v 0.9 h -1.79 v 5.92 c 0,0.35 0.05,0.63 0.14,0.82 0.1,0.2 0.34,0.31 0.72,0.33 0.31,0 0.61,-0.02 0.92,-0.05 v 0.9 c -0.16,0 -0.32,0.01 -0.48,0.02 -0.16,0.01 -0.32,0.02 -0.48,0.02 -0.71,0 -1.21,-0.14 -1.5,-0.42 -0.28,-0.28 -0.42,-0.79 -0.41,-1.54 v -6 h -1.53 v -0.9 h 1.53 v -2.63 h 1.07 v 2.63 z" id="path202" style="fill:#00a099"></path>
<path class="st0" d="m 330.12,480.2 v -1.58 h -0.03 c -0.28,0.59 -0.69,1.04 -1.23,1.35 -0.54,0.31 -1.14,0.47 -1.79,0.47 -0.56,0 -1.03,-0.08 -1.42,-0.23 -0.39,-0.15 -0.71,-0.37 -0.95,-0.66 -0.24,-0.28 -0.42,-0.63 -0.54,-1.04 -0.11,-0.41 -0.17,-0.87 -0.17,-1.39 v -5.7 h 1.07 v 5.71 c 0.02,0.79 0.21,1.39 0.55,1.8 0.34,0.41 0.94,0.61 1.79,0.61 0.46,0 0.86,-0.1 1.19,-0.3 0.33,-0.2 0.6,-0.46 0.82,-0.79 0.22,-0.33 0.37,-0.71 0.48,-1.13 0.1,-0.42 0.15,-0.86 0.15,-1.3 v -4.61 h 1.07 v 8.77 h -0.99 z" id="path204" style="fill:#00a099"></path>
<path class="st0" d="m 334.12,471.43 v 2.06 h 0.03 c 0.27,-0.71 0.69,-1.26 1.27,-1.65 0.57,-0.38 1.25,-0.56 2.05,-0.53 v 1.07 c -0.49,-0.02 -0.93,0.04 -1.33,0.2 -0.4,0.15 -0.74,0.37 -1.03,0.65 -0.29,0.28 -0.51,0.62 -0.67,1.01 -0.16,0.39 -0.24,0.82 -0.24,1.28 v 4.67 h -1.07 v -8.77 h 0.99 z" id="path206" style="fill:#00a099"></path>
<path class="st0" d="m 338.03,470.21 1.79,-2.4 h 1.33 l -2.24,2.4 z m 0.48,1.22 h 1.07 v 8.77 h -1.07 z" id="path208" style="fill:#00a099"></path>
<path class="st0" d="m 346.68,473.14 c -0.12,-0.24 -0.29,-0.44 -0.5,-0.6 -0.21,-0.16 -0.45,-0.27 -0.72,-0.35 -0.27,-0.07 -0.56,-0.11 -0.87,-0.11 -0.24,0 -0.48,0.03 -0.72,0.08 -0.24,0.05 -0.47,0.14 -0.67,0.25 -0.2,0.12 -0.37,0.28 -0.49,0.47 -0.12,0.19 -0.19,0.43 -0.19,0.71 0,0.24 0.06,0.44 0.18,0.6 0.12,0.17 0.27,0.3 0.45,0.42 0.18,0.11 0.38,0.21 0.59,0.28 0.21,0.07 0.41,0.13 0.59,0.18 l 1.43,0.32 c 0.31,0.04 0.61,0.13 0.91,0.25 0.3,0.12 0.57,0.27 0.8,0.47 0.23,0.19 0.42,0.43 0.57,0.71 0.15,0.28 0.22,0.62 0.22,1 0,0.48 -0.11,0.88 -0.32,1.22 -0.22,0.33 -0.49,0.61 -0.82,0.82 -0.33,0.21 -0.71,0.36 -1.13,0.45 -0.42,0.09 -0.83,0.14 -1.24,0.14 -1.03,0 -1.87,-0.24 -2.51,-0.73 -0.64,-0.49 -1.01,-1.27 -1.1,-2.35 h 1.07 c 0.05,0.73 0.31,1.27 0.79,1.64 0.48,0.37 1.08,0.55 1.79,0.55 0.26,0 0.53,-0.03 0.81,-0.08 0.28,-0.06 0.54,-0.15 0.77,-0.29 0.24,-0.14 0.43,-0.31 0.59,-0.52 0.15,-0.21 0.23,-0.47 0.23,-0.77 0,-0.26 -0.05,-0.48 -0.16,-0.66 -0.11,-0.17 -0.25,-0.32 -0.43,-0.44 -0.18,-0.12 -0.39,-0.22 -0.62,-0.3 -0.23,-0.08 -0.47,-0.15 -0.71,-0.2 l -1.38,-0.31 c -0.35,-0.09 -0.67,-0.2 -0.97,-0.31 -0.29,-0.12 -0.55,-0.27 -0.77,-0.44 -0.22,-0.18 -0.39,-0.39 -0.52,-0.65 -0.12,-0.25 -0.19,-0.57 -0.19,-0.94 0,-0.44 0.1,-0.82 0.3,-1.14 0.2,-0.32 0.46,-0.57 0.77,-0.76 0.32,-0.19 0.67,-0.33 1.06,-0.42 0.39,-0.09 0.78,-0.14 1.16,-0.14 0.44,0 0.85,0.06 1.23,0.17 0.38,0.11 0.71,0.29 1,0.53 0.29,0.24 0.52,0.53 0.69,0.88 0.17,0.35 0.27,0.77 0.29,1.24 h -1.07 c 0,-0.34 -0.06,-0.63 -0.19,-0.87 z" id="path210" style="fill:#00a099"></path>
<path class="st0" d="m 353.29,471.43 v 0.9 h -1.79 v 5.92 c 0,0.35 0.05,0.63 0.14,0.82 0.1,0.2 0.34,0.31 0.72,0.33 0.31,0 0.61,-0.02 0.92,-0.05 v 0.9 c -0.16,0 -0.32,0.01 -0.48,0.02 -0.16,0.01 -0.32,0.02 -0.48,0.02 -0.71,0 -1.21,-0.14 -1.5,-0.42 -0.28,-0.28 -0.42,-0.79 -0.41,-1.54 v -6 h -1.53 v -0.9 h 1.53 v -2.63 h 1.07 v 2.63 z" id="path212" style="fill:#00a099"></path>
<path class="st0" d="m 355.93,468.07 v 1.72 h -1.07 v -1.72 z m 0,3.36 v 8.77 h -1.07 v -8.77 z" id="path214" style="fill:#00a099"></path>
<path class="st0" d="m 363.36,472.64 c -0.4,-0.37 -0.95,-0.56 -1.67,-0.56 -0.51,0 -0.96,0.11 -1.34,0.32 -0.38,0.21 -0.71,0.5 -0.96,0.85 -0.25,0.35 -0.45,0.75 -0.58,1.2 -0.13,0.45 -0.2,0.9 -0.2,1.37 0,0.47 0.06,0.92 0.2,1.37 0.13,0.45 0.32,0.85 0.58,1.2 0.25,0.35 0.58,0.63 0.96,0.85 0.39,0.21 0.83,0.32 1.34,0.32 0.33,0 0.64,-0.06 0.94,-0.19 0.3,-0.13 0.55,-0.3 0.78,-0.52 0.23,-0.22 0.41,-0.48 0.56,-0.79 0.15,-0.31 0.24,-0.64 0.27,-1 h 1.07 c -0.15,1.07 -0.54,1.9 -1.17,2.49 -0.63,0.59 -1.45,0.89 -2.45,0.89 -0.67,0 -1.26,-0.12 -1.78,-0.37 -0.52,-0.24 -0.95,-0.57 -1.3,-0.99 -0.35,-0.42 -0.62,-0.91 -0.8,-1.47 -0.18,-0.56 -0.27,-1.16 -0.27,-1.79 0,-0.63 0.09,-1.23 0.27,-1.79 0.18,-0.56 0.45,-1.05 0.8,-1.47 0.35,-0.42 0.78,-0.75 1.3,-1 0.52,-0.25 1.11,-0.37 1.78,-0.37 0.94,0 1.74,0.25 2.39,0.75 0.65,0.5 1.04,1.25 1.17,2.26 h -1.07 c -0.15,-0.67 -0.42,-1.19 -0.82,-1.56 z" id="path216" style="fill:#00a099"></path>
<path class="st0" d="m 372.29,471.55 c 0.52,0.25 0.95,0.58 1.3,1 0.35,0.42 0.62,0.91 0.8,1.47 0.18,0.56 0.27,1.16 0.27,1.79 0,0.63 -0.09,1.23 -0.27,1.79 -0.18,0.56 -0.45,1.05 -0.8,1.47 -0.35,0.42 -0.78,0.75 -1.3,0.99 -0.52,0.24 -1.11,0.37 -1.78,0.37 -0.67,0 -1.26,-0.12 -1.78,-0.37 -0.52,-0.24 -0.95,-0.57 -1.3,-0.99 -0.35,-0.42 -0.62,-0.91 -0.8,-1.47 -0.18,-0.56 -0.27,-1.16 -0.27,-1.79 0,-0.63 0.09,-1.23 0.27,-1.79 0.18,-0.56 0.45,-1.05 0.8,-1.47 0.35,-0.42 0.78,-0.75 1.3,-1 0.52,-0.25 1.11,-0.37 1.78,-0.37 0.67,0 1.27,0.12 1.78,0.37 z m -3.12,0.85 c -0.38,0.21 -0.71,0.5 -0.96,0.85 -0.25,0.35 -0.45,0.75 -0.58,1.2 -0.13,0.45 -0.2,0.9 -0.2,1.37 0,0.47 0.06,0.92 0.2,1.37 0.13,0.45 0.32,0.85 0.58,1.2 0.25,0.35 0.58,0.63 0.96,0.85 0.39,0.21 0.83,0.32 1.34,0.32 0.51,0 0.96,-0.11 1.34,-0.32 0.38,-0.22 0.71,-0.5 0.96,-0.85 0.25,-0.35 0.45,-0.75 0.58,-1.2 0.13,-0.45 0.2,-0.9 0.2,-1.37 0,-0.47 -0.07,-0.92 -0.2,-1.37 -0.13,-0.45 -0.32,-0.85 -0.58,-1.2 -0.25,-0.35 -0.58,-0.63 -0.96,-0.85 -0.39,-0.22 -0.83,-0.32 -1.34,-0.32 -0.5,0 -0.95,0.11 -1.34,0.32 z" id="path218" style="fill:#00a099"></path>
<path class="st0" d="m 381.31,473.14 c -0.12,-0.24 -0.29,-0.44 -0.5,-0.6 -0.21,-0.16 -0.45,-0.27 -0.72,-0.35 -0.27,-0.07 -0.56,-0.11 -0.87,-0.11 -0.24,0 -0.48,0.03 -0.72,0.08 -0.24,0.05 -0.47,0.14 -0.67,0.25 -0.2,0.12 -0.37,0.28 -0.49,0.47 -0.12,0.19 -0.19,0.43 -0.19,0.71 0,0.24 0.06,0.44 0.18,0.6 0.12,0.17 0.27,0.3 0.45,0.42 0.18,0.11 0.38,0.21 0.59,0.28 0.21,0.07 0.41,0.13 0.59,0.18 l 1.43,0.32 c 0.31,0.04 0.61,0.13 0.91,0.25 0.3,0.12 0.57,0.27 0.8,0.47 0.23,0.19 0.42,0.43 0.57,0.71 0.15,0.28 0.22,0.62 0.22,1 0,0.48 -0.11,0.88 -0.32,1.22 -0.22,0.33 -0.49,0.61 -0.82,0.82 -0.33,0.21 -0.71,0.36 -1.13,0.45 -0.42,0.09 -0.83,0.14 -1.24,0.14 -1.03,0 -1.87,-0.24 -2.51,-0.73 -0.64,-0.49 -1.01,-1.27 -1.1,-2.35 h 1.07 c 0.05,0.73 0.31,1.27 0.79,1.64 0.48,0.37 1.08,0.55 1.79,0.55 0.26,0 0.53,-0.03 0.81,-0.08 0.28,-0.06 0.54,-0.15 0.77,-0.29 0.24,-0.14 0.43,-0.31 0.59,-0.52 0.15,-0.21 0.23,-0.47 0.23,-0.77 0,-0.26 -0.05,-0.48 -0.16,-0.66 -0.11,-0.17 -0.25,-0.32 -0.43,-0.44 -0.18,-0.12 -0.39,-0.22 -0.62,-0.3 -0.23,-0.08 -0.47,-0.15 -0.71,-0.2 l -1.38,-0.31 c -0.35,-0.09 -0.67,-0.2 -0.97,-0.31 -0.29,-0.12 -0.55,-0.27 -0.77,-0.44 -0.22,-0.18 -0.39,-0.39 -0.52,-0.65 -0.12,-0.25 -0.19,-0.57 -0.19,-0.94 0,-0.44 0.1,-0.82 0.3,-1.14 0.2,-0.32 0.46,-0.57 0.77,-0.76 0.32,-0.19 0.67,-0.33 1.06,-0.42 0.39,-0.09 0.78,-0.14 1.16,-0.14 0.44,0 0.85,0.06 1.23,0.17 0.38,0.11 0.71,0.29 1,0.53 0.29,0.24 0.52,0.53 0.69,0.88 0.17,0.35 0.27,0.77 0.29,1.24 h -1.07 c 0,-0.34 -0.07,-0.63 -0.19,-0.87 z" id="path220" style="fill:#00a099"></path>
</g>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 45 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

26
site/init.php Normal file
View file

@ -0,0 +1,26 @@
<?php namespace ProcessWire;
if(!defined("PROCESSWIRE")) die();
/** @var ProcessWire $wire */
/**
* ProcessWire Bootstrap Initialization
* ====================================
* This init.php file is called during ProcessWire bootstrap initialization process.
* This occurs after all autoload modules have been initialized, but before the current page
* has been determined. This is a good place to attach hooks. You may place whatever you'd
* like in this file. For example:
*
* $wire->addHookAfter('Page::render', function($event) {
* $event->return = str_replace("</body>", "<p>Hello World</p></body>", $event->return);
* });
*
*/
$wire->addHookAfter('Pages::added', function($event)
{
$page = $event->arguments(0);
foreach ($this->wire->languages as $lang) $page->set("status$lang", 1);
$page->save();
});

View file

@ -1,4 +0,0 @@
# Auto detect text files and perform LF normalization
* text=auto
# Show correct language for ProcessWire .module
*.module linguist-language=PHP

View file

@ -1,5 +0,0 @@
dematte/*
jscolor-2.0.4/*
colorpicker/*
InputfieldColor.js
.DS_Store

View file

@ -1,336 +0,0 @@
<?php namespace ProcessWire;
/**
* ProcessWire Color Fieldtype
* Field that stores an 32Bit unsigned integer value to hold RGB colors and Alpha channel
*
* @author Christoph Thelen aka @kixe 2017/07/03
* @copyright © 2017 Christoph Thelen
* @license Licensed under GNU/GPL v3
* @link https://processwire.com/talk/topic/...
* @version 1.1.8
*
*
* @since 1.0.1 2017/07/05 - better validation, spectrum options modifiable
* @since 1.0.2 2017/07/09 - added default value option
* @since 1.0.3 2017/07/09 - added option for custom javascript
* @since 1.0.4 2017/08/18 - made # optional for input (pattern attribute)
* @since 1.0.5 2017/08/28 - optimized default color handling, added output format option array()
* @since 1.0.6 2017/10/07 - changed dec to hex conversion in function wakeupValue() from dechex() to base_convert() to be safe on 32bit systems
* @since 1.0.7 2017/10/08 - changed dec to hex conversion in function wakeupValue() from dechex() to custom function to be safe on 32bit systems
* @since 1.0.8 2018/09/08 - Installation error if PHP is running on 32-bit system and BCMath extension is not installed
* @since 1.0.9 2019/01/12 - fixed number format bug for rgba() and hsla() alpha channel if comma is forced as decimal separator by locale settings
* @since 1.1.0 2019/08/12 - better input check formatColorString()
* @since 1.1.1 2019/09/01 - fixed bug missing opacity if 0
* @since 1.1.2 2019/09/04 - fixed bug #5 FieldtypeColor index typo in var in function RGB2HSL() thanks to @junoforno
* @since 1.1.3 2019/10/10 - fixed bug #1 InputfieldColor - remove pattern attribute if spectrum color picker is used to prevent error in Chrome
* @since 1.1.4 2020/03/21 - fixed number format bug for hsl() output: use dot instead of comma as decimal separator independent from language setup
* @since 1.1.5 2020/05/15 switched to ProcessWire namespace
* @since 1.1.6 2021/10/04 added comparison functions getClosestColorName(), getColorDistance(), getLuminanceDistance()
* @since 1.1.7 2021/10/10 added output format option: array([0,255], [0,255], [0,255]) indexed array: R,G,B
* @since 1.1.8 2023/07/17 added output format option: array([0,255], [0,255], [0,255]) indexed array: H,S,L
*
* made for ProcessWire 3.x by Ryan Cramer
* https://processwire.com
*
*/
class FieldtypeColor extends Fieldtype {
public static function getModuleInfo() {
return array(
'title' => 'Color',
'version' => 118,
'summary' => 'Field that stores a color value as 32bit integer reflecting a RGBA value. Many options for Input (HTML5 Inputfield Color, Textfield with changing background, various jQuery/JS ColorPickers, custom jQuery/JS/CSS) and Output (RGB, RGBA, HSL, HSLA, HEX, Array).',
'installs' => 'InputfieldColor',
'href' => 'https://processwire.com/talk/topic/16679-fieldtypecolor/'
);
}
public function ___getCompatibleFieldtypes(Field $field) {
$fieldtypes = $this->wire(new Fieldtypes());
foreach($this->wire('fieldtypes') as $fieldtype) {
if(!$fieldtype instanceof FieldtypeInteger &&
!$fieldtype instanceof FieldtypeColor &&
$fieldtype != 'FieldtypeText') {
$fieldtypes->remove($fieldtype);
}
}
return $fieldtypes;
}
public function getInputfield(Page $page, Field $field) {
$inputfield = $this->modules->get('InputfieldColor');
$inputfield->initValue = $this->sanitizeValue($page, $field, $field->defaultValue);
$inputfield->class = $this->className();
return $inputfield;
}
public function sanitizeValue(Page $page, Field $field, $value) {
if (!$value) return $value;
$value = ltrim($value, '#');
if (strlen($value) == 8) return $value;
else if (strlen($value) == 6) return 'ff'.$value; // add alpha channel
else throw New WireException('Expecting Hex color string (length 6 or 8 digits) with optional leading \'#\'');
}
public function sleepValue(Page $page, Field $field, $value) {
return hexdec($value);
}
public function wakeupValue(Page $page, Field $field, $value) {
if (!$value) return $value;
if (function_exists("bcmod")) return str_pad(self::bcdechex($value), 8, '0', STR_PAD_LEFT); // BCMath extension required
return str_pad(dechex($value), 8, '0', STR_PAD_LEFT); // 64-bit system required
}
/**
* Converts a number from decimal to hex (BCMath extension required)
* returns precice result even if number is bigger than PHP_INT_MAX (safe for 32bit systems)
*
* @param int/string/float number
* @return string
*
* @see http://php.net/manual/en/ref.bc.php#99130
*/
public static function bcdechex($dec) {
$last = bcmod("$dec", 16);
$remain = bcdiv(bcsub("$dec", $last), 16);
if($remain == 0) return dechex($last);
else return self::bcdechex($remain).dechex($last);
}
/**
* Converts a RGB color value to HSL. Conversion formula
* @param array of 3 color values R, G, and B [0, 255]
* @return array The HSL representation
*
* @see https://stackoverflow.com/questions/2353211/hsl-to-rgb-color-conversion/9493060#9493060
* @see http://en.wikipedia.org/wiki/HSL_color_space
*/
public function RGB2HSL(array $rgb) {
$rgb = array_map(function($v) { return $v/ 255; }, $rgb);
$max = max($rgb);
$min = min($rgb);
$hue = $sat = $light = ($max + $min) / 2;
if($max == $min) {
$hue = $sat = 0; // achromatic
} else {
$d = $max - $min;
$sat = $light > 0.5 ? $d / (2 - $max - $min) : $d / ($max + $min);
switch($max) {
case $rgb[0]:
$hue = ($rgb[1] - $rgb[2]) / $d + ($rgb[1] < $rgb[1] ? 6 : 0);
break;
case $rgb[1]:
$hue = ($rgb[2] - $rgb[0]) / $d + 2;
break;
case $rgb[2]:
$hue = ($rgb[0] - $rgb[1]) / $d + 4;
break;
}
$hue = $hue / 6;
}
// round and convert float to string with dot as decimal separator in any language
$hue = str_replace(',', '.', round($hue * 360));
$sat = str_replace(',', '.', round($sat * 100, 1));
$light = str_replace(',', '.', round($light * 100, 1));
return [$hue, $sat, $light];
}
/**
* Find the "naive" difference between two colors.
* @see https://php.tutorialink.com/finding-nearest-match-rgb-color-from-array-of-colors/
* @param int[] $color_a Three-element array with R,G,B color values 0-255.
* @param int[] $color_b Three-element array with R,G,B color values 0-255.
* @return int
*/
public function getColorDistance(array $color_a, array $color_b): int {
return
abs($color_a[0] - $color_b[0]) +
abs($color_a[1] - $color_b[1]) +
abs($color_a[2] - $color_b[2]);
}
/**
* Find the difference between two colors' luminance values.
* @see https://php.tutorialink.com/finding-nearest-match-rgb-color-from-array-of-colors/
* @param int[] $color_a Three-element array with R,G,B color values 0-255.
* @param int[] $color_b Three-element array with R,G,B color values 0-255.
* @return int
*/
public function getLuminanceDistance(array $color_a, array $color_b): int {
$luminance_f = function ($red, $green, $blue): int {
// Source: https://en.wikipedia.org/wiki/Relative_luminance
$luminance = (int) (0.2126 * $red + 0.7152 * $green + 0.0722 * $blue);
return $luminance;
};
return abs(
$luminance_f($color_a[0], $color_a[1], $color_a[2]) -
$luminance_f($color_b[0], $color_b[1], $color_b[2])
);
}
/**
* Find the closest named color
* @param hexcolor
* @return string
*/
public function getClosestColorName(string $color) {
$color = ltrim($color, '#');
if (strlen($color) == 6) $color = "ff$color";
if (strlen($color) != 8) throw new WireException("Invalid parameter. Expected hex string of 6 or 8 digits length with or without leading '#'.");
$color = $this->formatColorString($color, 9);
$palette = json_decode(file_get_contents(__DIR__ . '/colornames.json'), true);
$min = 765;
$match = null;
foreach ($palette as $name => $pcolor) {
$pcolor = $this->formatColorString("ff$pcolor", 9);
if ($pcolor === $color) return $name; // quick exit if full match
$distance = $this->getColorDistance($pcolor, $color);
if ($distance >= $min) continue;
$min = $distance;
$match = $name;
}
return $match;
}
/**
* Format value for output
*
*/
public function ___formatValue(Page $page, Field $field, $value) {
if (!$value) return null;
if ($field->outputFormat === 7) return $this->sleepValue($page, $field, $value);
return $this->formatColorString($value, $field->outputFormat);
}
/**
* Format color string
*
* @param $value string - hex string of 8 chiffres, first 2 is the alpha channel
* @param $of int - output format
* @return string formatted color string
* @throws object WireException - if input doesn't match (check for length, detailed check in debug mode)
*
*/
public function formatColorString($value, $of = 0) {
// simple length check or preg_match in debug mode
if (strlen($value) != 8 || ($this->wire('config')->debug && !preg_match('/[A-Fa-f0-9]{8}/', $value))) {
throw new WireException("Invalid input: $value. Expected hex string of 8 digits length.");
}
if ($of === 6) return $value;
if ($of === 0) return "#".substr($value,2);
if ($of === 1) return "#".$value;
$hexVals = str_split($value, 2);
$value = array_map('hexdec', $hexVals);
// opacity
$opacity = '0';
if ($value[0] > 1 && in_array($of ,array(3,5,8,10,12))) {
$opacity = round($value[0] / 255, 2); // float
$opacity = rtrim(number_format($opacity, 2, '.', ''),'.0'); // convert float to string with dot as decimal separator
}
if ($of === 9) return [$value[1], $value[2], $value[3]];
if ($of === 10) return [$value[1], $value[2], $value[3], $opacity];
if ($of === 8) {
$assocArray = array(
'o' => $opacity,
'r' => $value[1],
'g' => $value[2],
'b' => $value[3],
'ox' => $hexVals[0],
'rx' => $hexVals[1],
'gx' => $hexVals[2],
'bx' => $hexVals[3],
);
return array_merge($value, $assocArray);
}
if ($of === 2) return "rgb($value[1], $value[2], $value[3])";
if ($of === 3) return "rgba($value[1], $value[2], $value[3], $opacity)";
$hsl = $this->RGB2HSL(array_slice($value,1,3));
if ($of === 11) return $hsl;
if ($of === 12) {
$hsla = $hsl;
$hsla[] = $opacity;
return $hsla;
}
if ($of === 4) return "hsl($hsl[0], $hsl[1]%, $hsl[2]%)";
if ($of === 5) return "hsla($hsl[0], $hsl[1]%, $hsl[2]%, $opacity)";
}
public function getDatabaseSchema(Field $field) {
$schema = parent::getDatabaseSchema($field);
$schema['data'] = "int UNSIGNED NOT NULL";
return $schema;
}
public function ___getConfigInputfields(Field $field) {
$inputfields = $this->wire(new InputfieldWrapper());
$f = $this->wire('modules')->get('InputfieldRadios');
$f->attr('name', 'outputFormat');
$f->label = $this->_('Output Format');
$f->description = $this->_('Choose your preferred output format.');
$f->addOption(0, $this->_('string 6-digit hex color *#4496dd*'));
$f->addOption(1, $this->_('string 8-digit hex color *#fa4496dd* (limited browser support)'));
$f->addOption(2, $this->_('string *rgb(68, 100, 221)*'));
$f->addOption(3, $this->_('string *rgba(68, 100, 221, 0.98)*'));
$f->addOption(4, $this->_('string *hsl(227, 69.2%, 56.7%)*'));
$f->addOption(5, $this->_('string *hsla(227, 69.2%, 56.7%, 0.98)*'));
$f->addOption(6, $this->_('string 8-digit raw hex *fa4496dd* (unformatted)'));
$f->addOption(7, $this->_('int 32bit (storage)'));
$f->addOption(8, $this->_('array(r[0,255], g[0,255], b[0,255], o[0,1], rx[00,ff], gx[00,ff], bx[00,ff], ox[00,ff])'));
$f->addOption(9, $this->_('array([0,255], [0,255], [0,255]) indexed array: R,G,B'));
$f->addOption(10, $this->_('array([0,255], [0,255], [0,255], [0,1]) indexed array: R,G,B,Alpha'));
$f->addOption(11, $this->_('array([0,360], [69.2%], [56.7%]) indexed array: H,S,L'));
$f->addOption(12, $this->_('array([0,360], [69.2%], [56.7%], [0,1]) indexed array: H,S,L,Alpha'));
$f->attr('value', (int) $field->outputFormat);
$inputfields->add($f);
$f = $this->wire('modules')->get('InputfieldColor');
$f->attr('name', 'defaultValue');
$f->label = $this->_('Default value');
$f->inputType = $field->inputType;
$f->spectrum = $field->spectrum;
$f->initJS = $field->initJS;
$f->fileJS = $field->fileJS;
$f->fileCSS = $field->fileCSS;
$f->jqueryCore = $field->jqueryCore;
$f->jqueryUI = $field->jqueryUI;
$f->alpha = $field->alpha;
$f->description = $this->_('This value is assigned as the default for blank fields and on newly created pages.');
$f->collapsed = Inputfield::collapsedBlank;
$f->attr('value', strlen($field->defaultValue) ? $this->sanitizeValue($this->wire('page'), $field, $field->defaultValue) : null);
$inputfields->add($f);
return $inputfields;
}
public function ___install() {
if (function_exists("bcmod") === false && PHP_INT_SIZE < 8) {
throw new WireException($this->_('The BCMath extension is required if your system can not handle 64-bit integer values.'));
}
parent::___install();
}
}

View file

@ -1,9 +0,0 @@
.InputfieldColor input[type=color], input[type=color].FieldtypeColor, input[type=color]#Inputfield_defaultValue {
height:2em;
padding:0;
}
.AdminThemeUikit .InputfieldColor input[type=color], .AdminThemeUikit input[type=color].FieldtypeColor, .AdminThemeUikit input[type=color]#Inputfield_defaultValue {
height:40px;
width: 100% !important;
}

View file

@ -1,354 +0,0 @@
<?php namespace ProcessWire;
/**
* ProcessWire Color Inputfield
*
* @author Christoph Thelen aka @kixe 2017/07/03
* @copyright © 2017 Christoph Thelen
* @license Licensed under GNU/GPL v3
* @link https://processwire.com/talk/topic/...
* @version 1.1.6
*
* @since 1.0.1 2017/07/05 - better validation, spectrum options modifiable
* @since 1.0.2 2017/07/09 - added default value option
* @since 1.0.3 2017/07/09 - added option for custom javascript
* @since 1.0.4 2017/08/18 - made # optional for input (pattern attribute)
* @since 1.0.5 2017/08/28 - optimized default color handling, added output format option array()
* @since 1.0.6 2017/12/17 - modified render() for usage in modules config
* @since 1.0.7 2017/12/17 - sync version number to fieldtype
* @since 1.0.8 2018/08/31 - added functions getTextColor() convertColorName()
* @since 1.0.9 2019/01/12 - fixed number format bug for rgba() and hsla() alpha channel if comma is forced as decimal separator by locale settings, added data-input-type attribute for better JS handling
* @since 1.1.0 2019/08/12 - better input check formatColorString()
* @since 1.1.1 2019/09/01 - fixed bug missing opacity if 0
* @since 1.1.2 2019/09/04 - fixed bug #5 FieldtypeColor index typo in var in function RGB2HSL() thanks to @junoforno
* @since 1.1.3 2019/10/10 - fixed bug #1 InputfieldColor - remove pattern attribute if spectrum color picker is used to prevent error in Chrome
* @since 1.1.4 2020/05/15 switched to ProcessWire namespace
* @since 1.1.5 2021/10/10 set field value to 0 if the color parameter is null as a result of showEmpty option enabled on spectrum, bugfix (workaround): something went wrong in javascript spectrum
* @since 1.1.6 added option to disable alpha channel for spectrum color picker
*
* made for ProcessWire 3.x by Ryan Cramer
* https://processwire.com
*
* @todo
* - include i18n support provided by spectrum color picker
*
*/
class InputfieldColor extends Inputfield {
public static function getModuleInfo() {
return array(
'title' => __('Color', __FILE__), // Module Title
'summary' => __('Inputfield for colors', __FILE__), // Module Summary
'version' => 116,
'href' => 'https://processwire.com/talk/topic/16679-fieldtypecolor/'
);
}
/**
* Construct
*
* @throws WireException
*
*/
public function __construct() {
parent::__construct();
$this->set('icon', 'paint-brush');
$this->setAttribute('type', 'text');
$this->setAttribute('size', 10);
$this->setAttribute('placeholder', '#000000');
$this->setAttribute('pattern', '(#?[a-fA-F\d]{6})?');
}
public function init() {
$this->inputType = 0;
$this->spectrum = '';
$this->initJS = '';
$this->fileJS = '';
$this->fileCSS = '';
$this->jqueryCore = 0;
$this->jqueryUI = 0;
$this->alpha = 0; // int 0, 1 will be set dependend on inputType. To disable explicitly for inputType = 3 (spectrum color picker) set bool false
parent::init();
}
/**
* Called before the render method
* checking for SpectrumColorPicker
*
* @param Inputfield $parent
* @param bool $renderValueMode
* @return $this
*
*/
public function renderReady(Inputfield $parent = null, $renderValueMode = false) {
$url = $this->config->urls->get('InputfieldColor');
switch ($this->inputType) {
case 3:
$this->wire('modules')->get('JqueryCore');
$this->config->scripts->add($url . 'spectrum/spectrum.js');
$this->config->styles->add($url . 'spectrum/spectrum.css');
break;
case 4:
if ($this->jqueryCore) $this->wire('modules')->get('JqueryCore');
if ($this->jqueryUI) $this->wire('modules')->get('JqueryUI');
if ($this->fileJS) $this->config->scripts->add($url . $this->fileJS);
if ($this->fileCSS) $this->config->styles->add($url . $this->fileCSS);
break;
}
parent::renderReady($parent, $renderValueMode);
}
/**
* get textcolor (light or dark) corresponding to the background for better contrast
*
* @param int/string $bgColor expecting string or int with 6 (24bit) or 8 (32bit) digits with or without leading '#'
* @param int/string $textColorLight default: '#fff' (white)
* @param int/string $textColorDark default: '#000' (black)
* @return string $color light or dark
*
*/
public function getTextColor($bgColor, $textColorLight = '#fff', $textColorDark = '#000') {
if (!is_string($bgColor)) return $textColorDark;
else if (!ctype_xdigit(ltrim($bgColor, '#'))) {
$bgColor = $this->convertColorName($bgColor);
if (false === $bgColor) return $textColorDark;
}
$bgColor = ltrim($bgColor, '#');
$bgColor = str_pad($bgColor,8,'f',STR_PAD_LEFT);
$ARGB = array_map('hexdec', str_split($bgColor, 2));
$opacity = round($ARGB[0] / 255, 2);
if ($opacity < 0.45) return $textColorDark;
return ($ARGB[1]+6*$ARGB[2]+$ARGB[3])*3/8 > 460? $textColorDark : $textColorLight;
}
/**
* convert color name (hex -> html, html -> hex)
*
* @param $color
* @param $to convert to 'hex' or 'html'
* @return bool/ string
*
*/
public function convertColorName($color, $to = 'hex') {
$colorArray = $this->getX11ColorArray();
if ($to = 'hex') {
$key = array_search($color, array_column($colorArray, 0));
return empty($colorArray[$key][1])? false : $colorArray[$key][1];
}
else if ($to = 'html') {
$key = array_search($color, array_column($colorArray, 1));
return empty($colorArray[$key][0])? false : $colorArray[$key][0];
}
return false;
}
/**
* get multiple array with html color names and corresponding hex codes and rgb values
*
* @param $domain
* @param $path file path
* @return boolean
*
*/
protected function getX11ColorArray() {
$path = __DIR__ .'/x11color.txt';
if (!file_exists($path)) throw new WireException("Missing file " . $path);
$array = file($path, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
if ($array === false) throw new WireException("Failed to open file: $path");
return array_map(function($e) {
return explode("\t", $e);
}, $array);
}
public function ___render() {
if ($this->value === "" && strlen($this->initValue)) $this->value = $this->initValue;
if (!$this->value) $this->value = null;
if ($this->value) {
$this->value = str_pad(ltrim($this->value, '#'),8,'f',STR_PAD_LEFT);
$color32 = "#".$this->value;
$color24 = $bgColor = "#".substr($this->value,2,6);
$value = array_map('hexdec', str_split($this->value, 2));
} else {
$color32 = $color24 = null;
$value = array(255,255,255,255);
$bgColor = '#fff';
}
$opacity = round($value[0] / 255, 2);
$opacity = $opacity? rtrim(number_format($opacity, 2, '.', ''),'.0') : '0';
$textColor = $this->getTextColor($this->value);
$rgba = "rgba($value[1], $value[2], $value[3], $opacity)";
$this->attr('value', $color24);
$this->attr('data-input-type', $this->inputType);
switch ($this->inputType) {
case 0:
$this->attr('type', 'color');
break;
case 1:
$this->attr('style', "color: $textColor; background: $bgColor;");
break;
case 2:
$this->alpha = 1;
$this->attr('value', $color32);
$this->attr('style', "color: $textColor; background: $bgColor; background-image: linear-gradient($rgba, $rgba), url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAMCAIAAADZF8uwAAAAGUlEQVQYV2M4gwH+YwCGIasIUwhT25BVBADtzYNYrHvv4gAAAABJRU5ErkJggg==');");
$this->attr('placeholder', '#ff000000');
$this->attr('pattern', '(#?[a-fA-F\d]{8})?');
break;
case 3:
if ($this->alpha !== false) $this->alpha = 1;
if (!$color32) $color32 = '#00000000';
$this->attr('value', $color32);
$this->attr('placeholder', '#ff000000');
$this->removeAttr('pattern');
break;
case 4:
if ($this->alpha) $this->attr('value', $color32);
else $this->attr('value', $color24);
}
$attrs = $this->getAttributes();
$out = "<input " . $this->getAttributesString($attrs) . " />";
if( $this->inputType == 3) {
$options = $this->spectrum? str_replace(array(",\n","\n"),", ", trim($this->spectrum,",\t\n\r\0\x0B")).',' : '';
$value = $color32? $color32 : null;
$format = $this->alpha? 'toHex8String' : 'toHexString';
$out .= "<script>
$(\"#$this->id\").spectrum({
$options
color: \"$value\",
change: function(color) {
if (color === null) {
this.value = 0;
} else {
this.value = color.$format();
}
}
});
</script>
";
}
if( $this->inputType == 4) {
$value = $color32? $color32 : null;
if ($this->initJS) {
$initJS = str_replace(array("{value}","{id}"), array($color24, $this->id), $this->initJS);
$out .= "<script>
$initJS
</script>
";
}
}
return $out;
}
public function ___processInput(WireInputData $input) {
parent::___processInput($input);
$value = $this->attr('value');
if (!$value) return $this;
// bugfix (workaround): something went wrong in javascript spectrum
if (is_string($value) && in_array($value, ['hsva(0, 0%, 0%, 0)','hsla(0, 0%, 0%, 0)','rgba(0, 0, 0, 0)'])) {
$this->attr('value', '00000000');
return $this;
}
$pattern = $this->alpha? '/#?[a-fA-F\d]{8}/' : '/#?[a-fA-F\d]{6}/';
if(!preg_match($pattern, $value)) $this->error("Submitted value: $value does not match required pattern: $pattern.");
return $this;
}
public function getConfigInputfields() {
$inputfields = parent::getConfigInputfields();
$f = $this->wire('modules')->get('InputfieldRadios');
$f->attr('name', 'inputType');
$f->label = $this->_('Inputfieldtype');
$f->addOption(0, $this->_('Inputfield type=\'color\' (HTML5 - limited browser support)'));
$f->addOption(1, $this->_('Inputfield type=\'text\' expects 24bit hexcode strings'));
$f->addOption(2, $this->_('Inputfield type=\'text\' expects 32bit hexcode strings (alpha channel)'));
$f->addOption(3, $this->_('Inputfield with Spectrum Color Picker (JavaScript)'));
$f->addOption(4, $this->_('Inputfield type=\'text\' with custom JavaScript and/or CSS'));
$f->attr('value', $this->inputType);
$f->description = $this->_('');
$f->columnWidth = 50;
$inputfields->add($f);
$f = $this->wire('modules')->get('InputfieldTextarea');
$f->attr('name', 'spectrum');
$f->attr('rows', 10);
$f->label = $this->_('Color Picker Options');
$f->attr('value', $this->spectrum);
$f->description = $this->_('Set or modify options for the **Spectrum Color Picker**. [Read more ...](https://bgrins.github.io/spectrum/#options)');
$f->notes = $this->_("One option per line in the format: 'option: value'. The options: 'color' and 'change' are used by the system and not modifiable.");
$f->columnWidth = 50;
$f->showIf = "inputType=3";
$inputfields->add($f);
$f = $this->wire('modules')->get('InputfieldTextarea');
$f->attr('name', 'initJS');
$f->attr('rows', 3);
$f->label = $this->_('Initial JS');
$f->attr('value', $this->initJS);
$f->description = $this->_('JavaScript code initiating your custom JS color picker. Use {id} and {value} as placeholders for the related field attributes in your selector');
$f->notes = sprintf($this->_('{id} will be replaced by the string "%s"'), $this->id);
$f->columnWidth = 33;
$f->showIf = "inputType=4";
$f->requiredIf = "inputType=4";
$inputfields->add($f);
$rootUrl = $this->config->urls->get('InputfieldColor');
$f = $this->wire('modules')->get('InputfieldURL');
$f->attr('name', 'fileJS');
$f->label = $this->_('Include JS File');
$f->attr('value', $this->fileJS);
$f->description = $this->_('Set the path to your custom JavaScript file.');
$f->notes = sprintf($this->_('URL string relative to "%s"'), $rootUrl);
$f->columnWidth = 34;
$f->showIf = "inputType=4";
$f->requiredIf = "inputType=4";
$inputfields->add($f);
$f = $this->wire('modules')->get('InputfieldURL');
$f->attr('name', 'fileCSS');
$f->label = $this->_('Include CSS File');
$f->attr('value', $this->fileCSS);
$f->description = $this->_('Set the path to your custom stylesheet file.');
$f->notes = sprintf($this->_('URL string relative to "%s"'), $rootUrl);
$f->columnWidth = 33;
$f->showIf = "inputType=4";
$f->requiredIf = "inputType=4";
$inputfields->add($f);
$f = $this->modules->get('InputfieldCheckbox');
$f->attr('name', 'jqueryCore');
$f->label = __('Enable JqueryCore');
$f->attr('checked', $this->jqueryCore ? 'checked' : '' );
$f->columnWidth = 33;
$f->showIf = "inputType=4";
$inputfields->append($f);
$f = $this->modules->get('InputfieldCheckbox');
$f->attr('name', 'jqueryUI');
$f->label = __('Enable JqueryUI');
$f->attr('checked', $this->jqueryUI ? 'checked' : '' );
$f->columnWidth = 34;
$f->showIf = "inputType=4";
$inputfields->append($f);
$f = $this->modules->get('InputfieldRadios');
$f->attr('name', 'alpha');
$f->addOption(0, $this->_('6 digits "#ff0000"'));
$f->addOption(1, $this->_('8 digits "#ffff0000" (leading alpha channel)'));
$f->label = __('Select value type');
$f->attr('value', $this->alpha);
$f->columnWidth = 33;
$f->showIf = "inputType=4";
$inputfields->append($f);
return $inputfields;
}
}

View file

@ -1,107 +0,0 @@
FieldtypeColor
==============
## Fieldtype/Inputfield for ProcessWire 3.0
Field that stores colors. Many options for Input (HTML5 Inputfield Color, Textfield with changing background, various jQuery/JS ColorPickers, custom jQuery/JS/CSS) and Output (RGB, RGBA, HSL, HSLA, HEX). Package includes Fieldtype Color Select.
## Inputfield
Select between **5 types of Inputfields**
+ Html5 Inputfield of type='color' (if supported by browser)
+ Inputfield type='text' expecting a 24bit hexcode string (RGB). Input format: *'#4496dd'*
The background color of the input fields shows selected color
+ Inputfield of type='text' expecting 32bit hexcode strings (RGB + alpha channel) Input format: *'#fa4496dd'*
+ Inputfield with **Spectrum Color Picker** (JavaScript)
Options modifiable
+ Inputfield type='text' with **custom JavaScript** and/or CSS
## Output
Define output format under **Details** - Tab in field settings. Select from the following options:
+ *string* 6-digit hex color. Example: **'#4496dd'**
+ *string* 8-digit hex color with leading Alpha channel (limited browser support). Example: **'#fa4496dd'**
+ *string* CSS color value **RGB**. Example: **'rgb(68, 100, 221)'**
+ *string* CSS color value **RGBA**. Example: **'rgba(68, 100, 221, 0.98)'**
+ *string* CSS color value **HSL**. Example: **'hsl(227, 69.2%, 56.7%)'**
+ *string* CSS color value **HSLA**. Example: **'hsla(227, 69.2%, 56.7%, 0.98)'**
+ *string* 32bit raw hex value. Example: **'fa4496dd'** (unformatted output value)
+ *int 32bit*. Example: **'4198799069'** (storage value)
+ *array(R,G,B)*
+ *array(R,G,B,Alpha)*
+ *array(H,S,L)*
+ *array(H,S,L,Alpha)*
```
array(
[0] => 0-255, // opacity
[1],['r'] => 0-255,
[2],['g'] => 0-255,
[3],['b'] => 0-255,
['rx'] => 00-ff,
['gx'] => 00-ff,
['bx'] => 00-ff,
['ox'] => 00-ff, // opacity
['o'] => 0-1 // opacity
)
```
## Templates & API
You can always modify values or output format via ProcessWire API.
**Modify output format**
```
$f = $page->fields->get('myColorField');
$f->outputFormat = 8;
echo $page->color['rx'];
```
**Modify values**
+ Delete the page field value by setting empty string or *NULL*.
+ The values (int) 0, (string) '0', '00000000' and '#00000000' are similar and stored as (int) 0 (black, full transparent).
```
$page->of(false);
$page->myColorField = 'ff0000'; // red
$page->save('myColorField');
```
## Notes
**Deleting values** is only possible with inputfields of type='text' and via API.
If a **default value** is set, the field is filled with it if the field is empty (for example on newly created pages).
If Inputfield of type='text' 32bit is selected you can set the value to '#00000000' and the default value will be ignored.
The Fieldtype includes
[**Spectrum Color Picker** by Brian Grinstead](https://github.com/bgrins/spectrum)
Any custom Javascript based Inputfield can be used.
If the **Inputfield** is **used as is** e.g. for Module Settings, the following properties are provided:
```
$f->wire('modules')->get('InputfieldColor);
$f->inputType = 0; // int 0 - 4
$f->alpha = 0; // int 0 or 1, will be set automatically dependend on inputType. To disable explicitly for inputType = 3 (spectrum color picker) set to bool false
$f->spectrum = ''; // options for spectrum Color Picker if inputType = 3 @see https://bgrins.github.io/spectrum/
// properties for inputType = 4 only
$f->initJS = ''; // initial JS
$f->fileJS = ''; // path to JS file
$f->fileCSS = ''; // path to CSS file
$f->jqueryCore = 0; // enable jqueryCore
$f->jqueryUI = 0; // enable jqueryUI
```
---
Fieldtype Select Color Options
==============================
This fieldtype is included in the package. The module is an extension of the Core **FieldtypeOptions** module and offers colors as predefined selectable options via 4 different input field types (Select, SelectMultiple, Checkboxes and Radios).

View file

@ -1,143 +0,0 @@
{
"AliceBlue": "f0f8ff",
"AntiqueWhite": "faebd7",
"Aqua": "00ffff",
"AquaMarine": "7fffd4",
"Azure": "f0ffff",
"Beige": "f5f5dc",
"Bisque": "ffe4c4",
"Black": "000000",
"BlanchedAlmond": "ffebcd",
"Blue": "0000ff",
"BlueViolet": "8a2be2",
"Brown": "a52a2a",
"BurlyWood": "deb887",
"CadetBlue": "5f9ea0",
"Chartreuse": "7fff00",
"Chocolate": "d2691e",
"Coral": "ff7f50",
"CornFlowerBlue": "6495ed",
"Cornsilk": "fff8dc",
"Crimson": "dc143c",
"Cyan": "00ffff",
"DarkBlue": "00008b",
"DarkCyan": "008b8b",
"DarkGoldenRod": "b8860b",
"DarkGray": "a9a9a9",
"DarkGreen": "006400",
"DarkKhaki": "bdb76b",
"DarkMagenta": "8b008b",
"DarkOliveGreen": "556b2f",
"DarkOrange": "ff8c00",
"DarkOrchid": "9932cc",
"DarkRed": "8b0000",
"DarkSalmon": "e9967a",
"DarkSeaGreen": "8fbc8f",
"DarkSlateBlue": "483d8b",
"DarkSlateGray": "2f4f4f",
"DarkTurquoise": "00ced1",
"DarkViolet": "9400d3",
"DeepPink": "ff1493",
"DeepSkyBlue": "00bfff",
"DimGray": "696969",
"DodgerBlue": "1e90ff",
"FireBrick": "b22222",
"FloralWhite": "fffaf0",
"ForestGreen": "228b22",
"Fuchsia": "ff00ff",
"Gainsboro": "dcdcdc",
"GhostWhite": "f8f8ff",
"Gold": "ffd700",
"GoldenRod": "daa520",
"Gray": "808080",
"Green": "008000",
"GreenYellow": "adff2f",
"HoneyDew": "f0fff0",
"HotPink": "ff69b4",
"IndianRed": "cd5c5c",
"Indigo": "4b0082",
"Ivory": "fffff0",
"Khaki": "f0e68c",
"Lavender": "e6e6fa",
"LavenderBlush": "fff0f5",
"LawnGreen": "7cfc00",
"LemonChiffon": "fffacd",
"LightBlue": "add8e6",
"LightCoral": "f08080",
"LightCyan": "e0ffff",
"LightGoldenrodYellow": "fafad2",
"LightGray": "d3d3d3",
"LightGreen": "90ee90",
"LightPink": "ffb6c1",
"LightSalmon": "ffa07a",
"LightSeaGreen": "20b2aa",
"LightSkyBlue": "87cefa",
"LightSlateGray": "778899",
"LightSteelBlue": "b0c4de",
"LightYellow": "ffffe0",
"Lime": "00ff00",
"LimeGreen": "32cd32",
"Linen": "faf0e6",
"Magenta": "ff00ff",
"Maroon": "800000",
"MediumAquaMarine": "66cdaa",
"MediumBlue": "0000cd",
"MediumOrchid": "ba55d3",
"MediumPurple": "9370d8",
"MediumSeaGreen": "3cb371",
"MediumSlateBlue": "7b68ee",
"MediumSpringGreen": "00fa9a",
"MediumTurquoise": "48d1cc",
"MediumVioletRed": "c71585",
"MidnightBlue": "191970",
"MintCream": "f5fffa",
"MistyRose": "ffe4e1",
"Moccasin": "ffe4b5",
"NavajoWhite": "ffdead",
"Navy": "000080",
"OldLace": "fdf5e6",
"Olive": "808000",
"OliveDrab": "6b8e23",
"Orange": "ffa500",
"OrangeRed": "ff4500",
"Orchid": "da70d6",
"PaleGoldenRod": "eee8aa",
"PaleGreen": "98fb98",
"PaleTurquoise": "afeeee",
"PaleVioletRed": "db7093",
"PapayaWhip": "ffefd5",
"PeachPuff": "ffdab9",
"Peru": "cd853f",
"Pink": "ffc0cb",
"Plum": "dda0dd",
"PowderBlue": "b0e0e6",
"Purple": "800080",
"RebeccaPurple":"663399",
"Red": "ff0000",
"RosyBrown": "bc8f8f",
"RoyalBlue": "4169e1",
"SaddleBrown": "8b4513",
"Salmon": "fa8072",
"SandyBrown": "f4a460",
"SeaGreen": "2e8b57",
"SeaShell": "fff5ee",
"Sienna": "a0522d",
"Silver": "c0c0c0",
"SkyBlue": "87ceeb",
"SlateBlue": "6a5acd",
"SlateGray": "708090",
"Snow": "fffafa",
"SpringGreen": "00ff7f",
"SteelBlue": "4682b4",
"Tan": "d2b48c",
"Teal": "008080",
"Thistle": "d8bfd8",
"Tomato": "ff6347",
"Turquoise": "40e0d0",
"Violet": "ee82ee",
"Wheat": "f5deb3",
"White": "ffffff",
"WhiteSmoke": "f5f5f5",
"Yellow": "ffff00",
"YellowGreen": "9acd32"
}

View file

@ -1,507 +0,0 @@
/***
Spectrum Colorpicker v1.8.1
https://github.com/bgrins/spectrum
Author: Brian Grinstead
License: MIT
***/
.sp-container {
position:absolute;
top:0;
left:0;
display:inline-block;
*display: inline;
*zoom: 1;
/* https://github.com/bgrins/spectrum/issues/40 */
z-index: 9999994;
overflow: hidden;
}
.sp-container.sp-flat {
position: relative;
}
/* Fix for * { box-sizing: border-box; } */
.sp-container,
.sp-container * {
-webkit-box-sizing: content-box;
-moz-box-sizing: content-box;
box-sizing: content-box;
}
/* http://ansciath.tumblr.com/post/7347495869/css-aspect-ratio */
.sp-top {
position:relative;
width: 100%;
display:inline-block;
}
.sp-top-inner {
position:absolute;
top:0;
left:0;
bottom:0;
right:0;
}
.sp-color {
position: absolute;
top:0;
left:0;
bottom:0;
right:20%;
}
.sp-hue {
position: absolute;
top:0;
right:0;
bottom:0;
left:84%;
height: 100%;
}
.sp-clear-enabled .sp-hue {
top:33px;
height: 77.5%;
}
.sp-fill {
padding-top: 80%;
}
.sp-sat, .sp-val {
position: absolute;
top:0;
left:0;
right:0;
bottom:0;
}
.sp-alpha-enabled .sp-top {
margin-bottom: 18px;
}
.sp-alpha-enabled .sp-alpha {
display: block;
}
.sp-alpha-handle {
position:absolute;
top:-4px;
bottom: -4px;
width: 6px;
left: 50%;
cursor: pointer;
border: 1px solid black;
background: white;
opacity: .8;
}
.sp-alpha {
display: none;
position: absolute;
bottom: -14px;
right: 0;
left: 0;
height: 8px;
}
.sp-alpha-inner {
border: solid 1px #333;
}
.sp-clear {
display: none;
}
.sp-clear.sp-clear-display {
background-position: center;
}
.sp-clear-enabled .sp-clear {
display: block;
position:absolute;
top:0px;
right:0;
bottom:0;
left:84%;
height: 28px;
}
/* Don't allow text selection */
.sp-container, .sp-replacer, .sp-preview, .sp-dragger, .sp-slider, .sp-alpha, .sp-clear, .sp-alpha-handle, .sp-container.sp-dragging .sp-input, .sp-container button {
-webkit-user-select:none;
-moz-user-select: -moz-none;
-o-user-select:none;
user-select: none;
}
.sp-container.sp-input-disabled .sp-input-container {
display: none;
}
.sp-container.sp-buttons-disabled .sp-button-container {
display: none;
}
.sp-container.sp-palette-buttons-disabled .sp-palette-button-container {
display: none;
}
.sp-palette-only .sp-picker-container {
display: none;
}
.sp-palette-disabled .sp-palette-container {
display: none;
}
.sp-initial-disabled .sp-initial {
display: none;
}
/* Gradients for hue, saturation and value instead of images. Not pretty... but it works */
.sp-sat {
background-image: -webkit-gradient(linear, 0 0, 100% 0, from(#FFF), to(rgba(204, 154, 129, 0)));
background-image: -webkit-linear-gradient(left, #FFF, rgba(204, 154, 129, 0));
background-image: -moz-linear-gradient(left, #fff, rgba(204, 154, 129, 0));
background-image: -o-linear-gradient(left, #fff, rgba(204, 154, 129, 0));
background-image: -ms-linear-gradient(left, #fff, rgba(204, 154, 129, 0));
background-image: linear-gradient(to right, #fff, rgba(204, 154, 129, 0));
-ms-filter: "progid:DXImageTransform.Microsoft.gradient(GradientType = 1, startColorstr=#FFFFFFFF, endColorstr=#00CC9A81)";
filter : progid:DXImageTransform.Microsoft.gradient(GradientType = 1, startColorstr='#FFFFFFFF', endColorstr='#00CC9A81');
}
.sp-val {
background-image: -webkit-gradient(linear, 0 100%, 0 0, from(#000000), to(rgba(204, 154, 129, 0)));
background-image: -webkit-linear-gradient(bottom, #000000, rgba(204, 154, 129, 0));
background-image: -moz-linear-gradient(bottom, #000, rgba(204, 154, 129, 0));
background-image: -o-linear-gradient(bottom, #000, rgba(204, 154, 129, 0));
background-image: -ms-linear-gradient(bottom, #000, rgba(204, 154, 129, 0));
background-image: linear-gradient(to top, #000, rgba(204, 154, 129, 0));
-ms-filter: "progid:DXImageTransform.Microsoft.gradient(startColorstr=#00CC9A81, endColorstr=#FF000000)";
filter : progid:DXImageTransform.Microsoft.gradient(startColorstr='#00CC9A81', endColorstr='#FF000000');
}
.sp-hue {
background: -moz-linear-gradient(top, #ff0000 0%, #ffff00 17%, #00ff00 33%, #00ffff 50%, #0000ff 67%, #ff00ff 83%, #ff0000 100%);
background: -ms-linear-gradient(top, #ff0000 0%, #ffff00 17%, #00ff00 33%, #00ffff 50%, #0000ff 67%, #ff00ff 83%, #ff0000 100%);
background: -o-linear-gradient(top, #ff0000 0%, #ffff00 17%, #00ff00 33%, #00ffff 50%, #0000ff 67%, #ff00ff 83%, #ff0000 100%);
background: -webkit-gradient(linear, left top, left bottom, from(#ff0000), color-stop(0.17, #ffff00), color-stop(0.33, #00ff00), color-stop(0.5, #00ffff), color-stop(0.67, #0000ff), color-stop(0.83, #ff00ff), to(#ff0000));
background: -webkit-linear-gradient(top, #ff0000 0%, #ffff00 17%, #00ff00 33%, #00ffff 50%, #0000ff 67%, #ff00ff 83%, #ff0000 100%);
background: linear-gradient(to bottom, #ff0000 0%, #ffff00 17%, #00ff00 33%, #00ffff 50%, #0000ff 67%, #ff00ff 83%, #ff0000 100%);
}
/* IE filters do not support multiple color stops.
Generate 6 divs, line them up, and do two color gradients for each.
Yes, really.
*/
.sp-1 {
height:17%;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff0000', endColorstr='#ffff00');
}
.sp-2 {
height:16%;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffff00', endColorstr='#00ff00');
}
.sp-3 {
height:17%;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00ff00', endColorstr='#00ffff');
}
.sp-4 {
height:17%;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#00ffff', endColorstr='#0000ff');
}
.sp-5 {
height:16%;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#0000ff', endColorstr='#ff00ff');
}
.sp-6 {
height:17%;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff00ff', endColorstr='#ff0000');
}
.sp-hidden {
display: none !important;
}
/* Clearfix hack */
.sp-cf:before, .sp-cf:after { content: ""; display: table; }
.sp-cf:after { clear: both; }
.sp-cf { *zoom: 1; }
/* Mobile devices, make hue slider bigger so it is easier to slide */
@media (max-device-width: 480px) {
.sp-color { right: 40%; }
.sp-hue { left: 63%; }
.sp-fill { padding-top: 60%; }
}
.sp-dragger {
border-radius: 5px;
height: 5px;
width: 5px;
border: 1px solid #fff;
background: #000;
cursor: pointer;
position:absolute;
top:0;
left: 0;
}
.sp-slider {
position: absolute;
top:0;
cursor:pointer;
height: 3px;
left: -1px;
right: -1px;
border: 1px solid #000;
background: white;
opacity: .8;
}
/*
Theme authors:
Here are the basic themeable display options (colors, fonts, global widths).
See http://bgrins.github.io/spectrum/themes/ for instructions.
*/
.sp-container {
border-radius: 0;
background-color: #ECECEC;
border: solid 1px #f0c49B;
padding: 0;
}
.sp-container, .sp-container button, .sp-container input, .sp-color, .sp-hue, .sp-clear {
font: normal 12px "Lucida Grande", "Lucida Sans Unicode", "Lucida Sans", Geneva, Verdana, sans-serif;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
-ms-box-sizing: border-box;
box-sizing: border-box;
}
.sp-top {
margin-bottom: 3px;
}
.sp-color, .sp-hue, .sp-clear {
border: solid 1px #666;
}
/* Input */
.sp-input-container {
float:right;
width: 100px;
margin-bottom: 4px;
}
.sp-initial-disabled .sp-input-container {
width: 100%;
}
.sp-input {
font-size: 12px !important;
border: 1px inset;
padding: 4px 5px;
margin: 0;
width: 100%;
background:transparent;
border-radius: 3px;
color: #222;
}
.sp-input:focus {
border: 1px solid orange;
}
.sp-input.sp-validation-error {
border: 1px solid red;
background: #fdd;
}
.sp-picker-container , .sp-palette-container {
float:left;
position: relative;
padding: 10px;
padding-bottom: 300px;
margin-bottom: -290px;
}
.sp-picker-container {
width: 172px;
border-left: solid 1px #fff;
}
/* Palettes */
.sp-palette-container {
border-right: solid 1px #ccc;
}
.sp-palette-only .sp-palette-container {
border: 0;
}
.sp-palette .sp-thumb-el {
display: block;
position:relative;
float:left;
width: 24px;
height: 15px;
margin: 3px;
cursor: pointer;
border:solid 2px transparent;
}
.sp-palette .sp-thumb-el:hover, .sp-palette .sp-thumb-el.sp-thumb-active {
border-color: orange;
}
.sp-thumb-el {
position:relative;
}
/* Initial */
.sp-initial {
float: left;
border: solid 1px #333;
}
.sp-initial span {
width: 30px;
height: 25px;
border:none;
display:block;
float:left;
margin:0;
}
.sp-initial .sp-clear-display {
background-position: center;
}
/* Buttons */
.sp-palette-button-container,
.sp-button-container {
float: right;
}
/* Replacer (the little preview div that shows up instead of the <input>) */
.sp-replacer {
margin:0;
overflow:hidden;
cursor:pointer;
padding: 4px;
display:inline-block;
*zoom: 1;
*display: inline;
border: solid 1px #91765d;
background: #eee;
color: #333;
vertical-align: middle;
}
.sp-replacer:hover, .sp-replacer.sp-active {
border-color: #F0C49B;
color: #111;
}
.sp-replacer.sp-disabled {
cursor:default;
border-color: silver;
color: silver;
}
.sp-dd {
padding: 2px 0;
height: 16px;
line-height: 16px;
float:left;
font-size:10px;
}
.sp-preview {
position:relative;
width:25px;
height: 20px;
border: solid 1px #222;
margin-right: 5px;
float:left;
z-index: 0;
}
.sp-palette {
*width: 220px;
max-width: 220px;
}
.sp-palette .sp-thumb-el {
width:16px;
height: 16px;
margin:2px 1px;
border: solid 1px #d0d0d0;
}
.sp-container {
padding-bottom:0;
}
/* Buttons: http://hellohappy.org/css3-buttons/ */
.sp-container button {
background-color: #eeeeee;
background-image: -webkit-linear-gradient(top, #eeeeee, #cccccc);
background-image: -moz-linear-gradient(top, #eeeeee, #cccccc);
background-image: -ms-linear-gradient(top, #eeeeee, #cccccc);
background-image: -o-linear-gradient(top, #eeeeee, #cccccc);
background-image: linear-gradient(to bottom, #eeeeee, #cccccc);
border: 1px solid #ccc;
border-bottom: 1px solid #bbb;
border-radius: 3px;
color: #333;
font-size: 14px;
line-height: 1;
padding: 5px 4px;
text-align: center;
text-shadow: 0 1px 0 #eee;
vertical-align: middle;
}
.sp-container button:hover {
background-color: #dddddd;
background-image: -webkit-linear-gradient(top, #dddddd, #bbbbbb);
background-image: -moz-linear-gradient(top, #dddddd, #bbbbbb);
background-image: -ms-linear-gradient(top, #dddddd, #bbbbbb);
background-image: -o-linear-gradient(top, #dddddd, #bbbbbb);
background-image: linear-gradient(to bottom, #dddddd, #bbbbbb);
border: 1px solid #bbb;
border-bottom: 1px solid #999;
cursor: pointer;
text-shadow: 0 1px 0 #ddd;
}
.sp-container button:active {
border: 1px solid #aaa;
border-bottom: 1px solid #888;
-webkit-box-shadow: inset 0 0 5px 2px #aaaaaa, 0 1px 0 0 #eeeeee;
-moz-box-shadow: inset 0 0 5px 2px #aaaaaa, 0 1px 0 0 #eeeeee;
-ms-box-shadow: inset 0 0 5px 2px #aaaaaa, 0 1px 0 0 #eeeeee;
-o-box-shadow: inset 0 0 5px 2px #aaaaaa, 0 1px 0 0 #eeeeee;
box-shadow: inset 0 0 5px 2px #aaaaaa, 0 1px 0 0 #eeeeee;
}
.sp-cancel {
font-size: 11px;
color: #d93f3f !important;
margin:0;
padding:2px;
margin-right: 5px;
vertical-align: middle;
text-decoration:none;
}
.sp-cancel:hover {
color: #d93f3f !important;
text-decoration: underline;
}
.sp-palette span:hover, .sp-palette span.sp-thumb-active {
border-color: #000;
}
.sp-preview, .sp-alpha, .sp-thumb-el {
position:relative;
background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAMCAIAAADZF8uwAAAAGUlEQVQYV2M4gwH+YwCGIasIUwhT25BVBADtzYNYrHvv4gAAAABJRU5ErkJggg==);
}
.sp-preview-inner, .sp-alpha-inner, .sp-thumb-inner {
display:block;
position:absolute;
top:0;left:0;bottom:0;right:0;
}
.sp-palette .sp-thumb-inner {
background-position: 50% 50%;
background-repeat: no-repeat;
}
.sp-palette .sp-thumb-light.sp-thumb-active .sp-thumb-inner {
background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABIAAAASCAYAAABWzo5XAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAIVJREFUeNpiYBhsgJFMffxAXABlN5JruT4Q3wfi/0DsT64h8UD8HmpIPCWG/KemIfOJCUB+Aoacx6EGBZyHBqI+WsDCwuQ9mhxeg2A210Ntfo8klk9sOMijaURm7yc1UP2RNCMbKE9ODK1HM6iegYLkfx8pligC9lCD7KmRof0ZhjQACDAAceovrtpVBRkAAAAASUVORK5CYII=);
}
.sp-palette .sp-thumb-dark.sp-thumb-active .sp-thumb-inner {
background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABIAAAASCAYAAABWzo5XAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAJcEhZcwAADsMAAA7DAcdvqGQAAAAadEVYdFNvZnR3YXJlAFBhaW50Lk5FVCB2My41LjEwMPRyoQAAAMdJREFUOE+tkgsNwzAMRMugEAahEAahEAZhEAqlEAZhEAohEAYh81X2dIm8fKpEspLGvudPOsUYpxE2BIJCroJmEW9qJ+MKaBFhEMNabSy9oIcIPwrB+afvAUFoK4H0tMaQ3XtlrggDhOVVMuT4E5MMG0FBbCEYzjYT7OxLEvIHQLY2zWwQ3D+9luyOQTfKDiFD3iUIfPk8VqrKjgAiSfGFPecrg6HN6m/iBcwiDAo7WiBeawa+Kwh7tZoSCGLMqwlSAzVDhoK+6vH4G0P5wdkAAAAASUVORK5CYII=);
}
.sp-clear-display {
background-repeat:no-repeat;
background-position: center;
background-image: url(data:image/gif;base64,R0lGODlhFAAUAPcAAAAAAJmZmZ2dnZ6enqKioqOjo6SkpKWlpaampqenp6ioqKmpqaqqqqurq/Hx8fLy8vT09PX19ff39/j4+Pn5+fr6+vv7+wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACH5BAEAAP8ALAAAAAAUABQAAAihAP9FoPCvoMGDBy08+EdhQAIJCCMybCDAAYUEARBAlFiQQoMABQhKUJBxY0SPICEYHBnggEmDKAuoPMjS5cGYMxHW3IiT478JJA8M/CjTZ0GgLRekNGpwAsYABHIypcAgQMsITDtWJYBR6NSqMico9cqR6tKfY7GeBCuVwlipDNmefAtTrkSzB1RaIAoXodsABiZAEFB06gIBWC1mLVgBa0AAOw==);
}

File diff suppressed because it is too large Load diff

View file

@ -1,143 +0,0 @@
indianred #CD5C5C 205,92,92
lightcoral #F08080 240,128,128
salmon #FA8072 250,128,114
darksalmon #E9967A 233,150,122
lightsalmon #FFA07A 255,160,122
crimson #DC143C 220,20,60
red #FF0000 255,0,0
firebrick #B22222 178,34,34
darkred #8B0000 139,0,0
pink #FFC0CB 255,192,203
lightpink #FFB6C1 255,182,193
hotpink #FF69B4 255,105,180
deeppink #FF1493 255,20,147
mediumvioletred #C71585 199,21,133
palevioletred #DB7093 219,112,147
lightsalmon #FFA07A 255,160,122
coral #FF7F50 255,127,80
tomato #FF6347 255,99,71
orangered #FF4500 255,69,0
darkorange #FF8C00 255,140,0
orange #FFA500 255,165,0
gold #FFD700 255,215,0
yellow #FFFF00 255,255,0
lightyellow #FFFFE0 255,255,224
lemonchiffon #FFFACD 255,250,205
lightgoldenrodyellow #FAFAD2 250,250,210
papayawhip #FFEFD5 255,239,213
moccasin #FFE4B5 255,228,181
peachpuff #FFDAB9 255,218,185
palegoldenrod #EEE8AA 238,232,170
khaki #F0E68C 240,230,140
darkkhaki #BDB76B 189,183,107
lavender #E6E6FA 230,230,250
thistle #D8BFD8 216,191,216
plum #DDA0DD 221,160,221
violet #EE82EE 238,130,238
orchid #DA70D6 218,112,214
fuchsia #FF00FF 255,0,255
magenta #FF00FF 255,0,255
mediumorchid #BA55D3 186,85,211
mediumpurple #9370DB 147,112,219
blueviolet #8A2BE2 138,43,226
darkviolet #9400D3 148,0,211
darkorchid #9932CC 153,50,204
darkmagenta #8B008B 139,0,139
purple #800080 128,0,128
indigo #4B0082 75,0,130
slateblue #6A5ACD 106,90,205
darkslateblue #483D8B 72,61,139
mediumslateblue #7B68EE 123,104,238
greenyellow #ADFF2F 173,255,47
chartreuse #7FFF00 127,255,0
lawngreen #7CFC00 124,252,0
lime #00FF00 0,255,0
limegreen #32CD32 50,205,50
palegreen #98FB98 152,251,152
lightgreen #90EE90 144,238,144
mediumspringgreen #00FA9A 0,250,154
springgreen #00FF7F 0,255,127
mediumseagreen #3CB371 60,179,113
seagreen #2E8B57 46,139,87
forestgreen #228B22 34,139,34
green #008000 0,128,0
darkgreen #006400 0,100,0
yellowgreen #9ACD32 154,205,50
olivedrab #6B8E23 107,142,35
olive #808000 128,128,0
darkolivegreen #556B2F 85,107,47
mediumaquamarine #66CDAA 102,205,170
darkseagreen #8FBC8F 143,188,143
lightseagreen #20B2AA 32,178,170
darkcyan #008B8B 0,139,139
teal #008080 0,128,128
aqua #00FFFF 0,255,255
cyan #00FFFF 0,255,255
lightcyan #E0FFFF 224,255,255
paleturquoise #AFEEEE 175,238,238
aquamarine #7FFFD4 127,255,212
turquoise #40E0D0 64,224,208
mediumturquoise #48D1CC 72,209,204
darkturquoise #00CED1 0,206,209
cadetblue #5F9EA0 95,158,160
steelblue #4682B4 70,130,180
lightsteelblue #B0C4DE 176,196,222
powderblue #B0E0E6 176,224,230
lightblue #ADD8E6 173,216,230
skyblue #87CEEB 135,206,235
lightskyblue #87CEFA 135,206,250
deepskyblue #00BFFF 0,191,255
dodgerblue #1E90FF 30,144,255
cornflowerblue #6495ED 100,149,237
mediumslateblue #7B68EE 123,104,238
royalblue #4169E1 65,105,225
blue #0000FF 0,0,255
mediumblue #0000CD 0,0,205
darkblue #00008B 0,0,139
navy #000080 0,0,128
midnightblue #191970 25,25,112
cornsilk #FFF8DC 255,248,220
blanchedalmond #FFEBCD 255,235,205
bisque #FFE4C4 255,228,196
navajowhite #FFDEAD 255,222,173
wheat #F5DEB3 245,222,179
burlywood #DEB887 222,184,135
tan #D2B48C 210,180,140
rosybrown #BC8F8F 188,143,143
sandybrown #F4A460 244,164,96
goldenrod #DAA520 218,165,32
darkgoldenrod #B8860B 184,134,11
peru #CD853F 205,133,63
chocolate #D2691E 210,105,30
saddlebrown #8B4513 139,69,19
sienna #A0522D 160,82,45
brown #A52A2A 165,42,42
maroon #800000 128,0,0
white #FFFFFF 255,255,255
snow #FFFAFA 255,250,250
honeydew #F0FFF0 240,255,240
mintcream #F5FFFA 245,255,250
azure #F0FFFF 240,255,255
aliceblue #F0F8FF 240,248,255
ghostwhite #F8F8FF 248,248,255
whitesmoke #F5F5F5 245,245,245
seashell #FFF5EE 255,245,238
beige #F5F5DC 245,245,220
oldlace #FDF5E6 253,245,230
floralwhite #FFFAF0 255,250,240
ivory #FFFFF0 255,255,240
antiquewhite #FAEBD7 250,235,215
linen #FAF0E6 250,240,230
lavenderblush #FFF0F5 255,240,245
mistyrose #FFE4E1 255,228,225
gainsboro #DCDCDC 220,220,220
lightgrey #D3D3D3 211,211,211
silver #C0C0C0 192,192,192
darkgray #A9A9A9 169,169,169
gray #808080 128,128,128
dimgray #696969 105,105,105
lightslategray #778899 119,136,153
slategray #708090 112,128,144
darkslategray #2F4F4F 47,79,79
black #000000 0,0,0
rebeccapurple #663399 102,51,153

View file

@ -1,6 +0,0 @@
[*.{php,module}]
end_of_line = LF
indent_style = space
indent_size = 4
trim_trailing_whitespace = true
insert_final_newline = true

View file

@ -1 +0,0 @@
+.module linguist-language=PHP

View file

@ -1,96 +0,0 @@
# Changelog
### 0.6.0 - 2021-04-15
- PHP 8 support
### 0.5.2 - 2020-05-25
- changed Manuel Lemos smtp-class to new version 1.52, as he added a new token feature
### 0.5.1 - 2020-05-11
- minor fix to testconnection in the configpage
### 0.5.0 - 2020-05-04
- added a verbose debug testconnection into the configpage
### 0.4.2 - 2019-05-02
- added support for connections without authentication: allow_without_authentication
### 0.4.1 - 2019-04-19
- added support for verbose debug of the connection and sending process via a new method: $mail->debugSend()
### 0.4.0 - 2019-04-19
- added support for manual selection of a crypto method for TLS per this request: https://processwire.com/talk/topic/5704-wiremailsmtp/page/12/?tab=comments#comment-184229
### 0.3.1 - 2019-03-27
- enhanced the module to get overridden by site/config settings per this request: https://processwire.com/talk/topic/5704-wiremailsmtp/page/12/?tab=comments#comment-182735
### 0.3.0 - 2017-12-08
- fixed code that broke backward compatibility for PW 2.4 and 2.5, brought in with the config cosmetics (0.2.6)
### 0.2.7 - 2017-10-19
- @abdus fixed smtp password not saving
### 0.2.6 - 2017-10-17
- module config cosmetics by @abdus, many thanks! [See this forum post](https://processwire.com/talk/topic/5704-wiremailsmtp/?page=9&tab=comments#comment-153329)
### 0.2.5 - 2017-09-12
- fixed adding HTML-signatures into HTML-messages without body-end-tag
### 0.2.4 - 2017-09-03
- updated the attachment function to silence a PHP-Strict notice
### 0.2.3 - 2016-10-08
- updated the attachment function to be conform with the new integrated function in core WireMail class (introduced with PW 3.0.36)
### 0.2.2 - 2016-05-26
- fixed date string to follow strict RFC2822, See [Issue 5](https://github.com/horst-n/WireMailSmtp/issues/5) - Many thanks to @selsermedia!
### 0.2.0 - 2016-02-15
- added support for Selfsigned Certificates, a contribution from @flydev, [See this post](https://processwire.com/talk/topic/5704-wiremailsmtp/page-5#entry113290) - Many thanks!
### 0.1.14
- changed smtp class to new version 1.50 to solve a bug with two debug messages echoed out, even if debug was set to false
### 0.1.13 - 2015-06-14
- changed default setting for wrapText from true to false.
### 0.1.12
- fixed not sending to all CC-recipients when in sendSingle mode. See [issue 3](https://github.com/horst-n/WireMailSmtp/issues/3)
### 0.1.11
- changed smtp class to new version to solve problems with mixed usage of IP and hostname, found by @k07n. See [this post](https://processwire.com/talk/topic/5704-wiremailsmtp/page-3#entry95880)
### 0.1.10
- made wrapText configurable by Jan Romero [Commit abc0ac0b](https://github.com/horst-n/WireMailSmtp/commit/abc0ac0b4a3edd0fcbbb8b4695f00a362705ad5b)
### 0.1.9
- disabling connecting without authentication in the smtp base class
### 0.1.8
- added a separate inputfield for a HTML signature into config page
### 0.1.7
- set status from alpha to beta
### 0.0.7
- added new sentLog methods for permanent logging, intended for usage with third party modules, e.g. newsletter modules
### 0.0.6
- corrected addSignature to check and respect the config screen setting
### 0.0.5
- added multiple emails sending and bulkmail sending
### 0.0.4
- changed the functions "to" "cc" "bcc" to be compatible with Ryans changes
### 0.0.3
- added GMT Timezone to the Dateheader to reflect local timezones and show DateTime correct in Mailclients
### 0.0.2
- added sanitization to recipient names in email addresses (in file: WireMailSmtp.module)
### 0.0.1
- initial release
More information and code examples, please visit the [WireMailSmtp ProcessWire forum thread.](http://processwire.com/talk/topic/5704-module-wiremailsmtp/)

View file

@ -1,84 +0,0 @@
WireMailSmtp
============
### ProcessWire: a extension to the WireMail base class that uses SMTP-transport ###
### Only functional with ProcessWire Version 2.4.1 or greater ###
This module integrates EmailMessage, SMTP and SASL php-libraries from [Manuel Lemos](http://www.phpclasses.org/browse/author/1.html) into ProcessWire.
[More information and code examples](http://processwire.com/talk/topic/5704-module-wiremailsmtp/)
---
### Current Version 0.6.0 ###
### List of all options and features ###
**testConnection** () *- returns true on success, false on failures*
**debugSend** () *- send the mail(s) and output or return verbose messages of the complete connection and sending process*
**sendSingle** ( true | false ) *- default is false*
**sendBulk** ( true | false ) *- default is false, Set this to true if you have lots of recipients (50+)*
**to** ($recipients) *- one emailaddress or array with multiple emailaddresses*
**cc** ($recipients) *- only available with mode sendSingle, one emailaddress or array with multiple emailaddresses*
**bcc** ($recipients) *- one emailaddress or array with multiple emailaddresses*
**from** = 'person@example.com' *- can be set in module config (called Sender Emailaddress) but it can be overwritten here*
**fromName =** 'Name Surname' *- optional, can be set in module config (called Sender Name) but it can be overwritten here*
**priority** (3) *- 1 = Highest | 2 = High | 3 = Normal | 4 = Low | 5 = Lowest*
**dispositionNotification** () or **notification** () *- request a Disposition Notification*
**subject** ($subject) *- subject of the message*
**body** ($textBody) *- use this one alone to create and send plainText emailmessages*
**bodyHTML** ($htmlBody) *- use this to create a Multipart Alternative Emailmessage (containing a HTML-Part and a Plaintext-Part as fallback)*
**addSignature** ( true | false ) *- the default-behave is selectable in config screen, this can be overridden here. (only available if a signature is defined in the config screen)*
**attachment** ($filename, $alternativeBasename = '') *- add attachment file*
**send** () *- send the mail(s) and return number of successful send messages*
**getResult** () *- returns a dump (array) with all recipients (to, cc, bcc) and settings you have selected with the message, the message subject and body, and lists of successfull addresses and failed addresses,*
**logActivity** ($logmessage) *- you may log success if you want*
**logError** ($logmessage) *- you may log errors, too. - Errors are also logged automaticaly*
**useSentLog** (true | false) *- intended for usage with e.g. third party newsletter modules - tells the send() method to make usage of the sentLog-methods*
**sentLogReset** () *- starts a new Session. Best usage would be interactively once when setting up a new Newsletter*
**sentLogGet** () *- returns an array containing all previously used emailaddresses*
**sentLogAdd** ($emailaddress) *- is called automaticly within the send() method*
**wrapText** (true|false) *- default is true*
[More information and code examples](http://processwire.com/talk/topic/5704-module-wiremailsmtp/)

File diff suppressed because it is too large Load diff

View file

@ -1,448 +0,0 @@
<?php
/*******************************************************************************
* WireMailSmtp | hnsmtp
*
* @version - '0.6.0'
* @date - 2021/04/15
* @author - Horst Nogajski
* @licence - GNU GPL v2 - http://www.gnu.org/licenses/gpl-2.0.html
* @licence - MIT - https://processwire.com/about/license/mit/
********************************************************************************/
require_once( dirname(__FILE__) . '/smtp_classes/email_message.php' );
require_once( dirname(__FILE__) . '/smtp_classes/smtp_message.php' );
require_once( dirname(__FILE__) . '/smtp_classes/smtp.php' );
require_once( dirname(__FILE__) . '/smtp_classes/sasl.php' );
class hnsmtp {
private $default_charset = 'UTF-8';
private $smtp_host = ''; /* SMTP server host name */
private $smtp_port = 25; /* SMTP server host port,
usually 25 but for use with SSL or TLS 587 */
private $smtp_ssl = 0; /* Establish secure connections using SSL */
private $smtp_ssl_crypto_method = ''; /* Define the crypto method to use with SSL */
private $smtp_start_tls = 0; /* Establish secure connections using START_TLS */
private $smtp_tls_crypto_method = ''; /* Define the crypto method to use with TLS */
private $localhost = ''; /* this computers address */
private $realm = ''; /* Authentication realm or domain */
private $workstation = ''; /* Workstation for NTLM authentication */
private $authentication_mechanism = ''; /* SASL authentication mechanism */
private $allow_without_authentication = 0; /* Server allows connection without authentication */
private $smtp_user = ''; /* Authentication user name */
private $smtp_password = ''; /* Authentication password */
private $smtp_debug = 0; /* Output debug information */
private $smtp_html_debug = 0; /* Debug information is in HTML */
private $sender_name = ''; // From: the senders name
private $sender_email = ''; // From: the senders email address
private $sender_reply = ''; // Reply-To: optional email address
private $sender_errors_to = ''; // Errors-To: optional email address
private $sender_signature = ''; // a Signature Text, like Contact Data and / or Confidentiality Notices
private $sender_signature_html = ''; // a Signature Text in HTML, like Contact Data and / or Confidentiality Notices
private $send_sender_signature = 1; // when the signature should be send: with every mail | only when the default Email is the sender | only when explicitly called via the API
private $extra_headers = array(); // optional Custom-Meta-Headers
private $valid_recipients = array(); /* SenderEmailAddresses wich are allowed to
receive Messages */
private $smtp_certificate = false; // @flydev: https://processwire.com/talk/topic/5704-wiremailsmtp/page-5#entry113290
private $aValidVars = null;
private $emailMessage = null;
private $connected = null;
private $errors = array();
private $from = '';
private $fromName = '';
public function testConnection($debug = false) {
$res = $this->connect($debug);
$this->close();
return $res;
}
public function connect($debug = false) {
$this->connected = (($this->errors[] = $this->emailMessage->StartSendingMessage()) == '') ? true : false;
return $this->connected;
}
public function close() {
if(!isset($this->emailMessage)) {
return null;
}
$res = $this->emailMessage->ResetConnection('') == '' ? true : false;
$this->connected = false;
return $res;
}
public function getErrors() {
$a = array();
foreach( $this->errors as $e ) {
if($e=='') {
continue;
}
$a[] = $e;
}
$this->errors = $a;
return $this->errors;
}
protected function set_var_val( $k, $v ) {
if(!isset($this->aValidVars[$k])) {
return;
}
switch($k) {
case 'send_sender_signature':
case 'smtp_port':
$this->$k = intval($v);
break;
case 'smtp_certificate':
case 'smtp_ssl':
case 'smtp_start_tls':
case 'smtp_debug':
case 'smtp_html_debug':
case 'allow_without_authentication':
if(is_bool($v)) {
$this->$k = $v==true ? 1 : 0;
}
elseif(is_int($v)) {
$this->$k = $v==1 ? 1 : 0;
}
elseif(is_string($v) && in_array($v, array('1','on','On','ON','true','TRUE'))) {
$this->$k = 1;
}
elseif(is_string($v) && in_array($v, array('0','off','Off','OFF','false','FALSE'))) {
$this->$k = 0;
}
else {
$this->$k = 0;
}
break;
case 'smtp_tls_crypto_method':
$availableTLSmethods = WireMailSmtp::getCryptoMethodsTLS();
if(is_string($v) && isset($v, $availableTLSmethods)) {
$this->$k = $v;
}
break;
case 'smtp_ssl_crypto_method':
$availableSSLmethods = WireMailSmtp::getCryptoMethodsSSL();
if(is_string($v) && isset($v, $availableSSLmethods)) {
$this->$k = $v;
}
break;
case 'authentication_mechanism':
$this->authentication_mechanism = $v;
break;
case 'valid_recipients':
case 'extra_headers';
$this->$k = is_array($v) || is_string($v) ? (array)$v : array();
break;
default:
if(in_array($k, array('smtp_host', 'smtp_user', 'smtp_password',
'localhost', 'workstation', 'realm',
'sender_name', 'sender_email', 'sender_reply',
'sender_errors_to', 'sender_signature', 'sender_signature_html',
'default_charset'
))
) {
$this->$k = strval($v);
}
}
}
public function __construct($aConfig = null) {
if(!is_array($aConfig)) {
return;
}
$this->aValidVars = get_class_vars(__CLASS__);
foreach($aConfig as $k => $v) {
$this->set_var_val($k, $v);
}
foreach($this->valid_recipients as $k=>$v) {
$this->valid_recipients[$k] = str_replace(array('<','>'), '', strtolower(trim($v)));
}
// start SMTP-Mail
$this->emailMessage = new smtp_message_class();
// SMTP Server Authentication
$this->emailMessage->default_charset = $this->default_charset;
$this->emailMessage->localhost = $this->localhost;
$this->emailMessage->smtp_host = $this->smtp_host;
$this->emailMessage->smtp_port = $this->smtp_port;
$this->emailMessage->smtp_ssl = $this->smtp_ssl;
$this->emailMessage->smtp_ssl_crypto_method = $this->smtp_ssl_crypto_method;
$this->emailMessage->smtp_start_tls = $this->smtp_start_tls;
$this->emailMessage->smtp_tls_crypto_method = $this->smtp_tls_crypto_method;
$this->emailMessage->smtp_user = $this->smtp_user;
$this->emailMessage->smtp_password = $this->smtp_password;
$this->emailMessage->allow_without_authentication = $this->allow_without_authentication;
$this->emailMessage->smtp_certificate = $this->smtp_certificate;
// advanced SMTP Server Settings
$this->emailMessage->realm = $this->realm;
$this->emailMessage->workstation = $this->workstation;
$this->emailMessage->authentication_mechanism = $this->authentication_mechanism;
// Debug on / off
$this->emailMessage->smtp_debug = $this->smtp_debug;
$this->emailMessage->smtp_html_debug = $this->smtp_html_debug;
}
public function __destruct() {
if( $this->connected ) {
$this->close();
}
unset($this->emailMessage);
}
protected function logError($msg) {
if(!isset($this->module)) $this->module = wire('modules')->get('WireMailSmtp');
$this->module->logError($msg);
}
protected function logActivity($msg) {
if(!isset($this->module)) $this->module = wire('modules')->get('WireMailSmtp');
$this->module->logActivity($msg);
}
public function setSender($from='', $fromName='') {
$genericEmail = isset($this->localhost) ? 'processwire@' . $this->localhost : false;
$sender = strlen($from)>0 ? $from : $this->sender_email;
if(empty($sender) && false!==$genericEmail) {
$sender = $genericEmail; // fallback to a generic email address
}
$this->isValidEmailadress($sender); // if it is not a valid Emailaddress a Error is thrown
$senderName = strlen($fromName)>0 ? $fromName : $this->sender_name;
$this->from = $sender;
$this->fromName = $senderName;
if($sender==$this->sender_email) {
// we use the defaults from module config
$replyTo = isset($this->sender_reply) && strlen($this->sender_reply)>0 ? $this->sender_reply : $this->sender_email;
$errorsTo = isset($this->sender_errors_to) && strlen($this->sender_errors_to)>0 ? $this->sender_errors_to : $this->sender_email;
}
else {
$replyTo = $genericEmail!=$sender ? $sender : ''; // we don't want get replys to the generic emailaddress
$errorsTo = '';
}
$this->setEmailHeader('from', $sender, $senderName);
if(''!=$replyTo) $this->setEmailHeader('reply', $replyTo);
if(''!=$errorsTo) $this->setEmailHeader('errors', $errorsTo);
}
public function setCustomHeader($header) {
$extra_headers = (isset($this->extra_headers) && is_array($this->extra_headers) && 0<count($this->extra_headers)) ? $this->extra_headers : array();
$headers = array_merge($extra_headers, $header);
foreach($headers as $k=>$v) {
$this->setHeader($k, $v);
}
}
public function setTextBody($text, $addSignature, $wrapText, &$maildata) {
if($addSignature===true && isset($this->sender_signature) && is_string($this->sender_signature) && strlen(trim($this->sender_signature))>0) {
$text .= "\r\n\r\n" . $this->sender_signature;
}
$text = $wrapText ? $this->emailMessage->WrapText($text) : (string)$text;
$maildata = $text;
$ret = $this->emailMessage->AddQuotedPrintableTextPart($text);
if($ret=='') {
return true;
}
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . $ret);
return false;
}
public function setTextAndHtmlBody($text, $html, $addSignature, $wrapText, &$maildata1, &$maildata2) {
if($addSignature===true && isset($this->sender_signature) && is_string($this->sender_signature) && strlen(trim($this->sender_signature))>0) {
$text .= "\r\n\r\n--\r\n" . $this->sender_signature;
}
if($addSignature===true && isset($this->sender_signature_html) && is_string($this->sender_signature_html) && strlen(trim($this->sender_signature_html))>0) {
// we first need to check if there is a </body> end tag in the html-markup
if(preg_match('</body>', $html)) {
$html = str_replace("</body>", "\r\n\r\n" . $this->sender_signature_html . "\r\n</body>", $html);
} else {
$html .= "\r\n\r\n" . $this->sender_signature_html . "\r\n";
}
}
$maildata1 = $text = $wrapText ? $this->emailMessage->WrapText($text) : (string)$text;
$maildata2 = $html = $wrapText ? $this->emailMessage->WrapText($html) : (string)$html;
// create Alternative-Multipart
$html_part = $text_part = $alternative_part = 0;
$this->emailMessage->CreateQuotedPrintableTextPart($text, 'UTF-8', $text_part);
$this->emailMessage->CreateQuotedPrintableHTMLPart($html, 'UTF-8', $html_part);
$alternative_parts = array( $text_part, $html_part );
#$this->emailMessage->CreateAlternativeMultipart($alternative_parts, $alternative_part);
$ret = $this->emailMessage->AddAlternativeMultipart($alternative_parts);
if($ret=='') {
return true;
}
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . $ret);
return false;
}
public function addAttachment($attachment) {
$ret = $this->emailMessage->AddFilePart($attachment);
if($ret=='') {
return true;
}
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . $ret);
return false;
}
public function setNotification(&$maildata) {
if(!isset($this->from) || strlen(trim($this->from))==0) {
return false;
}
$email = $this->bundleEmailAndName($this->from, $this->fromName);
$maildata = $email;
return $this->setHeader('Disposition-Notification-To', $email);
}
public function setPriority($priority=3) {
$priority = intval($priority);
if(!in_array($priority, array(1, 2, 3, 4, 5))) {
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . "($priority)");
return false;
}
$priorities = array(
5 => array('5 (Lowest)', 'Low', 'Low'),
4 => array('4 (Low)', 'Low', 'Low'),
3 => array('3 (Normal)', 'Normal', 'Normal'),
2 => array('2 (High)', 'High', 'High'),
1 => array('1 (Highest)', 'High', 'High')
);
$ret = 0;
$ret += $this->setHeader('X-Priority', $priorities[$priority][0]) ? 1 : 0;
$ret += $this->setHeader('X-MSMail-Priority', $priorities[$priority][1]) ? 1 : 0;
$ret += $this->setHeader('Importance', $priorities[$priority][2]) ? 1 : 0;
return 3==$ret ? true : false;
}
public function send($debugServer=false, $htmlDebug=false, &$maildata='') {
if($debugServer) $this->emailMessage->smtp_debug = 1;
if($htmlDebug) $this->emailMessage->smtp_html_debug = 1;
if(!$this->connect()) {
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : cannot connect to smtp-server!');
return false;
}
$this->emailMessage->SetHeader("Date", gmdate("D, j M Y H:i:s \G\M\T"));
$ret = $this->emailMessage->Send();
if($ret=='') {
$maildata = 'success';
return true;
}
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . $ret);
$maildata = (string)$ret;
return false;
}
public function setEmailHeader($type, $address, $name='') {
$address = str_replace(array('<','>'), '', $address);
if(!$this->isValidEmailadress($address)) {
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : No valid E-mailadress: '.$address);
return false;
}
$type = strtolower($type);
$valid_types = array('to'=>'To','from'=>'From','cc'=>'CC','bcc'=>'BCC','reply-to'=>'Reply-To','reply'=>'Reply-To','errors-to'=>'Errors-To','errors'=>'Errors-To','error'=>'Errors-To');
if(!in_array($type,array_keys($valid_types))) {
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : No valid Headertype: '.$type);
return false;
}
if(strpos($type,'reply')!==false) {
$this->emailMessage->SetHeader('Return-Path',$address);
}
$ret = $this->emailMessage->SetEncodedEmailHeader($valid_types[$type], $address, $name);
if($ret!='') {
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . $ret);
return false;
}
return true;
}
public function setHeader($headername,$content) {
$ret = $this->emailMessage->SetEncodedHeader($headername,$content);
if($ret!='') {
$this->logError('Error in '.__CLASS__.'::'.__FUNCTION__.' : ' . $ret);
return false;
}
return true;
}
public function isValidEmailadress($email) {
$email = strtolower(trim($email));
$clean = wire('sanitizer')->email($email);
if($email != $clean) throw new WireException("Invalid email address");
return true;
}
protected function bundleEmailAndName($email, $name) {
$email = strtolower(trim($email));
$clean = wire('sanitizer')->email($email);
if(!strlen($name)) return $email;
$name = wire('sanitizer')->emailHeader($name);
if(strpos($name, ',') !== false) {
// name contains a comma, so quote the value
$name = str_replace('"', '', $name); // remove existing quotes
$name = '"' . $name . '"'; // surround w/quotes
}
return "$name <$email>";
}
public function setBulkMail($bulk) {
return $this->emailMessage->setBulkMail($bulk);
}
} // END class hnsmtp

View file

@ -1,641 +0,0 @@
<?php
/*******************************************************************************
* WireMailSmtp | WireMailSmtpConfig
* ---------------------------------------------------------------------------
* @version - '0.6.0'
* @author - Horst Nogajski
* @licence - GNU GPL v2 - http://www.gnu.org/licenses/gpl-2.0.html
*******************************************************************************/
class WireMailSmtpConfig extends Wire {
public function getConfig(array $data) {
// check that they have the required PW version
if(version_compare(wire('config')->version, '2.4.1', '<')) {
$this->error(' requires ProcessWire 2.4.1 or newer. Please update.');
}
$siteconfig = is_array(wire('config')->wiremailsmtp) ? wire('config')->wiremailsmtp : array();
$modules = wire('modules');
$form = new InputfieldWrapper();
// LOCALHOST
$field = $modules->get('InputfieldText');
$field->attr('name', 'localhost');
$field->attr('value', $data['localhost']);
$field->label = $this->_('Local Hostname');
$field->description = $this->_('Hostname of this computer');
if(isset($siteconfig['localhost'])) {
$field->notes = $this->attentionMessage($siteconfig['localhost']);
$field->attr('tabindex', '-1');
} else {
$field->required = true;
}
$field->icon = 'desktop';
$form->add($field);
// WRAPPER SMTP SERVER
$fieldset = $modules->get('InputfieldFieldset');
$fieldset->label = $this->_('SMTP Server');
$fieldset->attr('name', '_smtp');
$fieldset->collapsed = Inputfield::collapsedNo;
$fieldset->icon = 'server';
// SMTP HOST
$field = $modules->get('InputfieldText');
$field->attr('name', 'smtp_host');
$field->attr('value', $data['smtp_host']);
$field->label = $this->_('SMTP Hostname');
$field->description = $this->_('Set to the host name of the SMTP server to which you want to relay the messages');
$field->columnWidth = 50;
if(isset($siteconfig['smtp_host'])) {
$field->notes = $this->attentionMessage($siteconfig['smtp_host']);
$field->attr('tabindex', '-1');
} else {
$field->required = true;
}
$field->icon = 'server';
$fieldset->add($field);
// SMTP PORT
$field = $modules->get('InputfieldInteger');
$field->attr('name', 'smtp_port');
$field->attr('value', $data['smtp_port']);
$field->label = $this->_('SMTP Port');
$field->description = $this->_('Set to the TCP port of the SMTP server host to connect');
if(isset($siteconfig['smtp_port'])) {
$field->notes = $this->attentionMessage($siteconfig['smtp_port']);
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_("default: 25\ndefault for TLS / SSL: 587 or 465");
$field->required = true;
}
$field->columnWidth = 50;
$field->icon = 'sign-out';
$fieldset->add($field);
// ALLOW WITHOUT ANY AUTHENTICATION
$field = $modules->get('InputfieldCheckbox');
$field->attr('name', 'allow_without_authentication');
$field->attr('id', 'allow_without_authentication');
$field->attr('value', 1);
$field->attr('checked', $data['allow_without_authentication'] ? 'checked' : '');
$field->label = $this->_('Allow Connection without Authentication');
$field->description = $this->_('Server allows connecting without Authentication Credentials');
if(isset($siteconfig['allow_without_authentication'])) {
$field->notes = $this->attentionMessage($siteconfig['allow_without_authentication']);
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_('Default: unchecked');
}
$field->columnWidth = 33;
$field->icon = 'unlock';
$fieldset->add($field);
// SMTP USER
$field = $modules->get('InputfieldText');
$field->attr('name', 'smtp_user');
$field->attr('value', $data['smtp_user']);
$field->label = $this->_('SMTP User');
$field->description = $this->_('Set this variable to the user name when the SMTP server requires authentication');
if(isset($siteconfig['smtp_user'])) {
$field->notes = $this->attentionMessage($siteconfig['smtp_user']);
$field->attr('tabindex', '-1');
}
$field->columnWidth = 34;
$field->icon = 'user';
$fieldset->add($field);
// SMTP PASSWORD
$field = $modules->get('InputfieldText');
$field->attr('name', 'smtp_password');
$field->attr('value', $data['smtp_password']);
$field->attr('type', 'password');
$field->label = $this->_('SMTP Password');
$field->description = $this->_('Set this variable to the user password when the SMTP server requires authentication');
if(isset($siteconfig['smtp_password'])) {
$field->notes = $this->attentionMessage('*******');
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_('**Note**: Password is stored as plain text in database.');
}
$field->columnWidth = 33;
$field->icon = 'asterisk';
$fieldset->add($field);
// SMTP STARTTLS
$field = $modules->get('InputfieldCheckbox');
$field->attr('name', 'smtp_start_tls');
$field->attr('id', 'smtp_start_tls');
$field->attr('value', 1);
$field->attr('checked', $data['smtp_start_tls'] ? 'checked' : '');
$field->columnWidth = 50;
$field->label = $this->_('Use START-TLS');
$field->description = $this->_('Check if the connection to the SMTP server should use encryption after the connection is established using TLS protocol');
if(isset($siteconfig['smtp_start_tls'])) {
$field->notes = $this->attentionMessage($siteconfig['smtp_start_tls']);
$field->attr('tabindex', '-1');
}
$field->icon = 'lock';
//$field->showIf = 'smtp_ssl=0';
$fieldset->add($field);
// TLS crypto method
$field = $modules->get('InputfieldSelect');
$field->attr('name', 'smtp_tls_crypto_method');
$field->attr('value', $data['smtp_tls_crypto_method']);
$field->label = $this->_('Select a crypto method for TLS');
$availableTLSmethods = WireMailSmtp::getCryptoMethodsTLS();
array_unshift($availableTLSmethods, array(''));
$field->addOptions($availableTLSmethods);
$field->description = $this->_("Select the crypto method that should be used for TLS connections. If you don't know what to select, try with the highest and strongest entry first!");
if(isset($siteconfig['smtp_tls_crypto_method'])) {
$field->notes = $this->attentionMessage($siteconfig['smtp_tls_crypto_method']);
$field->attr('tabindex', '-1');
}
$field->columnWidth = 50;
$field->icon = 'lock';
//$field->showIf = 'smtp_start_tls=1';
$fieldset->add($field);
// SMTP SSL
$field = $modules->get('InputfieldCheckbox');
$field->attr('name', 'smtp_ssl');
$field->attr('id', 'smtp_ssl');
$field->attr('value', 1);
$field->attr('checked', $data['smtp_ssl'] ? 'checked' : '');
$field->columnWidth = 100;
$field->label = $this->_('Use SSL');
$field->description = $this->_('Check if the SMTP server requires secure connections using SSL protocol');
if(isset($siteconfig['smtp_ssl'])) {
$field->notes = $this->attentionMessage($siteconfig['smtp_ssl']);
$field->attr('tabindex', '-1');
}
$field->icon = 'lock';
//$field->showIf = 'smtp_start_tls=0';
$fieldset->add($field);
// SSL crypto method
// $field = $modules->get('InputfieldSelect');
// $field->attr('name', 'smtp_ssl_crypto_method');
// $field->attr('value', $data['smtp_ssl_crypto_method']);
// $field->label = $this->_('Select a crypto method for SSL');
// $availableSSLmethods = WireMailSmtp::getCryptoMethodsSSL();
// array_unshift($availableSSLmethods, array(''));
// $field->addOptions($availableSSLmethods);
// $field->description = $this->_("Select the crypto method that should be used for SSL connections. If you don't know what to select, try with the highest and strongest entry first!");
// if(isset($siteconfig['smtp_ssl_crypto_method'])) {
// $field->notes = $this->attentionMessage($siteconfig['smtp_ssl_crypto_method']);
// $field->attr('tabindex', '-1');
// }
// $field->columnWidth = 50;
// $field->icon = 'lock';
// $fieldset->add($field);
// SMTP CERTIFICATE
// @flydev: https://processwire.com/talk/topic/5704-wiremailsmtp/page-5#entry113290
if(version_compare(phpversion(), '5.6.0', '>=')) {
$field = $modules->get('InputfieldCheckbox');
$field->attr('name', 'smtp_certificate');
$field->label = $this->_('PHP >= 5.6 - Allow self signed certificate');
$field->attr('value', $data['smtp_certificate']);
$field->attr('checked', $data['smtp_certificate'] ? 'checked' : '');
$field->columnWidth = 100;
$field->icon = 'certificate';
$fieldset->add($field);
}
// WRAPPER ADVANCED SMTP SETTINGS
$fieldset2 = $modules->get('InputfieldFieldset');
$fieldset2->label = $this->_('Advanced SMTP');
$fieldset2->attr('name', '_advanced_SMTP');
$fieldset2->collapsed = Inputfield::collapsedYes;
$fieldset2->icon = 'cogs';
// AUTHENTICATION MECHANISM
$field = $modules->get('InputfieldText');
$field->attr('name', 'authentication_mechanism');
$field->attr('value', $data['authentication_mechanism']);
$field->label = $this->_('Authentication Mechanism');
$field->description = $this->_('Force the use of a specific authentication mechanism.');
if(isset($siteconfig['authentication_mechanism'])) {
$field->notes = $this->attentionMessage($siteconfig['authentication_mechanism']);
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_('Default: empty');
}
$field->columnWidth = 33;
$field->icon = 'unlock';
$fieldset2->add($field);
// REALM
$field = $modules->get('InputfieldText');
$field->attr('name', 'realm');
$field->attr('value', $data['realm']);
$field->label = $this->_('Realm');
$field->description = $this->_('Set this variable when the SMTP server requires authentication and if more than one authentication realm is supported');
if(isset($siteconfig['realm'])) {
$field->notes = $this->attentionMessage($siteconfig['realm']);
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_('Default: empty');
}
$field->columnWidth = 34;
$field->icon = 'map-signs';
$fieldset2->add($field);
// WORKSTATION
$field = $modules->get('InputfieldText');
$field->attr('name', 'workstation');
$field->attr('value', $data['workstation']);
$field->label = $this->_('Workstation');
$field->description = $this->_('Set this variable to the client workstation when the SMTP server requires authentication identifiying the origin workstation name');
if(isset($siteconfig['workstation'])) {
$field->notes = $this->attentionMessage($siteconfig['workstation']);
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_('Default: empty');
}
$field->columnWidth = 33;
$field->icon = 'building';
$fieldset2->add($field);
$fieldset->add($fieldset2);
$form->add($fieldset);
// WRAPPER SENDER
$fieldset = $modules->get('InputfieldFieldset');
$fieldset->label = $this->_('Sender');
$fieldset->attr('name', '_sender');
$fieldset->collapsed = Inputfield::collapsedNo;
$fieldset->icon = 'address-book';
// SENDER EMAIL
$field = $modules->get('InputfieldText');
$field->attr('name', 'sender_email');
$field->attr('value', $data['sender_email']);
$field->label = $this->_('Sender Email Address');
if(isset($siteconfig['sender_email'])) {
$field->notes = $this->attentionMessage($siteconfig['sender_email']);
$field->attr('tabindex', '-1');
}
$field->columnWidth = 50;
$field->icon = 'at';
$fieldset->add($field);
// SENDER NAME
$field = $modules->get('InputfieldText');
$field->attr('name', 'sender_name');
$field->attr('value', $data['sender_name']);
$field->label = $this->_('Sender Name');
if(isset($siteconfig['sender_name'])) {
$field->notes = $this->attentionMessage($siteconfig['sender_name']);
$field->attr('tabindex', '-1');
}
$field->columnWidth = 50;
$field->icon = 'user';
$fieldset->add($field);
// SENDER REPLY EMAIL
$field = $modules->get('InputfieldText');
$field->attr('name', 'sender_reply');
$field->attr('value', $data['sender_reply']);
$field->label = $this->_('Reply Email Address');
$field->description = $this->_('if is empty, Sender Emailaddress is used');
if(isset($siteconfig['sender_reply'])) {
$field->notes = $this->attentionMessage($siteconfig['sender_reply']);
$field->attr('tabindex', '-1');
}
$field->columnWidth = 50;
$field->collapsed = Inputfield::collapsedYes;
$field->icon = 'mail-reply';
$fieldset->add($field);
// SENDER ERROR EMAIL
$field = $modules->get('InputfieldText');
$field->attr('name', 'sender_errors_to');
$field->attr('value', $data['sender_errors_to']);
$field->label = $this->_('Errors Email Address');
if(isset($siteconfig['sender_errors_to'])) {
$field->notes = $this->attentionMessage($siteconfig['sender_errors_to']);
$field->attr('tabindex', '-1');
} else {
$field->notes = $this->_('Default: empty');
}
$field->columnWidth = 50;
$field->collapsed = Inputfield::collapsedYes;
$field->icon = 'remove';
$fieldset->add($field);
// SENDER SIGNATURE (TEXT)
$field = $modules->get('InputfieldTextarea');
$field->attr('name', 'sender_signature');
$field->attr('value', $data['sender_signature']);
$field->label = $this->_('Sender Signature (Plain Text)');
$field->description = $this->_('Like Contact Data and / or Confidentiality Notices');
if(isset($siteconfig['sender_signature'])) {
$field->notes = $this->attentionMessage('***');
$field->attr('tabindex', '-1');
}
$field->columnWidth = 33;
$field->icon = 'pencil';
$fieldset->add($field);
// SENDER SIGNATURE (HTML)
$field = $modules->get('InputfieldTextarea');
$field->attr('name', 'sender_signature_html');
$field->attr('value', $data['sender_signature_html']);
$field->label = $this->_('Sender Signature (HTML)');
$field->description = $this->_('Like Contact Data and / or Confidentiality Notices');
if(isset($siteconfig['sender_signature_html'])) {
$field->notes = $this->attentionMessage('***');
$field->attr('tabindex', '-1');
}
$field->columnWidth = 33;
$field->icon = 'code';
$fieldset->add($field);
// SENDER SEND SIGNATURE
$field = $modules->get('InputfieldSelect');
$field->attr('name', 'send_sender_signature');
$field->attr('value', $data['send_sender_signature']);
$field->label = $this->_('Send Sender Signature');
$field->addOptions(array(
'1' => 'only when explicitly called via API',
'2' => 'automaticaly when FROM = Sender Emailaddress',
'3' => 'automaticaly with _every_ Message'
));
$field->description = $this->_('When the Signature should be send by default, (could be overriden by the API)');
$field->columnWidth = 34;
$field->icon = 'question';
$fieldset->add($field);
$form->add($fieldset);
// WRAPPER ADVANCED SETTINGS
$fieldset = $modules->get('InputfieldFieldset');
$fieldset->label = $this->_('Advanced');
$fieldset->attr('name', '_advanced');
$fieldset->collapsed = Inputfield::collapsedYes;
$fieldset->icon = 'gear';
// VALID RECIPIENTS
$field = $modules->get('InputfieldTextarea');
$field->attr('name', 'valid_recipients');
$field->attr('value', $data['valid_recipients']);
$field->label = $this->_('Valid Recipients');
$field->description = $this->_('List of email addresses that can receive messages.');
if(isset($siteconfig['valid_recipients'])) {
$aTemp = array();
foreach($siteconfig['valid_recipients'] as $k => $v) $aTemp[] = "{$k} : {$v}";
$field->notes = $this->attentionMessage("\n" . implode("\n", $aTemp) . "\n");
$field->attr('tabindex', '-1');
unset($k, $v, $aTemp);
} else {
$field->notes = $this->_('One email per line');
}
$field->columnWidth = 50;
$field->icon = 'users';
$fieldset->add($field);
// EXTRA HEADERS
$field = $modules->get('InputfieldTextarea');
$field->attr('name', 'extra_headers');
$field->attr('value', $data['extra_headers']);
$field->label = $this->_('Extra Headers');
$field->description = $this->_('Optionally define custom meta headers.');
if(isset($siteconfig['extra_headers'])) {
$aTemp = array();
foreach($siteconfig['extra_headers'] as $k => $v) $aTemp[] = "{$k} : {$v}";
$field->notes = $this->attentionMessage("\n" . implode("\n", $aTemp) . "\n");
$field->attr('tabindex', '-1');
unset($k, $v, $aTemp);
} else {
$field->notes = $this->_('One email per line');
}
$field->columnWidth = 50;
$field->icon = 'align-left';
$fieldset->add($field);
$form->add($fieldset);
// DISPLAY FINAL MERGED SETTINGS
$field = $modules->get('InputfieldMarkup');
$field->attr('name', '_final_settings');
$field->label = 'Final Merged Settings';
$field->icon = 'filter';
$field->columnWidth = 100;
$field->collapsed = Inputfield::collapsedNo;
$field->attr('value', $this->finalSettingsMessage($siteconfig));
$form->add($field);
// TEST SETTINGS
$field = $modules->get('InputfieldCheckbox');
$field->attr('name', '_test_settings');
$field->label = $this->_('Test settings');
$field->description = $this->_('Test settings now.');
$field->attr('value', 1);
$field->attr('checked', '');
$field->icon = 'heartbeat';
$form->add($field);
// OPTIONAL VERBOSE DEBUGGING
$fieldset = $modules->get('InputfieldFieldset');
$fieldset->label = $this->_('Verbose Debug settings');
$fieldset->attr('name', '_verbosedebug');
$fieldset->collapsed = Inputfield::collapsedNo;
$fieldset->showIf = '_test_settings=1';
$fieldset->icon = 'heartbeat';
$field = $modules->get('InputfieldText');
$field->attr('name', 'debug_senderemail');
$field->attr('value', $data['sender_email']);
$field->label = $this->_('Sender Email Address');
// if(isset($siteconfig['sender_email'])) {
// $field->notes = $this->attentionMessage($siteconfig['sender_email']);
// $field->attr('tabindex', '-1');
// }
$field->columnWidth = 50;
$field->icon = 'at';
$fieldset->add($field);
$field = $modules->get('InputfieldText');
$field->attr('name', 'debug_recipientemail');
$field->attr('value', '');
$field->label = $this->_('Recipient Email Address');
$field->columnWidth = 50;
$field->icon = 'at';
$fieldset->add($field);
$field = $modules->get('InputfieldText');
$field->attr('name', 'debug_subjectline');
$field->attr('value', '');
$field->label = $this->_('Subjectline');
$field->columnWidth = 50;
$field->icon = 'pencil';
$fieldset->add($field);
$field = $modules->get('InputfieldTextarea');
$field->attr('name', 'debug_bodycontent');
$field->attr('value', 'This is a test message. ÄÖÜ äöüß');
$field->label = $this->_('Bodycontent');
$field->columnWidth = 50;
$field->icon = 'envelope-o';
$fieldset->add($field);
$form->add($fieldset);
if(wire('session')->test_settings) {
// EXECUTE DEBUG CONNECTION AND DISPLAY LOG
$field = $modules->get('InputfieldMarkup');
$field->attr('name', '_debug_log');
$field->label = 'Debug Log';
$field->icon = 'heartbeat';
$field->columnWidth = 100;
$field->collapsed = Inputfield::collapsedNo;
$field->attr('value', $this->testSettings());
$form->add($field);
} else if(wire('input')->post->_test_settings) {
// PREPARE SESSION FOR DEBUGGING
$session = wire('session');
$session->set('test_settings', 1);
$post = wire('input')->post;
$session->set('debug_senderemail', $post->debug_senderemail);
$session->set('debug_recipientemail', $post->debug_recipientemail);
$session->set('debug_subjectline', $post->debug_subjectline);
$session->set('debug_bodycontent', $post->debug_bodycontent);
}
return $form;
}
public function testSettings() {
try {
$session = wire('session');
$from = $session->get('debug_senderemail');
$to = array($session->get('debug_recipientemail'));
$subject = $session->get('debug_subjectline');
$body = $session->get('debug_bodycontent');
$session->remove('test_settings');
$session->remove('debug_senderemail');
$session->remove('debug_recipientemail');
$session->remove('debug_subjectline');
$session->remove('debug_bodycontent');
if($from && $to) {
// do a verbose debugging
if(!$subject) $subject = 'Debug Testmail';
if(!$body) $body = 'Debug Testmail, äöüß';
$mail = wireMail();
if($mail->className != 'WireMailSmtp') {
$dump = "<p>Couldn't get the right WireMail-Module (WireMailSmtp). found: {$mail->className}</p>";
} else {
$mail->from = $from;
$mail->to($to);
$mail->subject($subject);
$mail->sendSingle(true);
$mail->body($body);
$dump = $mail->debugSend(3);
}
} else {
// only try a testconnection
$module = wire('modules')->get('WireMailSmtp');
$a = $module->getAdaptor();
if($a->testConnection()) {
$dump = $this->_("SUCCESS! SMTP settings appear to work correctly.");
} else {
$dump = $this->_("FAILURE! SMTP settings doesn't appear to work.");
}
}
} catch(Exception $e) {
$dump = $e->getMessage();
}
$outputTemplate = "<pre style=\"overflow:scroll !important; margin:15px auto; padding:10px; background-color:#ffeedd; color:#000; border:1px solid #AAA; font-family:'Hack', 'Source Code Pro', 'Lucida Console', 'Courier', monospace; font-size:12px; line-height:15px;\">".str_replace(array('<br>', '<br/>', '<br />'), '', $dump) ."</pre>";
return $outputTemplate;
}
private function attentionMessage($value) {
return sprintf($this->_("ATTENTION: Value is overwritten by an entry in your site/config.php:\n -[ %s ]- "), $value);
}
private function finalSettingsMessage($siteconfig) {
$outputTemplate = "<pre style=\"overflow:scroll !important; margin:15px auto; padding:10px; background-color:#ffffdd; color:#555; border:1px solid #AAA; font-family:'Hack', 'Source Code Pro', 'Lucida Console', 'Courier', monospace; font-size:12px; line-height:15px;\">[__CONTENT__]</pre>";
if(!count($siteconfig)) {
$content = 'There are no overriding settings defined in your site/config.php';
return str_replace('[__CONTENT__]', $content, $outputTemplate);
}
$validKeys = array(
'localhost',
'smtp_host',
'smtp_port',
'smtp_ssl',
'smtp_ssl_crypto_method',
'smtp_start_tls',
'smtp_tls_crypto_method',
'smtp_user',
'smtp_password',
'allow_without_authentication',
'smtp_certificate',
'realm',
'workstation',
'authentication_mechanism',
'sender_name',
'sender_email',
'sender_reply',
'sender_errors_to',
'sender_signature',
'sender_signature_html',
'extra_headers',
'valid_recipients',
#'smtp_debug',
#'smtp_html_debug',
);
$module = wire('modules')->get('WireMailSmtp');
$dump = $module->getSettings();
$v = array();
foreach($validKeys as $k) {
if(isset($dump[$k])) {
$v[$k] = 'smtp_password' == $k ? '********' : $dump[$k];
}
}
ob_start();
var_dump($v);
$content = ob_get_contents();
ob_end_clean();
$m = 0;
preg_match_all('#^(.*)=>#mU', $content, $stack);
$lines = $stack[1];
$indents = array_map('strlen', $lines);
if($indents) $m = max($indents) + 1;
$content = preg_replace_callback(
'#^(.*)=>\\n\s+(\S)#Um',
function($match) use ($m) {
return $match[1] . str_repeat(' ', ($m - strlen($match[1]) > 1 ? $m - strlen($match[1]) : 1)) . $match[2];
},
$content
);
$content = preg_replace('#^((\s*).*){$#m', "\\1\n\\2{", $content);
$content = str_replace(array('<pre>', '</pre>'), '', $content);
return str_replace('[__CONTENT__]', $content, $outputTemplate);
}
}

View file

@ -1,61 +0,0 @@
<?php
/*
* basic_sasl_client.php
*
* @(#) $Id: basic_sasl_client.php,v 1.1 2004/11/17 08:01:23 mlemos Exp $
*
*/
define("SASL_BASIC_STATE_START", 0);
define("SASL_BASIC_STATE_DONE", 1);
class basic_sasl_client_class
{
var $credentials=array();
var $state=SASL_BASIC_STATE_START;
Function Initialize(&$client)
{
return(1);
}
Function Start(&$client, &$message, &$interactions)
{
if($this->state!=SASL_BASIC_STATE_START)
{
$client->error="Basic authentication state is not at the start";
return(SASL_FAIL);
}
$this->credentials=array(
"user"=>"",
"password"=>""
);
$defaults=array(
);
$status=$client->GetCredentials($this->credentials,$defaults,$interactions);
if($status==SASL_CONTINUE)
{
$message=$this->credentials["user"].":".$this->credentials["password"];
$this->state=SASL_BASIC_STATE_DONE;
}
else
Unset($message);
return($status);
}
Function Step(&$client, $response, &$message, &$interactions)
{
switch($this->state)
{
case SASL_BASIC_STATE_DONE:
$client->error="Basic authentication was finished without success";
return(SASL_FAIL);
default:
$client->error="invalid Basic authentication step state";
return(SASL_FAIL);
}
return(SASL_CONTINUE);
}
};
?>

View file

@ -1,67 +0,0 @@
<?php
/*
* cram_md5_sasl_client.php
*
* @(#) $Id: cram_md5_sasl_client.php,v 1.3 2004/11/17 08:00:37 mlemos Exp $
*
*/
define("SASL_CRAM_MD5_STATE_START", 0);
define("SASL_CRAM_MD5_STATE_RESPOND_CHALLENGE", 1);
define("SASL_CRAM_MD5_STATE_DONE", 2);
class cram_md5_sasl_client_class
{
var $credentials=array();
var $state=SASL_CRAM_MD5_STATE_START;
Function Initialize(&$client)
{
return(1);
}
Function HMACMD5($key,$text)
{
$key=(strlen($key)<64 ? str_pad($key,64,"\0") : substr($key,0,64));
return(md5((str_repeat("\x5c", 64)^$key).pack("H32", md5((str_repeat("\x36", 64)^$key).$text))));
}
Function Start(&$client, &$message, &$interactions)
{
if($this->state!=SASL_CRAM_MD5_STATE_START)
{
$client->error="CRAM-MD5 authentication state is not at the start";
return(SASL_FAIL);
}
$this->credentials=array(
"user"=>"",
"password"=>""
);
$defaults=array();
$status=$client->GetCredentials($this->credentials,$defaults,$interactions);
if($status==SASL_CONTINUE)
$this->state=SASL_CRAM_MD5_STATE_RESPOND_CHALLENGE;
Unset($message);
return($status);
}
Function Step(&$client, $response, &$message, &$interactions)
{
switch($this->state)
{
case SASL_CRAM_MD5_STATE_RESPOND_CHALLENGE:
$message=$this->credentials["user"]." ".$this->HMACMD5($this->credentials["password"], $response);
$this->state=SASL_CRAM_MD5_STATE_DONE;
break;
case SASL_CRAM_MD5_STATE_DONE:
$client->error="CRAM-MD5 authentication was finished without success";
return(SASL_FAIL);
default:
$client->error="invalid CRAM-MD5 authentication step state";
return(SASL_FAIL);
}
return(SASL_CONTINUE);
}
};
?>

View file

@ -1,135 +0,0 @@
<?php
/*
* digest_sasl_client.php
*
* @(#) $Id: digest_sasl_client.php,v 1.1 2005/10/27 05:24:15 mlemos Exp $
*
*/
define('SASL_DIGEST_STATE_START', 0);
define('SASL_DIGEST_STATE_RESPOND_CHALLENGE', 1);
define('SASL_DIGEST_STATE_DONE', 2);
class digest_sasl_client_class
{
var $credentials=array();
var $state=SASL_DIGEST_STATE_START;
Function unq($string)
{
return(($string[0]=='"' && $string[strlen($string)-1]=='"') ? substr($string, 1, strlen($string)-2) : $string);
}
Function H($data)
{
return md5($data);
}
Function KD($secret, $data)
{
return $this->H($secret.':'.$data);
}
Function Initialize(&$client)
{
return(1);
}
Function Start(&$client, &$message, &$interactions)
{
if($this->state!=SASL_DIGEST_STATE_START)
{
$client->error='Digest authentication state is not at the start';
return(SASL_FAIL);
}
$this->credentials=array(
'user'=>'',
'password'=>'',
'uri'=>'',
'method'=>'',
'session'=>''
);
$defaults=array();
$status=$client->GetCredentials($this->credentials,$defaults,$interactions);
if($status==SASL_CONTINUE)
$this->state=SASL_DIGEST_STATE_RESPOND_CHALLENGE;
Unset($message);
return($status);
}
Function Step(&$client, $response, &$message, &$interactions)
{
switch($this->state)
{
case SASL_DIGEST_STATE_RESPOND_CHALLENGE:
$values=explode(',',$response);
$parameters=array();
for($v=0; $v<count($values); $v++)
$parameters[strtok(trim($values[$v]), '=')]=strtok('');
$message='username="'.$this->credentials['user'].'"';
if(!IsSet($parameters[$p='realm'])
&& !IsSet($parameters[$p='nonce']))
{
$client->error='Digest authentication parameter '.$p.' is missing from the server response';
return(SASL_FAIL);
}
$message.=', realm='.$parameters['realm'];
$message.=', nonce='.$parameters['nonce'];
$message.=', uri="'.$this->credentials['uri'].'"';
if(IsSet($parameters['algorithm']))
{
$algorithm=$this->unq($parameters['algorithm']);
$message.=', algorithm='.$parameters['algorithm'];
}
else
$algorithm='';
$realm=$this->unq($parameters['realm']);
$nonce=$this->unq($parameters['nonce']);
if(IsSet($parameters['qop']))
{
switch($qop=$this->unq($parameters['qop']))
{
case "auth":
$cnonce=$this->credentials['session'];
break;
default:
$client->error='Digest authentication quality of protection '.$qop.' is not yet supported';
return(SASL_FAIL);
}
}
$nc_value='00000001';
if(IsSet($parameters['qop'])
&& !strcmp($algorithm, 'MD5-sess'))
$A1=$this->H($this->credentials['user'].':'. $realm.':'. $this->credentials['password']).':'.$nonce.':'.$cnonce;
else
$A1=$this->credentials['user'].':'. $realm.':'. $this->credentials['password'];
$A2=$this->credentials['method'].':'.$this->credentials['uri'];
if(IsSet($parameters['qop']))
$response=$this->KD($this->H($A1), $nonce.':'. $nc_value.':'. $cnonce.':'. $qop.':'. $this->H($A2));
else
$response=$this->KD($this->H($A1), $nonce.':'. $this->H($A2));
$message.=', response="'.$response.'"';
if(IsSet($parameters['opaque']))
$message.=', opaque='.$parameters['opaque'];
if(IsSet($parameters['qop']))
$message.=', qop="'.$qop.'"';
$message.=', nc='.$nc_value;
if(IsSet($parameters['qop']))
$message.=', cnonce="'.$cnonce.'"';
$client->encode_response=0;
$this->state=SASL_DIGEST_STATE_DONE;
break;
case SASL_DIGEST_STATE_DONE:
$client->error='Digest authentication was finished without success';
return(SASL_FAIL);
default:
$client->error='invalid Digest authentication step state';
return(SASL_FAIL);
}
return(SASL_CONTINUE);
}
};
?>

View file

@ -1,193 +0,0 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>Class: Simple Authentication and Security Layer client</title>
</head>
<body>
<center><h1>Class: Simple Authentication and Security Layer client</h1></center>
<hr />
<ul>
<p><b>Version:</b> <tt>@(#) $Id: sasl_class.html,v 1.1 2014/03/03 12:28:31 horst Exp $</tt></p>
<h2><a name="table_of_contents">Contents</a></h2>
<ul>
<li><a href="#2.1.1">Summary</a></li>
<ul>
<li><a href="#3.2.0">Name</a></li>
<li><a href="#3.2.0.0">Author</a></li>
<li><a href="#3.2.0.1">Copyright</a></li>
<li><a href="#3.2.0.2">Version</a></li>
<li><a href="#3.2.0.3">Purpose</a></li>
<li><a href="#3.2.0.4">Usage</a></li>
</ul>
<li><a href="#4.1.1">Variables</a></li>
<ul>
<li><a href="#5.2.4">error</a></li>
<li><a href="#5.2.5">mechanism</a></li>
<li><a href="#5.2.6">encode_response</a></li>
</ul>
<li><a href="#6.1.1">Functions</a></li>
<ul>
<li><a href="#7.2.5">SetCredential</a></li>
<li><a href="#9.2.6">GetCredentials</a></li>
<li><a href="#11.2.7">Start</a></li>
<li><a href="#13.2.8">Step</a></li>
</ul>
</ul>
<p><a href="#table_of_contents">Top of the table of contents</a></p>
</ul>
<hr />
<ul>
<h2><li><a name="2.1.1">Summary</a></li></h2>
<ul>
<h3><a name="3.2.0">Name</a></h3>
<p>Simple Authentication and Security Layer client</p>
<h3><a name="3.2.0.0">Author</a></h3>
<p>Manuel Lemos (<a href="mailto:mlemos-at-acm.org">mlemos-at-acm.org</a>)</p>
<h3><a name="3.2.0.1">Copyright</a></h3>
<p>Copyright &copy; (C) Manuel Lemos 2004</p>
<h3><a name="3.2.0.2">Version</a></h3>
<p>@(#) $Id: sasl_class.html,v 1.1 2014/03/03 12:28:31 horst Exp $</p>
<h3><a name="3.2.0.3">Purpose</a></h3>
<p>Provide a common interface to plug-in driver classes that implement different mechanisms for authentication used by clients of standard protocols like SMTP, POP3, IMAP, HTTP, etc.. Currently the supported authentication mechanisms are: <tt>PLAIN</tt>, <tt>LOGIN</tt>, <tt>CRAM-MD5</tt>, <tt>Digest</tt> and <tt>NTML</tt> (Windows or Samba).</p>
<h3><a name="3.2.0.4">Usage</a></h3>
<p>.</p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<ul>
<h2><li><a name="variables"></a><a name="4.1.1">Variables</a></li></h2>
<ul>
<li><tt><a href="#variable_error">error</a></tt></li><br />
<li><tt><a href="#variable_mechanism">mechanism</a></tt></li><br />
<li><tt><a href="#variable_encode_response">encode_response</a></tt></li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
<h3><a name="variable_error"></a><li><a name="5.2.4">error</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Store the message that is returned when an error occurs.</p>
<h3>Usage</h3>
<p>Check this variable to understand what happened when a call to any of the class functions has failed.</p>
<p> This class uses cumulative error handling. This means that if one class functions that may fail is called and this variable was already set to an error message due to a failure in a previous call to the same or other function, the function will also fail and does not do anything.</p>
<p> This allows programs using this class to safely call several functions that may fail and only check the failure condition after the last function call.</p>
<p> Just set this variable to an empty string to clear the error condition.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_mechanism"></a><li><a name="5.2.5">mechanism</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Store the name of the mechanism that was selected during the call to the <tt><a href="#function_Start">Start</a></tt> function.</p>
<h3>Usage</h3>
<p>You can access this variable but do not change it.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_encode_response"></a><li><a name="5.2.6">encode_response</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>1</tt></p>
<h3>Purpose</h3>
<p>Let the drivers inform the applications whether responses need to be encoded.</p>
<h3>Usage</h3>
<p>Applications should check this variable before sending authentication responses to the server to determine if the responses need to be encoded, eventually with base64 algorithm.</p>
<p><a href="#variables">Variables</a></p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<ul>
<h2><li><a name="functions"></a><a name="6.1.1">Functions</a></li></h2>
<ul>
<li><tt><a href="#function_SetCredential">SetCredential</a></tt></li><br />
<li><tt><a href="#function_GetCredentials">GetCredentials</a></tt></li><br />
<li><tt><a href="#function_Start">Start</a></tt></li><br />
<li><tt><a href="#function_Step">Step</a></tt></li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
<h3><a name="function_SetCredential"></a><li><a name="7.2.5">SetCredential</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i></i> SetCredential(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_SetCredential_key">key</a></tt><tt>,</tt><br />
<tt><i>string</i> </tt><tt><a href="#argument_SetCredential_value">value</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Store the value of a credential that may be used by any of the supported mechanisms to process the authentication messages and responses.</p>
<h3>Usage</h3>
<p>Call this function before starting the authentication dialog to pass all the credential values that be needed to use the type of authentication that the applications may need.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_SetCredential_key">key</a></b></tt> - Specify the name of the credential key.</p>
<p><tt><b><a name="argument_SetCredential_value">value</a></b></tt> - Specify the value for the credential.</p>
</ul>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_GetCredentials"></a><li><a name="9.2.6">GetCredentials</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>int</i> GetCredentials(</tt><ul>
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_GetCredentials_credentials">credentials</a></tt><tt>,</tt><br />
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_GetCredentials_defaults">defaults</a></tt><tt>,</tt><br />
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_GetCredentials_interactions">interactions</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Retrieve the values of one or more credentials to be used by the authentication mechanism classes.</p>
<h3>Usage</h3>
<p>This is meant to be used by authentication mechanism driver classes to retrieve the credentials that may be neede.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_GetCredentials_credentials">credentials</a></b></tt> - Reference to an associative array variable with all the credentials that are being requested. The function initializes this associative array values.</p>
<p><tt><b><a name="argument_GetCredentials_defaults">defaults</a></b></tt> - Associative arrays with default values for credentials that may have not been defined.</p>
<p><tt><b><a name="argument_GetCredentials_interactions">interactions</a></b></tt> - Not yet in use. It is meant to provide context information to retrieve credentials that may be obtained interacting with the user.</p>
</ul>
<h3>Return value</h3>
<p>The function may return <tt>SASL_CONTINUE</tt> if it succeeded, or <tt>SASL_NOMECH</tt> if it was not possible to retrieve one of the requested credentials.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_Start"></a><li><a name="11.2.7">Start</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>int</i> Start(</tt><ul>
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_Start_mechanisms">mechanisms</a></tt><tt>,</tt><br />
<tt>(output) <i>string &amp;</i> </tt><tt><a href="#argument_Start_message">message</a></tt><tt>,</tt><br />
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_Start_interactions">interactions</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Process the initial authentication step initializing the driver class that implements the first of the list of requested mechanisms that is supported by this SASL client library implementation.</p>
<h3>Usage</h3>
<p>Call this function specifying a list of mechanisms that the server supports. If the <tt><a href="#argument_Start_message">message</a></tt> argument returns a string, it should be sent to the server as initial message. Check the <tt><a href="#variable_encode_response">encode_response</a></tt> variable to determine whether the initial message needs to be encoded, eventually with base64 algorithm, before it is sent to the server.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_Start_mechanisms">mechanisms</a></b></tt> - Define the list of names of authentication mechanisms supported by the that should be tried.</p>
<p><tt><b><a name="argument_Start_message">message</a></b></tt> - Return the initial message that should be sent to the server to start the authentication dialog. If this value is undefined, no message should be sent to the server.</p>
<p><tt><b><a name="argument_Start_interactions">interactions</a></b></tt> - Not yet in use. It is meant to provide context information to interact with the end user.</p>
</ul>
<h3>Return value</h3>
<p>The function may return <tt>SASL_CONTINUE</tt> if it could start one of the requested authentication mechanisms. It may return <tt>SASL_NOMECH</tt> if it was not possible to start any of the requested mechanisms. It returns <tt>SASL_FAIL</tt> or other value in case of error.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_Step"></a><li><a name="13.2.8">Step</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>int</i> Step(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_Step_response">response</a></tt><tt>,</tt><br />
<tt>(output) <i>string &amp;</i> </tt><tt><a href="#argument_Step_message">message</a></tt><tt>,</tt><br />
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_Step_interactions">interactions</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Process the authentication steps after the initial step, until the authetication iteration dialog is complete.</p>
<h3>Usage</h3>
<p>Call this function iteratively after a successful initial step calling the <tt><a href="#function_Start">Start</a></tt> function.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_Step_response">response</a></b></tt> - Pass the response returned by the server to the previous step.</p>
<p><tt><b><a name="argument_Step_message">message</a></b></tt> - Return the message that should be sent to the server to continue the authentication dialog. If this value is undefined, no message should be sent to the server.</p>
<p><tt><b><a name="argument_Step_interactions">interactions</a></b></tt> - Not yet in use. It is meant to provide context information to interact with the end user.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>SASL_CONTINUE</tt> if step was processed successfully, or returns <tt>SASL_FAIL</tt> in case of error.</p>
<p><a href="#functions">Functions</a></p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<address>Manuel Lemos (<a href="mailto:mlemos-at-acm.org">mlemos-at-acm.org</a>)</address>
</body>
</html>

View file

@ -1,584 +0,0 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>Class: Sending e-mail messages via SMTP protocol</title>
</head>
<body>
<center><h1>Class: Sending e-mail messages via SMTP protocol</h1></center>
<hr />
<ul>
<p><b>Version:</b> <tt>@(#) $Id: smtp_class.html,v 1.1 2014/03/03 12:28:31 horst Exp $</tt></p>
<h2><a name="table_of_contents">Contents</a></h2>
<ul>
<li><a href="#2.1.1">Summary</a></li>
<ul>
<li><a href="#3.2.0">Name</a></li>
<li><a href="#3.2.0.0">Author</a></li>
<li><a href="#3.2.0.1">Copyright</a></li>
<li><a href="#3.2.0.2">Version</a></li>
<li><a href="#3.2.0.3">Purpose</a></li>
<li><a href="#3.2.0.4">Translation</a></li>
<li><a href="#3.2.0.5">Support</a></li>
<li><a href="#3.2.0.6">Usage</a></li>
</ul>
<li><a href="#4.1.1">Variables</a></li>
<ul>
<li><a href="#5.2.29">user</a></li>
<li><a href="#5.2.30">realm</a></li>
<li><a href="#5.2.31">password</a></li>
<li><a href="#5.2.32">workstation</a></li>
<li><a href="#5.2.33">authentication_mechanism</a></li>
<li><a href="#5.2.34">host_name</a></li>
<li><a href="#5.2.35">host_port</a></li>
<li><a href="#5.2.36">socks_host_name</a></li>
<li><a href="#5.2.37">socks_host_port</a></li>
<li><a href="#5.2.38">socks_version</a></li>
<li><a href="#5.2.39">http_proxy_host_name</a></li>
<li><a href="#5.2.40">http_proxy_host_port</a></li>
<li><a href="#5.2.41">user_agent</a></li>
<li><a href="#5.2.42">ssl</a></li>
<li><a href="#5.2.43">start_tls</a></li>
<li><a href="#5.2.44">localhost</a></li>
<li><a href="#5.2.45">timeout</a></li>
<li><a href="#5.2.46">data_timeout</a></li>
<li><a href="#5.2.47">direct_delivery</a></li>
<li><a href="#5.2.48">error</a></li>
<li><a href="#5.2.49">debug</a></li>
<li><a href="#5.2.50">html_debug</a></li>
<li><a href="#5.2.51">esmtp</a></li>
<li><a href="#5.2.52">esmtp_extensions</a></li>
<li><a href="#5.2.53">exclude_address</a></li>
<li><a href="#5.2.54">getmxrr</a></li>
<li><a href="#5.2.55">pop3_auth_host</a></li>
<li><a href="#5.2.56">pop3_auth_port</a></li>
</ul>
<li><a href="#6.1.1">Functions</a></li>
<ul>
<li><a href="#7.2.11">Connect</a></li>
<li><a href="#9.2.12">MailFrom</a></li>
<li><a href="#11.2.13">SetRecipient</a></li>
<li><a href="#13.2.14">StartData</a></li>
<li><a href="#13.2.15">PrepareData</a></li>
<li><a href="#15.2.16">SendData</a></li>
<li><a href="#17.2.17">EndSendingData</a></li>
<li><a href="#17.2.18">ResetConnection</a></li>
<li><a href="#17.2.19">Disconnect</a></li>
<li><a href="#19.2.20">SendMessage</a></li>
</ul>
</ul>
<p><a href="#table_of_contents">Top of the table of contents</a></p>
</ul>
<hr />
<ul>
<h2><li><a name="2.1.1">Summary</a></li></h2>
<ul>
<h3><a name="3.2.0">Name</a></h3>
<p>Sending e-mail messages via SMTP protocol</p>
<h3><a name="3.2.0.0">Author</a></h3>
<p>Manuel Lemos (<a href="mailto:mlemos-at-acm.org">mlemos-at-acm.org</a>)</p>
<h3><a name="3.2.0.1">Copyright</a></h3>
<p>Copyright (C) Manuel Lemos 1999-2011</p>
<h3><a name="3.2.0.2">Version</a></h3>
<p>@(#) $Id: smtp_class.html,v 1.1 2014/03/03 12:28:31 horst Exp $</p>
<h3><a name="3.2.0.3">Purpose</a></h3>
<p>Sending e-mail messages via SMTP protocol</p>
<h3><a name="3.2.0.4">Translation</a></h3>
<p>If you are interested in translating the documentation of this class to your own idiom, please <a href="mailto:mlemos-at-acm.org">contact the author</a>.</p>
<h3><a name="3.2.0.5">Support</a></h3>
<p>Technical support for using this class may be obtained in the <tt>smtpclass</tt> support forum. Just go to the support forum pages page to browse the forum archives and post support request messages:</p>
<p> <a href="http://www.phpclasses.org/discuss/package/14/">http://www.phpclasses.org/discuss/package/14/</a></p>
<h3><a name="3.2.0.6">Usage</a></h3>
<p>To use this class just create a new object, set any variables to configure its options and call the <tt><a href="#function_SendMessage">SendMessage</a></tt> function to send a message.</p>
<p>It is not recommended that you use this class alone unless you have deep understanding of Internet mail standards on how to compose compliant e-mail messages. Instead, use the <a href="http://www.phpclasses.org/mimemessage">MIME message composing and sending class</a> and its sub-class SMTP message together with this SMTP class to properly compose e-mail messages, so your messages are not discarded for not being correctly composed.</p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<ul>
<h2><li><a name="variables"></a><a name="4.1.1">Variables</a></li></h2>
<ul>
<li><tt><a href="#variable_user">user</a></tt></li><br />
<li><tt><a href="#variable_realm">realm</a></tt></li><br />
<li><tt><a href="#variable_password">password</a></tt></li><br />
<li><tt><a href="#variable_workstation">workstation</a></tt></li><br />
<li><tt><a href="#variable_authentication_mechanism">authentication_mechanism</a></tt></li><br />
<li><tt><a href="#variable_host_name">host_name</a></tt></li><br />
<li><tt><a href="#variable_host_port">host_port</a></tt></li><br />
<li><tt><a href="#variable_socks_host_name">socks_host_name</a></tt></li><br />
<li><tt><a href="#variable_socks_host_port">socks_host_port</a></tt></li><br />
<li><tt><a href="#variable_socks_version">socks_version</a></tt></li><br />
<li><tt><a href="#variable_http_proxy_host_name">http_proxy_host_name</a></tt></li><br />
<li><tt><a href="#variable_http_proxy_host_port">http_proxy_host_port</a></tt></li><br />
<li><tt><a href="#variable_user_agent">user_agent</a></tt></li><br />
<li><tt><a href="#variable_ssl">ssl</a></tt></li><br />
<li><tt><a href="#variable_start_tls">start_tls</a></tt></li><br />
<li><tt><a href="#variable_localhost">localhost</a></tt></li><br />
<li><tt><a href="#variable_timeout">timeout</a></tt></li><br />
<li><tt><a href="#variable_data_timeout">data_timeout</a></tt></li><br />
<li><tt><a href="#variable_direct_delivery">direct_delivery</a></tt></li><br />
<li><tt><a href="#variable_error">error</a></tt></li><br />
<li><tt><a href="#variable_debug">debug</a></tt></li><br />
<li><tt><a href="#variable_html_debug">html_debug</a></tt></li><br />
<li><tt><a href="#variable_esmtp">esmtp</a></tt></li><br />
<li><tt><a href="#variable_esmtp_extensions">esmtp_extensions</a></tt></li><br />
<li><tt><a href="#variable_exclude_address">exclude_address</a></tt></li><br />
<li><tt><a href="#variable_getmxrr">getmxrr</a></tt></li><br />
<li><tt><a href="#variable_pop3_auth_host">pop3_auth_host</a></tt></li><br />
<li><tt><a href="#variable_pop3_auth_port">pop3_auth_port</a></tt></li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
<h3><a name="variable_user"></a><li><a name="5.2.29">user</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the authorized user when sending messages to a SMTP server.</p>
<h3>Usage</h3>
<p>Set this variable to the user name when the SMTP server requires authentication.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_realm"></a><li><a name="5.2.30">realm</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the authentication realm when sending messages to a SMTP server.</p>
<h3>Usage</h3>
<p>Set this variable when the SMTP server requires authentication and if more than one authentication realm is supported.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_password"></a><li><a name="5.2.31">password</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the authorized user password when sending messages to a SMTP server.</p>
<h3>Usage</h3>
<p>Set this variable to the user password when the SMTP server requires authentication.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_workstation"></a><li><a name="5.2.32">workstation</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the client workstation name when sending messages to a SMTP server.</p>
<h3>Usage</h3>
<p>Set this variable to the client workstation when the SMTP server requires authentication identifiying the origin workstation name.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_authentication_mechanism"></a><li><a name="5.2.33">authentication_mechanism</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Force the use of a specific authentication mechanism.</p>
<h3>Usage</h3>
<p>Set it to an empty string to let the class determine the authentication mechanism to use automatically based on the supported mechanisms by the server and by the SASL client library classes.</p>
<p> Set this variable to a specific mechanism name if you want to override the automatic authentication mechanism selection.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_host_name"></a><li><a name="5.2.34">host_name</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the SMTP server host name.</p>
<h3>Usage</h3>
<p>Set to the host name of the SMTP server to which you want to relay the messages.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_host_port"></a><li><a name="5.2.35">host_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>25</tt></p>
<h3>Purpose</h3>
<p>Define the SMTP server host port.</p>
<h3>Usage</h3>
<p>Set to the TCP port of the SMTP server host to connect.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_socks_host_name"></a><li><a name="5.2.36">socks_host_name</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the SOCKS server host name.</p>
<h3>Usage</h3>
<p>Set to the SOCKS server host name through which the SMTP connection should be routed. Leave it empty if you do not want the connections to be established through a SOCKS server.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_socks_host_port"></a><li><a name="5.2.37">socks_host_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>1080</tt></p>
<h3>Purpose</h3>
<p>Define the SOCKS server host port.</p>
<h3>Usage</h3>
<p>Set to the port of the SOCKS server host through which the the SMTP connection should be routed.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_socks_version"></a><li><a name="5.2.38">socks_version</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>'5'</tt></p>
<h3>Purpose</h3>
<p>Set the SOCKS protocol version.</p>
<h3>Usage</h3>
<p>Change this value if SOCKS server you want to use is listening to a different port.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_http_proxy_host_name"></a><li><a name="5.2.39">http_proxy_host_name</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Define the HTTP proxy server host name.</p>
<h3>Usage</h3>
<p>Set to the HTTP proxy server host name through which the SMTP connection should be routed. Leave it empty if you do not want the connections to be established through an HTTP proxy.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_http_proxy_host_port"></a><li><a name="5.2.40">http_proxy_host_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>80</tt></p>
<h3>Purpose</h3>
<p>Define the HTTP proxy server host port.</p>
<h3>Usage</h3>
<p>Set to the port of the HTTP proxy server host through which the SMTP connection should be routed.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_user_agent"></a><li><a name="5.2.41">user_agent</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>'SMTP Class (http://www.phpclasses.org/smtpclass $Revision: 1.1 $)'</tt></p>
<h3>Purpose</h3>
<p>Set the user agent used when connecting via an HTTP proxy.</p>
<h3>Usage</h3>
<p>Change this value only if for some reason you want emulate a certain e-mail client.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_ssl"></a><li><a name="5.2.42">ssl</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Define whether the connection to the SMTP server should be established securely using SSL protocol.</p>
<h3>Usage</h3>
<p>Set to 1 if the SMTP server requires secure connections using SSL protocol.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_start_tls"></a><li><a name="5.2.43">start_tls</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Define whether the connection to the SMTP server should use encryption after the connection is established using TLS protocol.</p>
<h3>Usage</h3>
<p>Set to 1 if the SMTP server requires that authentication be done securely starting the TLS protocol after the connection is established.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_localhost"></a><li><a name="5.2.44">localhost</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Name of the local host computer</p>
<h3>Usage</h3>
<p>Set to the name of the computer connecting to the SMTP server from the local network.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_timeout"></a><li><a name="5.2.45">timeout</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify the connection timeout period in seconds.</p>
<h3>Usage</h3>
<p>Leave it set to 0 if you want the connection attempts to wait forever. Change this value if for some reason the timeout period seems insufficient or otherwise it seems too long.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_data_timeout"></a><li><a name="5.2.46">data_timeout</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify the timeout period in seconds to wait for data from the server.</p>
<h3>Usage</h3>
<p>Leave it set to 0 if you want to use the same value defined in the <tt><a href="#variable_timeout">timeout</a></tt> variable. Change this value if for some reason the default data timeout period seems insufficient or otherwise it seems too long.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_direct_delivery"></a><li><a name="5.2.47">direct_delivery</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Boolean flag that indicates whether the message should be sent in direct delivery mode, i.e. the message is sent to the SMTP server associated to the domain of the recipient instead of relaying to the server specified by the <tt><a href="#variable_host_name">host_name</a></tt> variable.</p>
<h3>Usage</h3>
<p>Set this to <tt>1</tt> if you want to send urgent messages directly to the recipient domain SMTP server.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_error"></a><li><a name="5.2.48">error</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Message that describes the error when a call to a class function fails.</p>
<h3>Usage</h3>
<p>Check this variable when an error occurs to understand what happened.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_debug"></a><li><a name="5.2.49">debug</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify whether it is necessary to output SMTP connection debug information.</p>
<h3>Usage</h3>
<p>Set this variable to <tt>1</tt> if you need to see the progress of the SMTP connection and protocol dialog when you need to understand the reason for delivery problems.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_html_debug"></a><li><a name="5.2.50">html_debug</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify whether the debug information should be outputted in HTML format.</p>
<h3>Usage</h3>
<p>Set this variable to <tt>1</tt> if you need to see the debug output in a Web page.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_esmtp"></a><li><a name="5.2.51">esmtp</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>1</tt></p>
<h3>Purpose</h3>
<p>Specify whether the class should attempt to use ESMTP extensions supported by the server.</p>
<h3>Usage</h3>
<p>Set this variable to <tt>0</tt> if for some reason you want to avoid benefitting from ESMTP extensions.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_esmtp_extensions"></a><li><a name="5.2.52">esmtp_extensions</a></li></h3>
<h3>Type</h3>
<p><tt><i>array</i></tt></p>
<h3>Default value</h3>
<p><tt>array()</tt></p>
<h3>Purpose</h3>
<p>Associative array with the list of ESMTP extensions supported by the SMTP server.</p>
<h3>Usage</h3>
<p>Check this variable after connecting to the SMTP server to determine which ESMTP extensions are supported.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_exclude_address"></a><li><a name="5.2.53">exclude_address</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify an address that should be considered invalid when resolving host name addresses.</p>
<h3>Usage</h3>
<p>In some networks any domain name that does not exist is resolved as a sub-domain of the default local domain. If the DNS is configured in such way that it always resolves any sub-domain of the default local domain to a given address, it is hard to determine whether a given domain does not exist.</p>
<p> If your network is configured this way, you may set this variable to the address that all sub-domains of the default local domain resolves, so the class can assume that such address is invalid.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_getmxrr"></a><li><a name="5.2.54">getmxrr</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>'getmxrr'</tt></p>
<h3>Purpose</h3>
<p>Specify the name of the function that is called to determine the SMTP server address of a given domain.</p>
<h3>Usage</h3>
<p>Change this to a working replacement of the PHP <tt>getmxrr()</tt> function if this is not working in your system and you want to send messages in direct delivery mode.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_pop3_auth_host"></a><li><a name="5.2.55">pop3_auth_host</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the server address for POP3 based authentication.</p>
<h3>Usage</h3>
<p>Set this variable to the address of the POP3 server if the SMTP server requires POP3 based authentication.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_pop3_auth_port"></a><li><a name="5.2.56">pop3_auth_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>110</tt></p>
<h3>Purpose</h3>
<p>Specify the server port for POP3 based authentication.</p>
<h3>Usage</h3>
<p>Set this variable to the port of the POP3 server if the SMTP server requires POP3 based authentication.</p>
<p><a href="#variables">Variables</a></p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<ul>
<h2><li><a name="functions"></a><a name="6.1.1">Functions</a></li></h2>
<ul>
<li><tt><a href="#function_Connect">Connect</a></tt></li><br />
<li><tt><a href="#function_MailFrom">MailFrom</a></tt></li><br />
<li><tt><a href="#function_SetRecipient">SetRecipient</a></tt></li><br />
<li><tt><a href="#function_StartData">StartData</a></tt></li><br />
<li><tt><a href="#function_PrepareData">PrepareData</a></tt></li><br />
<li><tt><a href="#function_SendData">SendData</a></tt></li><br />
<li><tt><a href="#function_EndSendingData">EndSendingData</a></tt></li><br />
<li><tt><a href="#function_ResetConnection">ResetConnection</a></tt></li><br />
<li><tt><a href="#function_Disconnect">Disconnect</a></tt></li><br />
<li><tt><a href="#function_SendMessage">SendMessage</a></tt></li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
<h3><a name="function_Connect"></a><li><a name="7.2.11">Connect</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> Connect(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_Connect_domain">domain</a></tt> [default '']</ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Connect to an SMTP server.</p>
<h3>Usage</h3>
<p>Call this function as first step to send e-mail messages.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_Connect_domain">domain</a></b></tt> - Specify the domain of the recipient when using the direct delivery mode.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the connection is successfully established.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_MailFrom"></a><li><a name="9.2.12">MailFrom</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> MailFrom(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_MailFrom_sender">sender</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Set the address of the message sender.</p>
<h3>Usage</h3>
<p>Call this function right after establishing a connection with the <tt><a href="#function_Connect">Connect</a></tt> function.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_MailFrom_sender">sender</a></b></tt> - E-mail address of the sender.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the sender address is successfully set.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_SetRecipient"></a><li><a name="11.2.13">SetRecipient</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> SetRecipient(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_SetRecipient_recipient">recipient</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Set the address of a message recipient.</p>
<h3>Usage</h3>
<p>Call this function repeatedly for each recipient right after setting the message sender with the <tt><a href="#function_MailFrom">MailFrom</a></tt> function.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_SetRecipient_recipient">recipient</a></b></tt> - E-mail address of a recipient.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the recipient address is successfully set.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_StartData"></a><li><a name="13.2.14">StartData</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> StartData(</tt><tt>)</tt></p>
<h3>Purpose</h3>
<p>Tell the SMTP server that the message data will start being sent.</p>
<h3>Usage</h3>
<p>Call this function right after you are done setting all the message recipients with the <tt><a href="#function_SetRecipient">SetRecipient</a></tt> function.</p>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the server is ready to start receiving the message data.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_PrepareData"></a><li><a name="13.2.15">PrepareData</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>string</i> PrepareData(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_PrepareData_data">data</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Prepare message data to normalize line breaks and escaping lines that contain single dots.</p>
<h3>Usage</h3>
<p>Call this function if the message data you want to send may contain line breaks that are not the &quot;\r\n&quot; sequence or it may contain lines that just have a single dot.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_PrepareData_data">data</a></b></tt> - Message data to be prepared.</p>
</ul>
<h3>Return value</h3>
<p>Resulting normalized messages data.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_SendData"></a><li><a name="15.2.16">SendData</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> SendData(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_SendData_data">data</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Send message data.</p>
<h3>Usage</h3>
<p>Call this function repeatedly for all message data blocks to be sent right after start sending message data with the <tt><a href="#function_StartData">StartData</a></tt> function.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_SendData_data">data</a></b></tt> - Message data to be sent.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the message data was sent to the SMTP server successfully.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_EndSendingData"></a><li><a name="17.2.17">EndSendingData</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> EndSendingData(</tt><tt>)</tt></p>
<h3>Purpose</h3>
<p>Tell the server that all the message data was sent.</p>
<h3>Usage</h3>
<p>Call this function when you are done with sending the message data with the <tt><a href="#function_SendData">SendData</a></tt> function.</p>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the server accepted the message.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_ResetConnection"></a><li><a name="17.2.18">ResetConnection</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> ResetConnection(</tt><tt>)</tt></p>
<h3>Purpose</h3>
<p>Reset an already established SMTP connection to the initial state.</p>
<h3>Usage</h3>
<p>Call this function when there was an error sending a message and you need to skip to sending another message without disconnecting.</p>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the connection was resetted successfully.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_Disconnect"></a><li><a name="17.2.19">Disconnect</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> Disconnect(</tt><ul>
<tt><i>bool</i> </tt><tt><a href="#argument_Disconnect_quit">quit</a></tt> [default 1]</ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Terminate a previously opened connection.</p>
<h3>Usage</h3>
<p>Call this function after you are done sending your messages.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_Disconnect_quit">quit</a></b></tt> - Boolean option that tells whether the class should perform the final connection quit handshake, or just close the connection without waiting.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the connection was successfully closed.</p>
<p><a href="#functions">Functions</a></p>
<h3><a name="function_SendMessage"></a><li><a name="19.2.20">SendMessage</a></li></h3>
<h3>Synopsis</h3>
<p><tt><i>bool</i> SendMessage(</tt><ul>
<tt><i>string</i> </tt><tt><a href="#argument_SendMessage_sender">sender</a></tt><tt>,</tt><br />
<tt><i>string</i> </tt><tt><a href="#argument_SendMessage_recipients">recipients</a></tt><tt>,</tt><br />
<tt>(input and output) <i>array</i> </tt><tt><a href="#argument_SendMessage_headers">headers</a></tt><tt>,</tt><br />
<tt><i>string</i> </tt><tt><a href="#argument_SendMessage_body">body</a></tt></ul>
<tt>)</tt></p>
<h3>Purpose</h3>
<p>Send a message in a single call.</p>
<h3>Usage</h3>
<p>Call this function if you want to send a single messages to a small number of recipients in a single call.</p>
<h3>Arguments</h3>
<ul>
<p><tt><b><a name="argument_SendMessage_sender">sender</a></b></tt> - E-mail address of the sender.</p>
<p><tt><b><a name="argument_SendMessage_recipients">recipients</a></b></tt> - Array with a list of the e-mail addresses of the recipients of the message.</p>
<p><tt><b><a name="argument_SendMessage_headers">headers</a></b></tt> - Array with a list of the header lines of the message.</p>
<p><tt><b><a name="argument_SendMessage_body">body</a></b></tt> - Body data of the message.</p>
</ul>
<h3>Return value</h3>
<p>The function returns <tt>1</tt> if the message was sent successfully.</p>
<p><a href="#functions">Functions</a></p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<address>Manuel Lemos (<a href="mailto:mlemos-at-acm.org">mlemos-at-acm.org</a>)</address>
</body>
</html>

View file

@ -1,477 +0,0 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>Class: MIME E-mail message composing and sending via SMTP</title>
</head>
<body>
<center><h1>Class: MIME E-mail message composing and sending via SMTP</h1></center>
<hr />
<ul>
<p><b>Version:</b> <tt>@(#) $Id: smtp_message_class.html,v 1.1 2014/03/03 12:28:32 horst Exp $</tt></p>
<h2><a name="table_of_contents">Contents</a></h2>
<ul>
<li><a href="#2.1.1">Summary</a></li>
<ul>
<li><a href="#3.2.0">Name</a></li>
<li><a href="#3.2.0.0">Author</a></li>
<li><a href="#3.2.0.1">Copyright</a></li>
<li><a href="#3.2.0.2">Version</a></li>
<li><a href="#3.2.0.3">Parent classes</a></li>
<li><a href="#4.2.0">Purpose</a></li>
<li><a href="#4.2.0.0">Usage</a></li>
</ul>
<li><a href="#5.1.1">Variables</a></li>
<ul>
<li><a href="#6.2.27">localhost</a></li>
<li><a href="#6.2.28">smtp_host</a></li>
<li><a href="#6.2.29">smtp_port</a></li>
<li><a href="#6.2.30">smtp_ssl</a></li>
<li><a href="#6.2.31">smtp_start_tls</a></li>
<li><a href="#6.2.32">smtp_http_proxy_host_name</a></li>
<li><a href="#6.2.33">smtp_http_proxy_host_port</a></li>
<li><a href="#6.2.34">smtp_socks_host_name</a></li>
<li><a href="#6.2.35">smtp_socks_host_port</a></li>
<li><a href="#6.2.36">smtp_socks_version</a></li>
<li><a href="#6.2.37">smtp_direct_delivery</a></li>
<li><a href="#6.2.38">smtp_getmxrr</a></li>
<li><a href="#6.2.39">smtp_exclude_address</a></li>
<li><a href="#6.2.40">smtp_user</a></li>
<li><a href="#6.2.41">smtp_realm</a></li>
<li><a href="#6.2.42">smtp_workstation</a></li>
<li><a href="#6.2.43">smtp_authentication_mechanism</a></li>
<li><a href="#6.2.44">smtp_password</a></li>
<li><a href="#6.2.45">smtp_pop3_auth_host</a></li>
<li><a href="#6.2.46">smtp_debug</a></li>
<li><a href="#6.2.47">smtp_html_debug</a></li>
<li><a href="#6.2.48">esmtp</a></li>
<li><a href="#6.2.49">timeout</a></li>
<li><a href="#6.2.50">invalid_recipients</a></li>
<li><a href="#6.2.51">mailer_delivery</a></li>
<li><a href="#6.2.52">maximum_bulk_deliveries</a></li>
</ul>
<li><a href="#7.1.1">Inherited variables</a></li>
<li><a href="#9.1.1">Functions</a></li>
<li><a href="#11.1.1">Inherited functions</a></li>
</ul>
<p><a href="#table_of_contents">Top of the table of contents</a></p>
</ul>
<hr />
<ul>
<h2><li><a name="2.1.1">Summary</a></li></h2>
<ul>
<h3><a name="3.2.0">Name</a></h3>
<p>MIME E-mail message composing and sending via SMTP</p>
<h3><a name="3.2.0.0">Author</a></h3>
<p>Manuel Lemos (<a href="mailto:mlemos-at-acm.org">mlemos-at-acm.org</a>)</p>
<h3><a name="3.2.0.1">Copyright</a></h3>
<p>Copyright &copy; (C) Manuel Lemos 1999-2004</p>
<h3><a name="3.2.0.2">Version</a></h3>
<p>@(#) $Id: smtp_message_class.html,v 1.1 2014/03/03 12:28:32 horst Exp $</p>
<h3><a name="3.2.0.3">Parent classes</a></h3>
<ul>
<p><li>MIME E-mail message composing and sending</li></p>
<p><b>Version:</b> <tt>@(#) $Id: smtp_message_class.html,v 1.1 2014/03/03 12:28:32 horst Exp $</tt></p>
</ul>
<h3><a name="4.2.0">Purpose</a></h3>
<p>Implement an alternative message delivery method via SMTP protocol, overriding the method of using the PHP <tt>mail()</tt> function implemented by the base class.</p>
<h3><a name="4.2.0.0">Usage</a></h3>
<p>This class should be used exactly the same way as the base class for composing and sending messages. Just create a new object of this class as follows and set only the necessary variables to configure details of the SMTP delivery.</p>
<p> <tt>require('email_message.php');<br />
require('smtp.php');<br />
require('smtp_message.php');<br />
<br />
$message_object = new smtp_message_class;<br />
</tt></p>
<p> <b>- Requirements</b></p>
<p> You need the <a href="http://freshmeat.net/projects/smtpclass/">SMTP E-mail sending class</a> to perform the actual message delivery via the SMTP protocol.</p>
<p> <b>- SMTP connection</b></p>
<p> Before sending a message by relaying it to a given SMTP server you need set the <tt><a href="#variable_smtp_host">smtp_host</a></tt> variable to that server address. The <tt><a href="#variable_localhost">localhost</a></tt> variable needs to be set to the sending computer address.</p>
<p> You may also adjust the time the class will wait for establishing a connection by changing the <tt><a href="#variable_timeout">timeout</a></tt> variable.</p>
<p> <b>- Secure SMTP connections with SSL</b></p>
<p> Some SMTP servers, like for instance Gmail, require secure connections via SSL. In that case it is necessary to set the <tt><a href="#variable_smtp_ssl">smtp_ssl</a></tt> variable to 1. In the case of Gmail, it is also necessary to set the connection port changing the <tt><a href="#variable_smtp_port">smtp_port</a></tt> variable to 465.</p>
<p> SSL support requires at least PHP 4.3.0 with OpenSSL extension enabled.</p>
<p> <b>- Secure SMTP connections starting TLS after connections is established</b></p>
<p> Some SMTP servers, like for instance Hotmail, require starting the TLS protocol after the connection is already established to exchange data securely. In that case it is necessary to set the <tt><a href="#variable_smtp_start_tls">smtp_start_tls</a></tt> variable to 1.</p>
<p> Starting TLS protocol on an already established connection requires at least PHP 5.1.0 with OpenSSL extension enabled.</p>
<p> <b>- Authentication</b></p>
<p> Most servers only allow relaying messages sent by authorized users. If the SMTP server that you want to use requires authentication, you need to set the variables <tt><a href="#variable_smtp_user">smtp_user</a></tt>, <tt><a href="#variable_smtp_realm">smtp_realm</a></tt> and <tt><a href="#variable_smtp_password">smtp_password</a></tt>.</p>
<p> The way these values need to be set depends on the server. Usually the realm value is empty and only the user and password need to be set. If the server requires authentication via <tt>NTLM</tt> mechanism (Windows or Samba), you need to set the <tt><a href="#variable_smtp_realm">smtp_realm</a></tt> to the Windows domain name and also set the variable <tt><a href="#variable_smtp_workstation">smtp_workstation</a></tt> to the user workstation name.</p>
<p> Some servers require that the authentication be done on a separate server using the POP3 protocol before connecting to the SMTP server. In this case you need to specify the address of the POP3 server setting the <tt><a href="#variable_smtp_pop3_auth_host">smtp_pop3_auth_host</a></tt> variable.</p>
<p> <b>- Sending urgent messages with direct delivery</b></p>
<p> If you need to send urgent messages or obtain immediate confirmation that a message is accepted by the recipient SMTP server, you can use the direct delivery mode setting the <tt><a href="#variable_direct_delivery">direct_delivery</a></tt> variable to <tt>1</tt>. This mode can be used to send a message to only one recipient.</p>
<p> To use this mode, it is necessary to have a way to determine the recipient domain SMTP server address. The class uses the PHP <tt>getmxrr()</tt> function, but on some systems like for instance under Windows, this function does not work. In this case you may specify an equivalent alternative by setting the <tt><a href="#variable_smtp_getmxrr">smtp_getmxrr</a></tt> variable. See the SMTP class page for available alternatives.</p>
<p> <b>- Troubleshooting and debugging</b></p>
<p> If for some reason the delivery via SMTP is not working and the error messages are not self-explanatory, you may set the <tt><a href="#variable_smtp_debug">smtp_debug</a></tt> to <tt>1</tt> to make the class output the SMTP protocol dialog with the server. If you want to display this dialog properly formatted in an HTML page, also set the <tt><a href="#variable_smtp_debug">smtp_debug</a></tt> to <tt>1</tt>.</p>
<p> <b>- Optimizing the delivery of messages to many recipients</b></p>
<p> When sending messages to many recipients, this class can hinted to optimize its behavior by using the <tt><a href="#function_SetBulkMail">SetBulkMail</a></tt> function. After calling this function passing 1 to the <tt><a href="#argument_SetBulkMail_on">on</a></tt> argument, when the message is sent this class opens a TCP connection to the SMTP server but will not close it. This avoids the overhead of opening and closing connections.</p>
<p> When the delivery of the messages to all recipients is done, the connection may be closed implicitly by calling the <tt><a href="#function_SetBulkMail">SetBulkMail</a></tt> function again passing 0 to the <tt><a href="#argument_SetBulkMail_on">on</a></tt> argument.</p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<ul>
<h2><li><a name="variables"></a><a name="5.1.1">Variables</a></li></h2>
<ul>
<li><tt><a href="#variable_localhost">localhost</a></tt></li><br />
<li><tt><a href="#variable_smtp_host">smtp_host</a></tt></li><br />
<li><tt><a href="#variable_smtp_port">smtp_port</a></tt></li><br />
<li><tt><a href="#variable_smtp_ssl">smtp_ssl</a></tt></li><br />
<li><tt><a href="#variable_smtp_start_tls">smtp_start_tls</a></tt></li><br />
<li><tt><a href="#variable_smtp_http_proxy_host_name">smtp_http_proxy_host_name</a></tt></li><br />
<li><tt><a href="#variable_smtp_http_proxy_host_port">smtp_http_proxy_host_port</a></tt></li><br />
<li><tt><a href="#variable_smtp_socks_host_name">smtp_socks_host_name</a></tt></li><br />
<li><tt><a href="#variable_smtp_socks_host_port">smtp_socks_host_port</a></tt></li><br />
<li><tt><a href="#variable_smtp_socks_version">smtp_socks_version</a></tt></li><br />
<li><tt><a href="#variable_smtp_direct_delivery">smtp_direct_delivery</a></tt></li><br />
<li><tt><a href="#variable_smtp_getmxrr">smtp_getmxrr</a></tt></li><br />
<li><tt><a href="#variable_smtp_exclude_address">smtp_exclude_address</a></tt></li><br />
<li><tt><a href="#variable_smtp_user">smtp_user</a></tt></li><br />
<li><tt><a href="#variable_smtp_realm">smtp_realm</a></tt></li><br />
<li><tt><a href="#variable_smtp_workstation">smtp_workstation</a></tt></li><br />
<li><tt><a href="#variable_smtp_authentication_mechanism">smtp_authentication_mechanism</a></tt></li><br />
<li><tt><a href="#variable_smtp_password">smtp_password</a></tt></li><br />
<li><tt><a href="#variable_smtp_pop3_auth_host">smtp_pop3_auth_host</a></tt></li><br />
<li><tt><a href="#variable_smtp_debug">smtp_debug</a></tt></li><br />
<li><tt><a href="#variable_smtp_html_debug">smtp_html_debug</a></tt></li><br />
<li><tt><a href="#variable_esmtp">esmtp</a></tt></li><br />
<li><tt><a href="#variable_timeout">timeout</a></tt></li><br />
<li><tt><a href="#variable_invalid_recipients">invalid_recipients</a></tt></li><br />
<li><tt><a href="#variable_mailer_delivery">mailer_delivery</a></tt></li><br />
<li><tt><a href="#variable_maximum_bulk_deliveries">maximum_bulk_deliveries</a></tt></li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
<h3><a name="variable_localhost"></a><li><a name="6.2.27">localhost</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the domain name of the computer sending the message.</p>
<h3>Usage</h3>
<p>This value is used to identify the sending machine to the SMTP server. When using the direct delivery mode, if this variable is set to a non-empty string it used to generate the <tt>Recieved</tt> header to show that the message passed by the specified host address. To prevent confusing directly delivered messages with spam, it is strongly recommended that you set this variable to you server host name.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_host"></a><li><a name="6.2.28">smtp_host</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the address of the SMTP server.</p>
<h3>Usage</h3>
<p>Set to the address of the SMTP server that will relay the messages. This variable is not used in direct delivery mode.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_port"></a><li><a name="6.2.29">smtp_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>25</tt></p>
<h3>Purpose</h3>
<p>Specify the TCP/IP port of SMTP server to connect.</p>
<h3>Usage</h3>
<p>Most servers work on port 25 . Certain e-mail services use alternative ports to avoid firewall blocking. Gmail uses port 465.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_ssl"></a><li><a name="6.2.30">smtp_ssl</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify whether it should use secure connections with SSL to connect to the SMTP server.</p>
<h3>Usage</h3>
<p>Certain e-mail services like Gmail require SSL connections.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_start_tls"></a><li><a name="6.2.31">smtp_start_tls</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify whether it should use secure connections starting TLS protocol after connecting to the SMTP server.</p>
<h3>Usage</h3>
<p>Certain e-mail services like Hotmail require starting TLS protocol after the connection to the SMTP server is already established.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_http_proxy_host_name"></a><li><a name="6.2.32">smtp_http_proxy_host_name</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify name of the host when the connection should be routed via an HTTP proxy.</p>
<h3>Usage</h3>
<p>Leave empty if no proxy should be used.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_http_proxy_host_port"></a><li><a name="6.2.33">smtp_http_proxy_host_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>3128</tt></p>
<h3>Purpose</h3>
<p>Specify proxy port when the connection should be routed via an HTTP proxy.</p>
<h3>Usage</h3>
<p>Change this variable if you need to use a proxy with a specific port.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_socks_host_name"></a><li><a name="6.2.34">smtp_socks_host_name</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify name of the host when the connection should be routed via a SOCKS protocol proxy.</p>
<h3>Usage</h3>
<p>Leave empty if no proxy should be used.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_socks_host_port"></a><li><a name="6.2.35">smtp_socks_host_port</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>1080</tt></p>
<h3>Purpose</h3>
<p>Specify proxy port when the connection should be routed via a SOCKS protocol proxy.</p>
<h3>Usage</h3>
<p>Change this variable if you need to use a proxy with a specific port.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_socks_version"></a><li><a name="6.2.36">smtp_socks_version</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify protocol version when the connection should be routed via a SOCKS protocol proxy.</p>
<h3>Usage</h3>
<p>Change this variable if you need to use a proxy with a specific SOCKS protocol version.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_direct_delivery"></a><li><a name="6.2.37">smtp_direct_delivery</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Boolean flag that indicates whether the message should be sent in direct delivery mode.</p>
<h3>Usage</h3>
<p>Set this to <tt>1</tt> if you want to send urgent messages directly to the recipient domain SMTP server.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_getmxrr"></a><li><a name="6.2.38">smtp_getmxrr</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>'getmxrr'</tt></p>
<h3>Purpose</h3>
<p>Specify the name of the function that is called to determine the SMTP server address of a given domain.</p>
<h3>Usage</h3>
<p>Change this to a working replacement of the PHP <tt>getmxrr()</tt> function if this is not working in your system and you want to send messages in direct delivery mode.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_exclude_address"></a><li><a name="6.2.39">smtp_exclude_address</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify an address that should be considered invalid when resolving host name addresses.</p>
<h3>Usage</h3>
<p>In some networks any domain name that does not exist is resolved as a sub-domain of the default local domain. If the DNS is configured in such way that it always resolves any sub-domain of the default local domain to a given address, it is hard to determine whether a given domain does not exist.</p>
<p> If your network is configured this way, you may set this variable to the address that all sub-domains of the default local domain resolves, so the class can assume that such address is invalid.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_user"></a><li><a name="6.2.40">smtp_user</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the user name for authentication.</p>
<h3>Usage</h3>
<p>Set this variable if you need to authenticate before sending a message.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_realm"></a><li><a name="6.2.41">smtp_realm</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the user authentication realm.</p>
<h3>Usage</h3>
<p>Set this variable if you need to authenticate before sending a message.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_workstation"></a><li><a name="6.2.42">smtp_workstation</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the user authentication workstation needed when using the <tt>NTLM</tt> authentication (Windows or Samba).</p>
<h3>Usage</h3>
<p>Set this variable if you need to authenticate before sending a message.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_authentication_mechanism"></a><li><a name="6.2.43">smtp_authentication_mechanism</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the user authentication mechanism that should be used when authenticating with the SMTP server.</p>
<h3>Usage</h3>
<p>Set this variable if you need to force the SMTP connection to authenticate with a specific authentication mechanism. Leave this variable with an empty string if you want the authentication mechanism be determined automatically from the list of mechanisms supported by the server.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_password"></a><li><a name="6.2.44">smtp_password</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the user authentication password.</p>
<h3>Usage</h3>
<p>Set this variable if you need to authenticate before sending a message.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_pop3_auth_host"></a><li><a name="6.2.45">smtp_pop3_auth_host</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>''</tt></p>
<h3>Purpose</h3>
<p>Specify the server address for POP3 based authentication.</p>
<h3>Usage</h3>
<p>Set this variable to the address of the POP3 server if the SMTP server requires POP3 based authentication.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_debug"></a><li><a name="6.2.46">smtp_debug</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify whether it is necessary to output SMTP connection debug information.</p>
<h3>Usage</h3>
<p>Set this variable to <tt>1</tt> if you need to see the progress of the SMTP connection and protocol dialog when you need to understand the reason for delivery problems.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_smtp_html_debug"></a><li><a name="6.2.47">smtp_html_debug</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>0</tt></p>
<h3>Purpose</h3>
<p>Specify whether the debug information should be outputted in HTML format.</p>
<h3>Usage</h3>
<p>Set this variable to <tt>1</tt> if you need to see the debug output in a Web page.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_esmtp"></a><li><a name="6.2.48">esmtp</a></li></h3>
<h3>Type</h3>
<p><tt><i>bool</i></tt></p>
<h3>Default value</h3>
<p><tt>1</tt></p>
<h3>Purpose</h3>
<p>Specify whether the class should try to use Enhanced SMTP protocol features.</p>
<h3>Usage</h3>
<p>It is recommended to leave this variable set to <tt>1</tt> so the class can take advantage of Enhanced SMTP protocol features.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_timeout"></a><li><a name="6.2.49">timeout</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>25</tt></p>
<h3>Purpose</h3>
<p>Specify the connection timeout period in seconds.</p>
<h3>Usage</h3>
<p>Change this value if for some reason the timeout period seems insufficient or otherwise it seems too long.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_invalid_recipients"></a><li><a name="6.2.50">invalid_recipients</a></li></h3>
<h3>Type</h3>
<p><tt><i>array</i></tt></p>
<h3>Default value</h3>
<p><tt>array()</tt></p>
<h3>Purpose</h3>
<p>Return the list of recipient addresses that were not accepted by the SMTP server.</p>
<h3>Usage</h3>
<p>Check this variable after attempting to send a message to figure whether there were any recipients that were rejected by the SMTP server.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_mailer_delivery"></a><li><a name="6.2.51">mailer_delivery</a></li></h3>
<h3>Type</h3>
<p><tt><i>string</i></tt></p>
<h3>Default value</h3>
<p><tt>'smtp $Revision: 1.1 $'</tt></p>
<h3>Purpose</h3>
<p>Specify the text that is used to identify the mail delivery class or sub-class. This text is appended to the <tt>X-Mailer</tt> header text defined by the mailer variable.</p>
<h3>Usage</h3>
<p>Do not change this variable.</p>
<p><a href="#variables">Variables</a></p>
<h3><a name="variable_maximum_bulk_deliveries"></a><li><a name="6.2.52">maximum_bulk_deliveries</a></li></h3>
<h3>Type</h3>
<p><tt><i>int</i></tt></p>
<h3>Default value</h3>
<p><tt>100</tt></p>
<h3>Purpose</h3>
<p>Specify the number of consecutive bulk mail deliveries without disconnecting.</p>
<h3>Usage</h3>
<p>Lower this value if you have enabled the bulk mail mode but the SMTP server does not accept sending more than a number of messages within the same SMTP connection.</p>
<p> Set this value to 0 to never disconnect during bulk mail mode unless an error occurs.</p>
<p><a href="#variables">Variables</a></p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<ul>
<h2><li><a name="functions"></a><a name="7.1.1">Inherited variables</a></li></h2>
<ul>
<li>email_regular_expression</li><br />
<li>mailer</li><br />
<li>default_charset</li><br />
<li>line_quote_prefix</li><br />
<li>break_long_lines</li><br />
<li>file_buffer_length</li><br />
<li>debug</li><br />
<li>cache_body</li><br />
<li>error</li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<ul>
<h2><li><a name="functions"></a><a name="9.1.1">Functions</a></li></h2>
<ul>
<p><a href="#table_of_contents">Table of contents</a></p>
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<ul>
<h2><li><a name="functions"></a><a name="11.1.1">Inherited functions</a></li></h2>
<ul>
<li>ValidateEmailAddress</li><br />
<li>WrapText</li><br />
<li>CenterText</li><br />
<li>Ruler</li><br />
<li>QuoteText</li><br />
<li>SetHeader</li><br />
<li>SetEncodedHeader</li><br />
<li>SetEncodedEmailHeader</li><br />
<li>SetMultipleEncodedEmailHeader</li><br />
<li>ResetMessage</li><br />
<li>AddPart</li><br />
<li>ReplacePart</li><br />
<li>CreatePlainTextPart</li><br />
<li>AddPlainTextPart</li><br />
<li>CreateQuotedPrintableTextPart</li><br />
<li>AddQuotedPrintableTextPart</li><br />
<li>CreateHTMLPart</li><br />
<li>AddHTMLPart</li><br />
<li>CreateQuotedPrintableHTMLPart</li><br />
<li>AddQuotedPrintableHTMLPart</li><br />
<li>CreateFilePart</li><br />
<li>AddFilePart</li><br />
<li>CreateMessagePart</li><br />
<li>AddMessagePart</li><br />
<li>CreateAlternativeMultipart</li><br />
<li>AddAlternativeMultipart</li><br />
<li>CreateRelatedMultipart</li><br />
<li>AddRelatedMultipart</li><br />
<li>CreateMixedMultipart</li><br />
<li>AddMixedMultipart</li><br />
<li>GetPartContentID</li><br />
<li>GetDataURL</li><br />
<li>Send</li><br />
<li>GetMessage</li><br />
<li>GetMessageSize</li><br />
<li>Mail</li><br />
<li>SetBulkMail</li><br />
<p><a href="#table_of_contents">Table of contents</a></p>
</ul>
</ul>
<hr />
<address>Manuel Lemos (<a href="mailto:mlemos-at-acm.org">mlemos-at-acm.org</a>)</address>
</body>
</html>

File diff suppressed because it is too large Load diff

View file

@ -1,69 +0,0 @@
<?php
/*
* login_sasl_client.php
*
* @(#) $Id: login_sasl_client.php,v 1.2 2004/11/17 08:00:37 mlemos Exp $
*
*/
define("SASL_LOGIN_STATE_START", 0);
define("SASL_LOGIN_STATE_IDENTIFY_USER", 1);
define("SASL_LOGIN_STATE_IDENTIFY_PASSWORD", 2);
define("SASL_LOGIN_STATE_DONE", 3);
class login_sasl_client_class
{
var $credentials=array();
var $state=SASL_LOGIN_STATE_START;
Function Initialize(&$client)
{
return(1);
}
Function Start(&$client, &$message, &$interactions)
{
if($this->state!=SASL_LOGIN_STATE_START)
{
$client->error="LOGIN authentication state is not at the start";
return(SASL_FAIL);
}
$this->credentials=array(
"user"=>"",
"password"=>"",
"realm"=>""
);
$defaults=array(
"realm"=>""
);
$status=$client->GetCredentials($this->credentials,$defaults,$interactions);
if($status==SASL_CONTINUE)
$this->state=SASL_LOGIN_STATE_IDENTIFY_USER;
Unset($message);
return($status);
}
Function Step(&$client, $response, &$message, &$interactions)
{
switch($this->state)
{
case SASL_LOGIN_STATE_IDENTIFY_USER:
$message=$this->credentials["user"].(strlen($this->credentials["realm"]) ? "@".$this->credentials["realm"] : "");
$this->state=SASL_LOGIN_STATE_IDENTIFY_PASSWORD;
break;
case SASL_LOGIN_STATE_IDENTIFY_PASSWORD:
$message=$this->credentials["password"];
$this->state=SASL_LOGIN_STATE_DONE;
break;
case SASL_LOGIN_STATE_DONE:
$client->error="LOGIN authentication was finished without success";
break;
default:
$client->error="invalid LOGIN authentication step state";
return(SASL_FAIL);
}
return(SASL_CONTINUE);
}
};
?>

View file

@ -1,180 +0,0 @@
<?php
/*
* ntlm_sasl_client.php
*
* @(#) $Id: ntlm_sasl_client.php,v 1.3 2004/11/17 08:00:37 mlemos Exp $
*
*/
define("SASL_NTLM_STATE_START", 0);
define("SASL_NTLM_STATE_IDENTIFY_DOMAIN", 1);
define("SASL_NTLM_STATE_RESPOND_CHALLENGE", 2);
define("SASL_NTLM_STATE_DONE", 3);
class ntlm_sasl_client_class
{
var $credentials=array();
var $state=SASL_NTLM_STATE_START;
Function Initialize(&$client)
{
if(!function_exists($function="mcrypt_encrypt")
|| !function_exists($function="mhash"))
{
$extensions=array(
"mcrypt_encrypt"=>"mcrypt",
"mhash"=>"mhash"
);
$client->error="the extension ".$extensions[$function]." required by the NTLM SASL client class is not available in this PHP configuration";
return(0);
}
return(1);
}
Function ASCIIToUnicode($ascii)
{
for($unicode="",$a=0;$a<strlen($ascii);$a++)
$unicode.=substr($ascii,$a,1).chr(0);
return($unicode);
}
Function TypeMsg1($domain,$workstation)
{
$domain_length=strlen($domain);
$workstation_length=strlen($workstation);
$workstation_offset=32;
$domain_offset=$workstation_offset+$workstation_length;
return(
"NTLMSSP\0".
"\x01\x00\x00\x00".
"\x07\x32\x00\x00".
pack("v",$domain_length).
pack("v",$domain_length).
pack("V",$domain_offset).
pack("v",$workstation_length).
pack("v",$workstation_length).
pack("V",$workstation_offset).
$workstation.
$domain
);
}
Function NTLMResponse($challenge,$password)
{
$unicode=$this->ASCIIToUnicode($password);
$md4=mhash(MHASH_MD4,$unicode);
$padded=$md4.str_repeat(chr(0),21-strlen($md4));
$iv_size=mcrypt_get_iv_size(MCRYPT_DES,MCRYPT_MODE_ECB);
$iv=mcrypt_create_iv($iv_size,MCRYPT_RAND);
for($response="",$third=0;$third<21;$third+=7)
{
for($packed="",$p=$third;$p<$third+7;$p++)
$packed.=str_pad(decbin(ord(substr($padded,$p,1))),8,"0",STR_PAD_LEFT);
for($key="",$p=0;$p<strlen($packed);$p+=7)
{
$s=substr($packed,$p,7);
$b=$s.((substr_count($s,"1") % 2) ? "0" : "1");
$key.=chr(bindec($b));
}
$ciphertext=mcrypt_encrypt(MCRYPT_DES,$key,$challenge,MCRYPT_MODE_ECB,$iv);
$response.=$ciphertext;
}
return $response;
}
Function TypeMsg3($ntlm_response,$user,$domain,$workstation)
{
$domain_unicode=$this->ASCIIToUnicode($domain);
$domain_length=strlen($domain_unicode);
$domain_offset=64;
$user_unicode=$this->ASCIIToUnicode($user);
$user_length=strlen($user_unicode);
$user_offset=$domain_offset+$domain_length;
$workstation_unicode=$this->ASCIIToUnicode($workstation);
$workstation_length=strlen($workstation_unicode);
$workstation_offset=$user_offset+$user_length;
$lm="";
$lm_length=strlen($lm);
$lm_offset=$workstation_offset+$workstation_length;
$ntlm=$ntlm_response;
$ntlm_length=strlen($ntlm);
$ntlm_offset=$lm_offset+$lm_length;
$session="";
$session_length=strlen($session);
$session_offset=$ntlm_offset+$ntlm_length;
return(
"NTLMSSP\0".
"\x03\x00\x00\x00".
pack("v",$lm_length).
pack("v",$lm_length).
pack("V",$lm_offset).
pack("v",$ntlm_length).
pack("v",$ntlm_length).
pack("V",$ntlm_offset).
pack("v",$domain_length).
pack("v",$domain_length).
pack("V",$domain_offset).
pack("v",$user_length).
pack("v",$user_length).
pack("V",$user_offset).
pack("v",$workstation_length).
pack("v",$workstation_length).
pack("V",$workstation_offset).
pack("v",$session_length).
pack("v",$session_length).
pack("V",$session_offset).
"\x01\x02\x00\x00".
$domain_unicode.
$user_unicode.
$workstation_unicode.
$lm.
$ntlm
);
}
Function Start(&$client, &$message, &$interactions)
{
if($this->state!=SASL_NTLM_STATE_START)
{
$client->error="NTLM authentication state is not at the start";
return(SASL_FAIL);
}
$this->credentials=array(
"user"=>"",
"password"=>"",
"realm"=>"",
"workstation"=>""
);
$defaults=array();
$status=$client->GetCredentials($this->credentials,$defaults,$interactions);
if($status==SASL_CONTINUE)
$this->state=SASL_NTLM_STATE_IDENTIFY_DOMAIN;
Unset($message);
return($status);
}
Function Step(&$client, $response, &$message, &$interactions)
{
switch($this->state)
{
case SASL_NTLM_STATE_IDENTIFY_DOMAIN:
$message=$this->TypeMsg1($this->credentials["realm"],$this->credentials["workstation"]);
$this->state=SASL_NTLM_STATE_RESPOND_CHALLENGE;
break;
case SASL_NTLM_STATE_RESPOND_CHALLENGE:
$ntlm_response=$this->NTLMResponse(substr($response,24,8),$this->credentials["password"]);
$message=$this->TypeMsg3($ntlm_response,$this->credentials["user"],$this->credentials["realm"],$this->credentials["workstation"]);
$this->state=SASL_NTLM_STATE_DONE;
break;
case SASL_NTLM_STATE_DONE:
$client->error="NTLM authentication was finished without success";
return(SASL_FAIL);
default:
$client->error="invalid NTLM authentication step state";
return(SASL_FAIL);
}
return(SASL_CONTINUE);
}
};
?>

View file

@ -1,99 +0,0 @@
<?php
/*
* plain_sasl_client.php
*
* @(#) $Id: plain_sasl_client.php,v 1.2 2004/11/17 08:00:37 mlemos Exp $
*
*/
define("SASL_PLAIN_STATE_START", 0);
define("SASL_PLAIN_STATE_IDENTIFY", 1);
define("SASL_PLAIN_STATE_DONE", 2);
define("SASL_PLAIN_DEFAULT_MODE", 0);
define("SASL_PLAIN_EXIM_MODE", 1);
define("SASL_PLAIN_EXIM_DOCUMENTATION_MODE", 2);
class plain_sasl_client_class
{
var $credentials=array();
var $state=SASL_PLAIN_STATE_START;
Function Initialize(&$client)
{
return(1);
}
Function Start(&$client, &$message, &$interactions)
{
if($this->state!=SASL_PLAIN_STATE_START)
{
$client->error="PLAIN authentication state is not at the start";
return(SASL_FAIL);
}
$this->credentials=array(
"user"=>"",
"password"=>"",
"realm"=>"",
"mode"=>""
);
$defaults=array(
"realm"=>"",
"mode"=>""
);
$status=$client->GetCredentials($this->credentials,$defaults,$interactions);
if($status==SASL_CONTINUE)
{
switch($this->credentials["mode"])
{
case SASL_PLAIN_EXIM_MODE:
$message=$this->credentials["user"]."\0".$this->credentials["password"]."\0";
break;
case SASL_PLAIN_EXIM_DOCUMENTATION_MODE:
$message="\0".$this->credentials["user"]."\0".$this->credentials["password"];
break;
default:
$message=$this->credentials["user"]."\0".$this->credentials["user"].(strlen($this->credentials["realm"]) ? "@".$this->credentials["realm"] : "")."\0".$this->credentials["password"];
break;
}
$this->state=SASL_PLAIN_STATE_DONE;
}
else
Unset($message);
return($status);
}
Function Step(&$client, $response, &$message, &$interactions)
{
switch($this->state)
{
/*
case SASL_PLAIN_STATE_IDENTIFY:
switch($this->credentials["mode"])
{
case SASL_PLAIN_EXIM_MODE:
$message=$this->credentials["user"]."\0".$this->credentials["password"]."\0";
break;
case SASL_PLAIN_EXIM_DOCUMENTATION_MODE:
$message="\0".$this->credentials["user"]."\0".$this->credentials["password"];
break;
default:
$message=$this->credentials["user"]."\0".$this->credentials["user"].(strlen($this->credentials["realm"]) ? "@".$this->credentials["realm"] : "")."\0".$this->credentials["password"];
break;
}
var_dump($message);
$this->state=SASL_PLAIN_STATE_DONE;
break;
*/
case SASL_PLAIN_STATE_DONE:
$client->error="PLAIN authentication was finished without success";
return(SASL_FAIL);
default:
$client->error="invalid PLAIN authentication step state";
return(SASL_FAIL);
}
return(SASL_CONTINUE);
}
};
?>

View file

@ -1,422 +0,0 @@
<?php
/*
* sasl.php
*
* @(#) $Id: sasl.php,v 1.11 2005/10/31 18:43:27 mlemos Exp $
*
*/
define("SASL_INTERACT", 2);
define("SASL_CONTINUE", 1);
define("SASL_OK", 0);
define("SASL_FAIL", -1);
define("SASL_NOMECH", -4);
class sasl_interact_class
{
var $id;
var $challenge;
var $prompt;
var $default_result;
var $result;
};
/*
{metadocument}<?xml version="1.0" encoding="ISO-8859-1" ?>
<class>
<package>net.manuellemos.sasl</package>
<version>@(#) $Id: sasl.php,v 1.11 2005/10/31 18:43:27 mlemos Exp $</version>
<copyright>Copyright © (C) Manuel Lemos 2004</copyright>
<title>Simple Authentication and Security Layer client</title>
<author>Manuel Lemos</author>
<authoraddress>mlemos-at-acm.org</authoraddress>
<documentation>
<idiom>en</idiom>
<purpose>Provide a common interface to plug-in driver classes that
implement different mechanisms for authentication used by clients of
standard protocols like SMTP, POP3, IMAP, HTTP, etc.. Currently the
supported authentication mechanisms are: <tt>PLAIN</tt>,
<tt>LOGIN</tt>, <tt>CRAM-MD5</tt>, <tt>Digest</tt> and <tt>NTML</tt>
(Windows or Samba).</purpose>
<usage>.</usage>
</documentation>
{/metadocument}
*/
class sasl_client_class
{
/* Public variables */
/*
{metadocument}
<variable>
<name>error</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Store the message that is returned when an error
occurs.</purpose>
<usage>Check this variable to understand what happened when a call to
any of the class functions has failed.<paragraphbreak />
This class uses cumulative error handling. This means that if one
class functions that may fail is called and this variable was
already set to an error message due to a failure in a previous call
to the same or other function, the function will also fail and does
not do anything.<paragraphbreak />
This allows programs using this class to safely call several
functions that may fail and only check the failure condition after
the last function call.<paragraphbreak />
Just set this variable to an empty string to clear the error
condition.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $error='';
/*
{metadocument}
<variable>
<name>mechanism</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Store the name of the mechanism that was selected during the
call to the <functionlink>Start</functionlink> function.</purpose>
<usage>You can access this variable but do not change it.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $mechanism='';
/*
{metadocument}
<variable>
<name>encode_response</name>
<type>BOOLEAN</type>
<value>1</value>
<documentation>
<purpose>Let the drivers inform the applications whether responses
need to be encoded.</purpose>
<usage>Applications should check this variable before sending
authentication responses to the server to determine if the
responses need to be encoded, eventually with base64 algorithm.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $encode_response=1;
/* Private variables */
var $driver;
var $drivers=array(
"Digest" => array("digest_sasl_client_class", "digest_sasl_client.php" ),
"CRAM-MD5" => array("cram_md5_sasl_client_class", "cram_md5_sasl_client.php" ),
"LOGIN" => array("login_sasl_client_class", "login_sasl_client.php" ),
"NTLM" => array("ntlm_sasl_client_class", "ntlm_sasl_client.php" ),
"PLAIN" => array("plain_sasl_client_class", "plain_sasl_client.php" ),
"Basic" => array("basic_sasl_client_class", "basic_sasl_client.php" )
);
var $credentials=array();
/* Public functions */
/*
{metadocument}
<function>
<name>SetCredential</name>
<type>VOID</type>
<documentation>
<purpose>Store the value of a credential that may be used by any of
the supported mechanisms to process the authentication messages and
responses.</purpose>
<usage>Call this function before starting the authentication dialog
to pass all the credential values that be needed to use the type
of authentication that the applications may need.</usage>
<returnvalue>.</returnvalue>
</documentation>
<argument>
<name>key</name>
<type>STRING</type>
<documentation>
<purpose>Specify the name of the credential key.</purpose>
</documentation>
</argument>
<argument>
<name>value</name>
<type>STRING</type>
<documentation>
<purpose>Specify the value for the credential.</purpose>
</documentation>
</argument>
<do>
{/metadocument}
*/
Function SetCredential($key,$value)
{
$this->credentials[$key]=$value;
}
/*
{metadocument}
</do>
</function>
{/metadocument}
*/
/*
{metadocument}
<function>
<name>GetCredentials</name>
<type>INTEGER</type>
<documentation>
<purpose>Retrieve the values of one or more credentials to be used by
the authentication mechanism classes.</purpose>
<usage>This is meant to be used by authentication mechanism driver
classes to retrieve the credentials that may be neede.</usage>
<returnvalue>The function may return <tt>SASL_CONTINUE</tt> if it
succeeded, or <tt>SASL_NOMECH</tt> if it was not possible to
retrieve one of the requested credentials.</returnvalue>
</documentation>
<argument>
<name>credentials</name>
<type>HASH</type>
<documentation>
<purpose>Reference to an associative array variable with all the
credentials that are being requested. The function initializes
this associative array values.</purpose>
</documentation>
</argument>
<argument>
<name>defaults</name>
<type>HASH</type>
<documentation>
<purpose>Associative arrays with default values for credentials
that may have not been defined.</purpose>
</documentation>
</argument>
<argument>
<name>interactions</name>
<type>ARRAY</type>
<documentation>
<purpose>Not yet in use. It is meant to provide context
information to retrieve credentials that may be obtained
interacting with the user.</purpose>
</documentation>
</argument>
<do>
{/metadocument}
*/
Function GetCredentials(&$credentials,$defaults,&$interactions)
{
Reset($credentials);
$end=(GetType($key=Key($credentials))!="string");
for(;!$end;)
{
if(!IsSet($this->credentials[$key]))
{
if(IsSet($defaults[$key]))
$credentials[$key]=$defaults[$key];
else
{
$this->error="the requested credential ".$key." is not defined";
return(SASL_NOMECH);
}
}
else
$credentials[$key]=$this->credentials[$key];
Next($credentials);
$end=(GetType($key=Key($credentials))!="string");
}
return(SASL_CONTINUE);
}
/*
{metadocument}
</do>
</function>
{/metadocument}
*/
/*
{metadocument}
<function>
<name>Start</name>
<type>INTEGER</type>
<documentation>
<purpose>Process the initial authentication step initializing the
driver class that implements the first of the list of requested
mechanisms that is supported by this SASL client library
implementation.</purpose>
<usage>Call this function specifying a list of mechanisms that the
server supports. If the <argumentlink>
<argument>message</argument>
<function>Start</function>
</argumentlink> argument returns a string, it should be sent to
the server as initial message. Check the
<variablelink>encode_response</variablelink> variable to determine
whether the initial message needs to be encoded, eventually with
base64 algorithm, before it is sent to the server.</usage>
<returnvalue>The function may return <tt>SASL_CONTINUE</tt> if it
could start one of the requested authentication mechanisms. It
may return <tt>SASL_NOMECH</tt> if it was not possible to start
any of the requested mechanisms. It returns <tt>SASL_FAIL</tt> or
other value in case of error.</returnvalue>
</documentation>
<argument>
<name>mechanisms</name>
<type>ARRAY</type>
<inout />
<documentation>
<purpose>Define the list of names of authentication mechanisms
supported by the that should be tried.</purpose>
</documentation>
</argument>
<argument>
<name>message</name>
<type>STRING</type>
<out />
<documentation>
<purpose>Return the initial message that should be sent to the
server to start the authentication dialog. If this value is
undefined, no message should be sent to the server.</purpose>
</documentation>
</argument>
<argument>
<name>interactions</name>
<type>ARRAY</type>
<documentation>
<purpose>Not yet in use. It is meant to provide context
information to interact with the end user.</purpose>
</documentation>
</argument>
<do>
{/metadocument}
*/
Function Start($mechanisms, &$message, &$interactions)
{
if(strlen($this->error))
return(SASL_FAIL);
if(IsSet($this->driver))
return($this->driver->Start($this,$message,$interactions));
$no_mechanism_error="";
for($m=0;$m<count($mechanisms);$m++)
{
$mechanism=$mechanisms[$m];
if(IsSet($this->drivers[$mechanism]))
{
if(!class_exists($this->drivers[$mechanism][0]))
require(dirname(__FILE__)."/".$this->drivers[$mechanism][1]);
$this->driver=new $this->drivers[$mechanism][0];
if($this->driver->Initialize($this))
{
$this->encode_response=1;
$status=$this->driver->Start($this,$message,$interactions);
switch($status)
{
case SASL_NOMECH:
Unset($this->driver);
if(strlen($no_mechanism_error)==0)
$no_mechanism_error=$this->error;
$this->error="";
break;
case SASL_CONTINUE:
$this->mechanism=$mechanism;
return($status);
default:
Unset($this->driver);
$this->error="";
return($status);
}
}
else
{
Unset($this->driver);
if(strlen($no_mechanism_error)==0)
$no_mechanism_error=$this->error;
$this->error="";
}
}
}
$this->error=(strlen($no_mechanism_error) ? $no_mechanism_error : "it was not requested any of the authentication mechanisms that are supported");
return(SASL_NOMECH);
}
/*
{metadocument}
</do>
</function>
{/metadocument}
*/
/*
{metadocument}
<function>
<name>Step</name>
<type>INTEGER</type>
<documentation>
<purpose>Process the authentication steps after the initial step,
until the authetication iteration dialog is complete.</purpose>
<usage>Call this function iteratively after a successful initial
step calling the <functionlink>Start</functionlink> function.</usage>
<returnvalue>The function returns <tt>SASL_CONTINUE</tt> if step was
processed successfully, or returns <tt>SASL_FAIL</tt> in case of
error.</returnvalue>
</documentation>
<argument>
<name>response</name>
<type>STRING</type>
<in />
<documentation>
<purpose>Pass the response returned by the server to the previous
step.</purpose>
</documentation>
</argument>
<argument>
<name>message</name>
<type>STRING</type>
<out />
<documentation>
<purpose>Return the message that should be sent to the server to
continue the authentication dialog. If this value is undefined,
no message should be sent to the server.</purpose>
</documentation>
</argument>
<argument>
<name>interactions</name>
<type>ARRAY</type>
<documentation>
<purpose>Not yet in use. It is meant to provide context
information to interact with the end user.</purpose>
</documentation>
</argument>
<do>
{/metadocument}
*/
Function Step($response, &$message, &$interactions)
{
if(strlen($this->error))
return(SASL_FAIL);
return($this->driver->Step($this,$response,$message,$interactions));
}
/*
{metadocument}
</do>
</function>
{/metadocument}
*/
};
/*
{metadocument}
</class>
{/metadocument}
*/
?>

File diff suppressed because it is too large Load diff

View file

@ -1,803 +0,0 @@
<?php
/*
* smtp_message.php
*
* @(#) $Header: /opt2/ena/metal/mimemessage/smtp_message.php,v 1.36 2011/03/09 07:48:52 mlemos Exp $
*
*
*/
/**
* @horst, 19.04.2019:
* added support for: smtp_tls_crypto_method
*
*
*/
/*
{metadocument}<?xml version="1.0" encoding="ISO-8859-1"?>
<class>
<package>net.manuellemos.mimemessage</package>
<name>smtp_message_class</name>
<version>@(#) $Id: smtp_message.php,v 1.36 2011/03/09 07:48:52 mlemos Exp $</version>
<copyright>Copyright © (C) Manuel Lemos 1999-2004</copyright>
<title>MIME E-mail message composing and sending via SMTP</title>
<author>Manuel Lemos</author>
<authoraddress>mlemos-at-acm.org</authoraddress>
<documentation>
<idiom>en</idiom>
<purpose>Implement an alternative message delivery method via SMTP
protocol, overriding the method of using the PHP <tt>mail()</tt>
function implemented by the base class.</purpose>
<usage>This class should be used exactly the same way as the base
class for composing and sending messages. Just create a new object of
this class as follows and set only the necessary variables to
configure details of the SMTP delivery.<paragraphbreak />
<tt>require('email_message.php');<br />
require('smtp.php');<br />
require('smtp_message.php');<br />
<br />
$message_object = new smtp_message_class;<br /></tt><paragraphbreak />
<b>- Requirements</b><paragraphbreak />
You need the <link>
<data>SMTP E-mail sending class</data>
<url>http://freshmeat.net/projects/smtpclass/</url>
</link> to perform the actual message delivery via the SMTP
protocol.<paragraphbreak />
<b>- SMTP connection</b><paragraphbreak />
Before sending a message by relaying it to a given SMTP server you
need set the <variablelink>smtp_host</variablelink> variable to that
server address. The <variablelink>localhost</variablelink> variable
needs to be set to the sending computer address.<paragraphbreak />
You may also adjust the time the class will wait for establishing
a connection by changing the <variablelink>timeout</variablelink>
variable.<paragraphbreak />
<b>- Secure SMTP connections with SSL</b><paragraphbreak />
Some SMTP servers, like for instance Gmail, require secure
connections via SSL. In that case it is necessary to set the
<variablelink>smtp_ssl</variablelink> variable to
<booleanvalue>1</booleanvalue>. In the case of Gmail, it is also
necessary to set the connection port changing the
<variablelink>smtp_port</variablelink> variable to
<integervalue>465</integervalue>.<paragraphbreak />
SSL support requires at least PHP 4.3.0 with OpenSSL extension
enabled.<paragraphbreak />
<b>- Secure SMTP connections starting TLS after connections is established</b><paragraphbreak />
Some SMTP servers, like for instance Hotmail, require starting the
TLS protocol after the connection is already established to exchange
data securely. In that case it is necessary to set the
<variablelink>smtp_start_tls</variablelink> variable to
<booleanvalue>1</booleanvalue>.<paragraphbreak />
Starting TLS protocol on an already established connection requires
at least PHP 5.1.0 with OpenSSL extension enabled.<paragraphbreak />
<b>- Authentication</b><paragraphbreak />
Most servers only allow relaying messages sent by authorized
users. If the SMTP server that you want to use requires
authentication, you need to set the variables
<variablelink>smtp_user</variablelink>,
<variablelink>smtp_realm</variablelink> and
<variablelink>smtp_password</variablelink>.<paragraphbreak />
The way these values need to be set depends on the server. Usually
the realm value is empty and only the user and password need to be
set. If the server requires authentication via <tt>NTLM</tt>
mechanism (Windows or Samba), you need to set the
<variablelink>smtp_realm</variablelink> to the Windows domain name
and also set the variable
<variablelink>smtp_workstation</variablelink> to the user workstation
name.<paragraphbreak />
Some servers require that the authentication be done on a separate
server using the POP3 protocol before connecting to the SMTP server.
In this case you need to specify the address of the POP3 server
setting the <variablelink>smtp_pop3_auth_host</variablelink>
variable.<paragraphbreak />
<b>- Sending urgent messages with direct delivery</b><paragraphbreak />
If you need to send urgent messages or obtain immediate confirmation
that a message is accepted by the recipient SMTP server, you can use
the direct delivery mode setting the
<variablelink>direct_delivery</variablelink> variable to
<tt><booleanvalue>1</booleanvalue></tt>. This mode can be used to
send a message to only one recipient.<paragraphbreak />
To use this mode, it is necessary to have a way to determine the
recipient domain SMTP server address. The class uses the PHP
<tt>getmxrr()</tt> function, but on some systems like for instance
under Windows, this function does not work. In this case you may
specify an equivalent alternative by setting the
<variablelink>smtp_getmxrr</variablelink> variable. See the SMTP
class page for available alternatives.<paragraphbreak />
<b>- Troubleshooting and debugging</b><paragraphbreak />
If for some reason the delivery via SMTP is not working and the error
messages are not self-explanatory, you may set the
<variablelink>smtp_debug</variablelink> to
<tt><booleanvalue>1</booleanvalue></tt> to make the class output the
SMTP protocol dialog with the server. If you want to display this
dialog properly formatted in an HTML page, also set the
<variablelink>smtp_debug</variablelink> to
<tt><booleanvalue>1</booleanvalue></tt>.<paragraphbreak />
<b>- Optimizing the delivery of messages to many recipients</b><paragraphbreak />
When sending messages to many recipients, this class can hinted to
optimize its behavior by using the
<functionlink>SetBulkMail</functionlink> function. After calling this
function passing <booleanvalue>1</booleanvalue> to the <argumentlink>
<function>SetBulkMail</function>
<argument>on</argument>
</argumentlink> argument, when the message is sent this class opens
a TCP connection to the SMTP server but will not close it. This
avoids the overhead of opening and closing connections.<paragraphbreak />
When the delivery of the messages to all recipients is done, the
connection may be closed implicitly by calling the
<functionlink>SetBulkMail</functionlink> function again passing
<booleanvalue>0</booleanvalue> to the <argumentlink>
<function>SetBulkMail</function>
<argument>on</argument>
</argumentlink> argument.</usage>
</documentation>
{/metadocument}
*/
class smtp_message_class extends email_message_class
{
/* Private variables */
var $smtp;
var $line_break="\r\n";
var $delivery = 0;
/* Public variables */
/* Allow Self Signed Certificate */
var $smtp_certificate = 0; // @flydev: https://processwire.com/talk/topic/5704-wiremailsmtp/page-5#entry113290
/* @horst: Allow Connections without Authentication */
var $allow_without_authentication = 0;
/* @horst: Allow to define the crypto method for TLS connections */
var $smtp_tls_crypto_method = '';
/* @horst: Allow to define the crypto method for SSL connections */
var $smtp_ssl_crypto_method = '';
/*
{metadocument}
<variable>
<name>localhost</name>
<value></value>
<documentation>
<purpose>Specify the domain name of the computer sending the
message.</purpose>
<usage>This value is used to identify the sending machine to the
SMTP server. When using the direct delivery mode, if this variable
is set to a non-empty string it used to generate the
<tt>Recieved</tt> header to show that the message passed by the
specified host address. To prevent confusing directly delivered
messages with spam, it is strongly recommended that you set this
variable to you server host name.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $localhost="";
/*
{metadocument}
<variable>
<name>smtp_host</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the address of the SMTP server.</purpose>
<usage>Set to the address of the SMTP server that will relay the
messages. This variable is not used in direct delivery mode.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_host="localhost";
/*
{metadocument}
<variable>
<name>smtp_port</name>
<type>INTEGER</type>
<value>25</value>
<documentation>
<purpose>Specify the TCP/IP port of SMTP server to connect.</purpose>
<usage>Most servers work on port 25 . Certain e-mail services use
alternative ports to avoid firewall blocking. Gmail uses port
<integervalue>465</integervalue>.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_port=25;
/*
{metadocument}
<variable>
<name>smtp_ssl</name>
<type>BOOLEAN</type>
<value>0</value>
<documentation>
<purpose>Specify whether it should use secure connections with SSL
to connect to the SMTP server.</purpose>
<usage>Certain e-mail services like Gmail require SSL connections.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_ssl=0;
/*
{metadocument}
<variable>
<name>smtp_start_tls</name>
<type>BOOLEAN</type>
<value>0</value>
<documentation>
<purpose>Specify whether it should use secure connections starting
TLS protocol after connecting to the SMTP server.</purpose>
<usage>Certain e-mail services like Hotmail require starting TLS
protocol after the connection to the SMTP server is already
established.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_start_tls=0;
/*
{metadocument}
<variable>
<name>smtp_http_proxy_host_name</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify name of the host when the connection should be
routed via an HTTP proxy.</purpose>
<usage>Leave empty if no proxy should be used.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_http_proxy_host_name='';
/*
{metadocument}
<variable>
<name>smtp_http_proxy_host_port</name>
<type>INTEGER</type>
<value>3128</value>
<documentation>
<purpose>Specify proxy port when the connection should be routed via
an HTTP proxy.</purpose>
<usage>Change this variable if you need to use a proxy with a
specific port.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_http_proxy_host_port=3128;
/*
{metadocument}
<variable>
<name>smtp_socks_host_name</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify name of the host when the connection should be
routed via a SOCKS protocol proxy.</purpose>
<usage>Leave empty if no proxy should be used.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_socks_host_name = '';
/*
{metadocument}
<variable>
<name>smtp_socks_host_port</name>
<type>INTEGER</type>
<value>1080</value>
<documentation>
<purpose>Specify proxy port when the connection should be routed via
a SOCKS protocol proxy.</purpose>
<usage>Change this variable if you need to use a proxy with a
specific port.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_socks_host_port = 1080;
/*
{metadocument}
<variable>
<name>smtp_socks_version</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify protocol version when the connection should be
routed via a SOCKS protocol proxy.</purpose>
<usage>Change this variable if you need to use a proxy with a
specific SOCKS protocol version.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_socks_version = '5';
/*
{metadocument}
<variable>
<name>smtp_direct_delivery</name>
<type>BOOLEAN</type>
<value>0</value>
<documentation>
<purpose>Boolean flag that indicates whether the message should be
sent in direct delivery mode.</purpose>
<usage>Set this to <tt><booleanvalue>1</booleanvalue></tt> if you
want to send urgent messages directly to the recipient domain SMTP
server.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_direct_delivery=0;
/*
{metadocument}
<variable>
<name>smtp_getmxrr</name>
<type>STRING</type>
<value>getmxrr</value>
<documentation>
<purpose>Specify the name of the function that is called to determine
the SMTP server address of a given domain.</purpose>
<usage>Change this to a working replacement of the PHP
<tt>getmxrr()</tt> function if this is not working in your system
and you want to send messages in direct delivery mode.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_getmxrr="getmxrr";
/*
{metadocument}
<variable>
<name>smtp_exclude_address</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify an address that should be considered invalid
when resolving host name addresses.</purpose>
<usage>In some networks any domain name that does not exist is
resolved as a sub-domain of the default local domain. If the DNS is
configured in such way that it always resolves any sub-domain of
the default local domain to a given address, it is hard to
determine whether a given domain does not exist.<paragraphbreak />
If your network is configured this way, you may set this variable
to the address that all sub-domains of the default local domain
resolves, so the class can assume that such address is invalid.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_exclude_address="";
/*
{metadocument}
<variable>
<name>smtp_user</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the user name for authentication.</purpose>
<usage>Set this variable if you need to authenticate before sending
a message.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_user="";
/*
{metadocument}
<variable>
<name>smtp_realm</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the user authentication realm.</purpose>
<usage>Set this variable if you need to authenticate before sending
a message.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_realm="";
/*
{metadocument}
<variable>
<name>smtp_workstation</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the user authentication workstation needed when
using the <tt>NTLM</tt> authentication (Windows or Samba).</purpose>
<usage>Set this variable if you need to authenticate before sending
a message.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_workstation="";
/*
{metadocument}
<variable>
<name>smtp_authentication_mechanism</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the user authentication mechanism that should be
used when authenticating with the SMTP server.</purpose>
<usage>Set this variable if you need to force the SMTP connection to
authenticate with a specific authentication mechanism. Leave this
variable with an empty string if you want the authentication
mechanism be determined automatically from the list of mechanisms
supported by the server.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_authentication_mechanism="";
/*
{metadocument}
<variable>
<name>smtp_password</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the user authentication password.</purpose>
<usage>Set this variable if you need to authenticate before sending
a message.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_password="";
/*
{metadocument}
<variable>
<name>smtp_pop3_auth_host</name>
<type>STRING</type>
<value></value>
<documentation>
<purpose>Specify the server address for POP3 based authentication.</purpose>
<usage>Set this variable to the address of the POP3 server if the
SMTP server requires POP3 based authentication.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_pop3_auth_host="";
/*
{metadocument}
<variable>
<name>smtp_debug</name>
<type>BOOLEAN</type>
<value>0</value>
<documentation>
<purpose>Specify whether it is necessary to output SMTP connection
debug information.</purpose>
<usage>Set this variable to
<tt><booleanvalue>1</booleanvalue></tt> if you need to see
the progress of the SMTP connection and protocol dialog when you
need to understand the reason for delivery problems.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_debug=0;
/*
{metadocument}
<variable>
<name>smtp_html_debug</name>
<type>BOOLEAN</type>
<value>0</value>
<documentation>
<purpose>Specify whether the debug information should be outputted in
HTML format.</purpose>
<usage>Set this variable to
<tt><booleanvalue>1</booleanvalue></tt> if you need to see
the debug output in a Web page.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $smtp_html_debug=0;
/*
{metadocument}
<variable>
<name>esmtp</name>
<type>BOOLEAN</type>
<value>1</value>
<documentation>
<purpose>Specify whether the class should try to use Enhanced SMTP
protocol features.</purpose>
<usage>It is recommended to leave this variable set to
<tt><booleanvalue>1</booleanvalue></tt> so the class can take
advantage of Enhanced SMTP protocol features.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $esmtp=1;
/*
{metadocument}
<variable>
<name>timeout</name>
<type>INTEGER</type>
<value>25</value>
<documentation>
<purpose>Specify the connection timeout period in seconds.</purpose>
<usage>Change this value if for some reason the timeout period seems
insufficient or otherwise it seems too long.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $timeout=25;
/*
{metadocument}
<variable>
<name>invalid_recipients</name>
<type>ARRAY</type>
<value></value>
<documentation>
<purpose>Return the list of recipient addresses that were not
accepted by the SMTP server.</purpose>
<usage>Check this variable after attempting to send a message to
figure whether there were any recipients that were rejected by the
SMTP server.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $invalid_recipients=array();
/*
{metadocument}
<variable>
<name>mailer_delivery</name>
<value>smtp $Revision: 1.36 $</value>
<documentation>
<purpose>Specify the text that is used to identify the mail
delivery class or sub-class. This text is appended to the
<tt>X-Mailer</tt> header text defined by the
mailer variable.</purpose>
<usage>Do not change this variable.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $mailer_delivery='smtp $Revision: 1.36 $';
/*
{metadocument}
<variable>
<name>maximum_bulk_deliveries</name>
<type>INTEGER</type>
<value>100</value>
<documentation>
<purpose>Specify the number of consecutive bulk mail deliveries
without disconnecting.</purpose>
<usage>Lower this value if you have enabled the bulk mail mode but
the SMTP server does not accept sending more than a number of
messages within the same SMTP connection.<paragraphbreak />
Set this value to <integervalue>0</integervalue> to never
disconnect during bulk mail mode unless an error occurs.</usage>
</documentation>
</variable>
{/metadocument}
*/
var $maximum_bulk_deliveries=100;
Function SetRecipients(&$recipients,&$valid_recipients)
{
for($valid_recipients=$recipient=0,Reset($recipients);$recipient<count($recipients);Next($recipients),$recipient++)
{
$address=Key($recipients);
if($this->smtp->SetRecipient($address))
$valid_recipients++;
else
$this->invalid_recipients[$address]=$this->smtp->error;
}
return(1);
}
Function ResetConnection($error)
{
if(IsSet($this->smtp))
{
if(!$this->smtp->Disconnect()
&& strlen($error) == 0)
$error = $this->smtp->error;
UnSet($this->smtp);
}
if(strlen($error))
$this->OutputError($error);
return($error);
}
Function StartSendingMessage()
{
if(function_exists("class_exists")
&& !class_exists("smtp_class"))
return("the smtp_class class was not included");
if(IsSet($this->smtp))
return("");
$this->smtp=new smtp_class;
$this->smtp->localhost=$this->localhost;
$this->smtp->host_name=$this->smtp_host;
$this->smtp->host_port=$this->smtp_port;
$this->smtp->ssl=$this->smtp_ssl;
$this->smtp->smtp_ssl_crypto_method=$this->smtp_ssl_crypto_method; // @horst
$this->smtp->start_tls=$this->smtp_start_tls;
$this->smtp->smtp_tls_crypto_method=$this->smtp_tls_crypto_method; // @horst
$this->smtp->http_proxy_host_name=$this->smtp_http_proxy_host_name;
$this->smtp->http_proxy_host_port=$this->smtp_http_proxy_host_port;
$this->smtp->socks_host_name=$this->smtp_socks_host_name;
$this->smtp->socks_host_port=$this->smtp_socks_host_port;
$this->smtp->socks_version=$this->smtp_socks_version;
$this->smtp->timeout=$this->timeout;
$this->smtp->debug=$this->smtp_debug;
$this->smtp->html_debug=$this->smtp_html_debug;
$this->smtp->direct_delivery=$this->smtp_direct_delivery;
$this->smtp->getmxrr=$this->smtp_getmxrr;
$this->smtp->exclude_address=$this->smtp_exclude_address;
$this->smtp->pop3_auth_host=$this->smtp_pop3_auth_host;
$this->smtp->user=$this->smtp_user;
$this->smtp->realm=$this->smtp_realm;
$this->smtp->workstation=$this->smtp_workstation;
$this->smtp->authentication_mechanism=$this->smtp_authentication_mechanism;
$this->smtp->password=$this->smtp_password;
$this->smtp->esmtp=$this->esmtp;
$this->smtp->smtp_certificate = $this->smtp_certificate; // @flydev: https://processwire.com/talk/topic/5704-wiremailsmtp/page-5#entry113290
$this->smtp->allow_without_authentication = $this->allow_without_authentication; // @horst
if($this->smtp->Connect())
{
$this->delivery = 0;
return("");
}
return($this->ResetConnection($this->smtp->error));
}
Function SendMessageHeaders($headers)
{
$header_data="";
$date=date("D, d M Y H:i:s T");
if($this->smtp_direct_delivery
&& strlen($this->localhost))
{
$local_ip=gethostbyname($this->localhost);
$header_data.=$this->FormatHeader("Received","FROM ".$this->localhost." ([".$local_ip."]) BY ".$this->localhost." ([".$local_ip."]) WITH SMTP; ".$date)."\r\n";
}
for($message_id_set=$date_set=0,$header=0,$return_path=$from=$to=$recipients=array(),Reset($headers);$header<count($headers);$header++,Next($headers))
{
$header_name=Key($headers);
switch(strtolower($header_name))
{
case "return-path":
$return_path[$headers[$header_name]]=1;
break;
case "from":
$error=$this->GetRFC822Addresses($headers[$header_name],$from);
break;
case "to":
$error=$this->GetRFC822Addresses($headers[$header_name],$to);
break;
case "cc":
case "bcc":
$this->GetRFC822Addresses($headers[$header_name],$recipients);
break;
case "date":
$date_set=1;
break;
case "message-id":
$message_id_set=1;
break;
}
if(strcmp($error,""))
return($this->ResetConnection($error));
if(strtolower($header_name)=="bcc")
continue;
$header_data.=$this->FormatHeader($header_name,$headers[$header_name])."\r\n";
}
if(count($from)==0)
return($this->ResetConnection("it was not specified a valid From header"));
Reset($return_path);
Reset($from);
$this->invalid_recipients=array();
if(!$this->smtp->MailFrom(count($return_path) ? Key($return_path) : Key($from)))
return($this->ResetConnection($this->smtp->error));
$r = 0;
if(count($to))
{
if(!$this->SetRecipients($to,$valid_recipients))
return($this->ResetConnection($this->smtp->error));
$r += $valid_recipients;
}
if(!$date_set)
$header_data.="Date: ".$date."\r\n";
if(!$message_id_set
&& $this->auto_message_id)
{
$sender=(count($return_path) ? Key($return_path) : Key($from));
$header_data.=$this->GenerateMessageID($sender)."\r\n";
}
if(count($recipients))
{
if(!$this->SetRecipients($recipients,$valid_recipients))
return($this->ResetConnection($this->smtp->error));
$r += $valid_recipients;
}
if($r==0)
return($this->ResetConnection("it were not specified any valid recipients"));
if(!$this->smtp->StartData()
|| !$this->smtp->SendData($header_data."\r\n"))
return($this->ResetConnection($this->smtp->error));
return("");
}
Function SendMessageBody($data)
{
return($this->smtp->SendData($this->smtp->PrepareData($data)) ? "" : $this->ResetConnection($this->smtp->error));
}
Function EndSendingMessage()
{
return($this->smtp->EndSendingData() ? "" : $this->ResetConnection($this->smtp->error));
}
Function StopSendingMessage()
{
++$this->delivery;
if($this->bulk_mail
&& !$this->smtp_direct_delivery
&& ($this->maximum_bulk_deliveries == 0
|| $this->delivery < $this->maximum_bulk_deliveries))
return("");
return($this->ResetConnection(''));
}
Function ChangeBulkMail($on)
{
if($on
|| !IsSet($this->smtp))
return(1);
return($this->smtp->Disconnect() ? "" : $this->ResetConnection($this->smtp->error));
}
};
/*
{metadocument}
</class>
{/metadocument}
*/
?>

View file

@ -8,7 +8,7 @@
* @copyright © 2017 Christoph Thelen
* @license Licensed under GNU/GPL v3
* @link https://processwire.com/talk/topic/...
* @version 1.2.0
* @version 1.2.2
*
*
* @since 1.0.1 2017/07/05 - better validation, spectrum options modifiable
@ -31,6 +31,8 @@
* @since 1.1.8 2023/07/17 added output format option: array([0,255], [0,255], [0,255]) indexed array: H,S,L
* @since 1.1.9 2023/10/03 update sanitizeValue() formatColorString()
* @since 1.2.0 2024/03/27 fixed PHP 8.1 deprecation warning on strlen()
* @since 1.2.1 2024/06/08 fixed PHP 8.1 deprecation warning hexdec()
* @since 1.2.2 2024/07/16 made functions hookable: sleepValue(), wakeupValue()
*
*
* made for ProcessWire 3.x by Ryan Cramer
@ -43,10 +45,11 @@ class FieldtypeColor extends Fieldtype {
public static function getModuleInfo() {
return array(
'title' => 'Color',
'version' => 120,
'version' => 122,
'summary' => 'Field that stores a color value as 32bit integer reflecting a RGBA value. Many options for Input (HTML5 Inputfield Color, Textfield with changing background, various jQuery/JS ColorPickers, custom jQuery/JS/CSS) and Output (RGB, RGBA, HSL, HSLA, HEX, Array).',
'installs' => 'InputfieldColor',
'href' => 'https://processwire.com/talk/topic/16679-fieldtypecolor/'
'href' => 'https://processwire.com/talk/topic/16679-fieldtypecolor/',
'requires' => 'PHP>=7.2.0'
);
}
@ -81,11 +84,11 @@ class FieldtypeColor extends Fieldtype {
else throw New WireException('Expecting Hex color string (length 6 or 8 digits) with optional leading \'#\'');
}
public function sleepValue(Page $page, Field $field, $value) {
return hexdec($value);
public function ___sleepValue(Page $page, Field $field, $value) {
return hexdec($value ?? '');
}
public function wakeupValue(Page $page, Field $field, $value) {
public function ___wakeupValue(Page $page, Field $field, $value) {
if (!$value) return $value;
if (function_exists("bcmod")) return str_pad(self::bcdechex($value), 8, '0', STR_PAD_LEFT); // BCMath extension required
return str_pad(dechex($value), 8, '0', STR_PAD_LEFT); // 64-bit system required

View file

@ -0,0 +1,391 @@
<?php
/**
* Image Rasterizer Module
*
* @author Adrian Jones
*
* ProcessWire 2.x
* Copyright (C) 2010 by Ryan Cramer
* Licensed under GNU/GPL v2, see LICENSE.TXT
*
* http://www.processwire.com
* http://www.ryancramer.com
*
*/
class ImageRasterizer extends WireData implements Module, ConfigurableModule {
/**
* getModuleInfo is a module required by all modules to tell ProcessWire about them
*
* @return array
*
*/
public static function getModuleInfo() {
return array(
'title' => 'ImageRasterizer',
'version' => '0.2.4',
'summary' => 'Admin and front-end resizing and rasterizing of vector SVG images',
'href' => 'http://modules.processwire.com/modules/image-rasterizer/',
'singular' => true,
'autoload' => true,
'icon' => 'file-image-o'
);
}
protected static $configDefaults = array(
// global
"rasterizedImagesField" => "same",
"rasterDimensions" => "",
"format" => "png",
"image_type" => 7,
"image_depth" => 8,
"jpg_compression" => "90",
"jpg_background_color" => "#FFFFFF",
"png_background_color" => "#FFFFFF"
);
/**
* Data as used by the get/set functions
*
*/
protected $data = array();
protected $thumbWidth = 0;
protected $thumbHeight = 100;
/**
* Initialize the module
*
*/
public function init() {
}
public function ready() {
if($this->page->template == 'admin'){
$this->addHook('Pageimage::isVariation', $this, 'isVariationWithRasterizer');
$this->addHookBefore('InputfieldFile::fileAdded', $this, 'rasterizeImage');
if($this->rasterizedImagesField == 'replace') {
$this->addHookAfter('InputfieldImage::renderItem', $this, 'rasterizeThumb');
}
}
else{
$this->addHook('Pageimage::rasterize', $this, 'rasterizeImage');
}
}
public function rasterizeThumb(HookEvent $event){
$this->thumbWidth = $this->config->adminThumbOptions['width'] ? $this->config->adminThumbOptions['width'] : $this->thumbWidth;
$this->thumbHeight = $this->config->adminThumbOptions['height'] ? $this->config->adminThumbOptions['height'] : $this->thumbHeight;
$dom = new DOMDocument();
libxml_use_internal_errors(true); //hide any errors that relate to invalid HTML in the textarea code
$dom->loadHTML(mb_convert_encoding($event->return, 'HTML-ENTITIES', 'UTF-8'));
foreach($dom->getElementsByTagName('img') as $img) {
$fullFilename = $img->getAttribute('src');
if(strpos(pathinfo($fullFilename, PATHINFO_EXTENSION), 'svg') !== FALSE) {
$this->rasterizeImage($event);
$img->setAttribute('src', str_replace(".svg", ".".$this->thumbWidth."x".$this->thumbHeight.".".$this->format, $fullFilename));
}
}
$event->return = $dom->saveHTML();
}
public function rasterizeImage(HookEvent $event){
if($this->page->template == 'admin'){
$image = $event->argumentsByName("pagefile");
$fieldname = $event->object->name;
}
else{ //must be a front-end call from rasterize()
$image = $event->object;
$fieldname = $image->field;
}
// get actual fieldname if it's a repeater field
if (strpos($fieldname, '_repeater') !== false) $fieldname = strstr($fieldname, '_repeater', true);
if(pathinfo($image->filename, PATHINFO_EXTENSION) != 'svg') return; // leave now if we are not dealing with an SVG file
// these are the values sent when using rasterize(w,h)
if($this->page->template != 'admin'){
$rasterizeWidth = $event->arguments(0);
$rasterizeHeight = $event->arguments(1);
}
elseif($this->page->template == 'admin' && $this->rasterizedImagesField == 'replace'){
$rasterizeWidth = $this->thumbWidth;
$rasterizeHeight = $this->thumbHeight;
}
if(($this->page->template == 'admin' && $this->rasterizedImagesField != 'replace') || (!isset($rasterizeWidth) && !isset($rasterizeHeight))){
$new_img_path = str_replace('.svg', '.'.$this->format, $image->filename);
}
else{
$new_img_path = str_replace('.svg', '.'.$rasterizeWidth.'x'.$rasterizeHeight.'.'.$this->format, $image->filename);
}
if(!$this->page->$fieldname) { //if the current page does not contain the image field - eg an ajax called script
$pathSegments = explode('/', $new_img_path);
$pageId = (int) $pathSegments[count($pathSegments)-2];
$imagePage = $this->pages->get($pageId);
}
else {
$imagePage = $this->page;
}
//various checks to stop this module from starting the rasterize process
if(file_exists($new_img_path)){
$new_img = new Pageimage($imagePage->$fieldname, $new_img_path);
$event->return = $new_img;
return; //if rasterized variation already exists, return it now
}
if($this->rasterizedImagesField == 'none' && $this->page->template == 'admin') return;
if($this->rasterizedImagesField != 'none'){
$inputfield = $this->rasterizedImagesField == 'same' || $this->rasterizedImagesField == 'replace' || $this->rasterizedImagesField == '' ? $this->fields->get($fieldname) : $this->fields->get($this->rasterizedImagesField); //set inputfield for rasterized image
if(!$inputfield) return;
if(!$inputfield->type instanceof FieldtypeImage) return;
}
//if we get this far, get SVG details, resize and rasterize
clearstatcache();
$im = new Imagick();
if($this->format == 'png'){
// http://www.php.net/manual/en/imagick.getimagetype.php - "7" is imagick::IMGTYPE_TRUECOLORMATTE
$png_background_color = $this->image_type == '7' ? new ImagickPixel("transparent") : $this->png_background_color;
$im->setBackgroundColor($png_background_color);
}
else{
$im->setBackgroundColor($this->jpg_background_color);
}
//read the image to get the existing resolution and dimensions
$im->readImage($image->filename);
$res = $im->getImageResolution();
//get initial dimensions from the SVG
$initialWidth = $im->getImageWidth();
$initialHeight = $im->getImageHeight();
//get entered dimensions from module config settings
$rasterDimensions = '';
if($this->rasterDimensions != '') $rasterDimensions = explode(",", preg_replace('/\s+/', '', $this->rasterDimensions));
//set new dimensions to those in the module config settings, or if not set, then to the original dimensions of the SVG
$newWidth = $rasterDimensions ? $rasterDimensions[0] : $initialWidth;
$newHeight = $rasterDimensions ? $rasterDimensions[1] : $initialHeight;
if($this->page->template != 'admin' || $this->rasterizedImagesField == 'replace'){ //if front-end rasterize (or replacing admin thumb), and dimensions set, override dimensions just set above
//if no dimensions specified in rasterize(), use the ones entered in the module config settings or revert to initial dimensions
if(isset($rasterizeWidth)) $newWidth = $rasterizeWidth;
if(isset($rasterizeHeight)) $newHeight = $rasterizeHeight;
}
// if one of the dimensions is set to 0 (which it should be), then calculate the other dimension, otherwise just squish the image. Maybe should be cropping instead, but this could be handled by using a PW ->size() on the newly created PNG.
if($newWidth == 0 || $newHeight == 0){
if($newWidth > $newHeight){
$newHeight = round($newWidth / $initialWidth * $initialHeight);
}
else{
$newWidth = round($newHeight / $initialHeight * $initialWidth);
}
}
// calculate the resolution required before rasterizing based on the initial dimensions and the final required dimensions
$x_res = round($res['x'] * $newWidth / $initialWidth);
$y_res = round($res['y'] * $newHeight / $initialHeight);
$im->removeImage(); // Remove the image because setResolution has to be called before readImage because the image gets rasterized after that, and setResolution has no effect.
$im->setResolution($x_res, $y_res);
$im->readImage($image->filename);
//rasterize
if($this->format == 'png'){
$im->setImageFormat("png");
$im->setImageDepth($this->image_depth);
$im->setImageColorSpace(imagick::COLORSPACE_RGB);
$im->setImageType($this->image_type);
//$im->setOption("png:color-type","6");
//$im->setOption("png:compression-level","9"); // 9 is highest compression and going down towards 0 just makes huge files with no obvious improvements in quality
}
else{
$im->setImageFormat("jpg");
$im->setImageCompression(imagick::COMPRESSION_JPEG);
$im->setImageCompressionQuality($this->jpg_compression);
}
clearstatcache();
$im->writeImage($new_img_path);
$im->clear();
$im->destroy();
//add rasterized version to the images field
if($this->page->template == 'admin' && $this->rasterizedImagesField != 'replace' && $this->rasterizedImagesField != 'none'){
$image_page = $this->pages->get((int) $this->input->get->id);
$image_page->$inputfield->add(str_replace('.svg', '.'.$this->format, $image->filename));
$image_page->save($inputfield);
}
//front-end, so don't add to images field, just return the rasterized version to the rasterize() method for display
else{
$new_img = new Pageimage($imagePage->$fieldname, $new_img_path);
$event->return = $new_img;
}
}
/**
* Remove any rasterized versions when deleting an SVG in the admin.
* This is for images that were created by the rasterize() method on the front-end and therefore not added to the Pageimage, hence the need for this.
*
*/
public function isVariationWithRasterizer($event) {
$pageimage = $event->object;
$variationName = basename($event->arguments[0]);
// if the result of hooked method isn't false, or if the file isn't an SVG, leave now
if(pathinfo($pageimage->filename, PATHINFO_EXTENSION) != 'svg' || false!==$event->return) return $event->return;
//check to see if the variation also exists in the pageimage - in that case, return and don't remove it.
$image_page = $this->pages->get((int) $this->input->get->id);
if(count($image_page->{$pageimage->field})) {
$variation_image = $image_page->{$pageimage->field}->get("$variationName");
if($variation_image && !$variation_image->name =='') return $event->return;
}
$basename = basename($pageimage->name, '.' . $pageimage->ext);
$re = '/^' . $basename . '.*?' . '\.(gif|jpg|png)' . '$/';
if(preg_match($re, $variationName)) {
// we have a match, now return array with imageinfo
// (the following rows are taken from original method Pageimage::isVariation(), only regexp is modified)
$re2 = '/^.*?' . $basename . '\.' .
'(\d+)x(\d+)' . // 50x50
'([pd]\d+x\d+|[a-z]{1,2})?' . // nw or p30x40 or d30x40
'\.(gif|jpg|jpeg|png)' . // .ext
'$/';
preg_match($re2, $variationName, $matches);
$info = array(
'original' => $basename . '.' . $pageimage->ext,
'width' => $matches[1],
'height' => $matches[2],
'crop' => (isset($matches[3]) ? $matches[3] : '')
);
$event->return = $info;
return $event->return;
}
return false;
}
/**
* Get any inputfields used for configuration of this Fieldtype.
*
* This is in addition to any configuration fields supplied by the parent Inputfield.
*
* @param Field $field
* @return InputfieldWrapper
*
*/
public static function getModuleConfigInputfields(array $data) {
$modules = wire('modules');
foreach(self::$configDefaults as $key => $value) {
if(!isset($data[$key]) || $data[$key]=='') $data[$key] = $value;
}
$inputfields = new InputfieldWrapper();
$f = $modules->get("InputfieldSelect");
$f->attr('name', 'rasterizedImagesField');
$f->attr('value', $data["rasterizedImagesField"]);
$f->label = __('Rasterized Images Field');
$f->description = __("The field to send the rasterized images to.\n\nChoose 'Same as source image' to save them to the same images field as the vector image.\nChoose 'Replace the source image thumbnail' to replace the SVG with a rasterized version when viewing the thumbnails in the admin. This can significantly speed things up with complex SVG files.\nChoose 'None' if you don't want a rasterized version saved to the images field. NB You'll still be able to access a raster version in your templates using the rasterize() method.");
$f->addOption('same', 'Same as source image');
$f->addOption('replace', 'Replace the source image thumbnail');
$f->addOption('none', 'None');
// populate with all available fields
foreach(wire('fields') as $fieldoption) {
// filter out incompatible field types
if($fieldoption->type == "FieldtypeImage") $f->addOption($fieldoption->name);
}
$inputfields->add($f);
$f = $modules->get("InputfieldText");
$f->attr('name', 'rasterDimensions');
$f->attr('value', $data["rasterDimensions"]);
$f->attr('size', 10);
$f->label = __('Raster Dimensions');
$f->description = __('This determines dimensions of the rasterized version. Leave blank to keep same existing dimensions from the SVG.');
$f->notes = __("Width, Height. Be sure to enter 0 for one dimension to ensure proportional scaling, eg: 500,0");
$inputfields->add($f);
$f = $modules->get("InputfieldSelect");
$f->attr('name', 'format');
$f->attr('value', $data["format"]);
$f->label = __('Image Format');
$f->addOption('png');
$f->addOption('jpg');
$inputfields->add($f);
//http://www.php.net/manual/en/imagick.getimagetype.php
$f = $modules->get("InputfieldSelect");
$f->showIf = "format=png";
$f->attr('name', 'image_type');
$f->attr('value', $data["image_type"]);
$f->label = __('Color Type');
$f->addOption('7', 'True Color Alpha Transparent');
$f->addOption('6', 'True Color');
$f->addOption('4', 'Pallete');
$inputfields->add($f);
//http://www.php.net/manual/en/gmagick.setimagedepth.php
$f = $modules->get("InputfieldSelect");
$f->showIf = "format=png";
$f->attr('name', 'image_depth');
$f->attr('value', $data["image_depth"]);
$f->label = __('Image Depth');
$f->addOption('8', '8');
$f->addOption('16', '16');
$f->addOption('32', '32');
$f->notes = __("Default: 8");
$inputfields->add($f);
$f = $modules->get("InputfieldText");
$f->showIf = "format=jpg";
$f->attr('name', 'jpg_background_color');
$f->attr('value', $data["jpg_background_color"]);
$f->attr('size', 10);
$f->label = __('Background (Matte) Color');
$f->notes = __("Default: #FFFFFF");
$inputfields->add($f);
$f = $modules->get("InputfieldText");
$f->showIf = "format=png, image_type!=7";
$f->attr('name', 'png_background_color');
$f->attr('value', $data["png_background_color"]);
$f->attr('size', 10);
$f->label = __('Background (Matte) Color');
$f->notes = __("Default: #FFFFFF");
$inputfields->add($f);
$f = $modules->get("InputfieldText");
$f->showIf = "format=jpg";
$f->description = __('This determines filesize and image quality as percentage. 100 is the best quality and largest file size.');
$f->attr('name', 'jpg_compression');
$f->attr('value', $data["jpg_compression"]);
$f->attr('size', 10);
$f->label = __('JPG Compression Level');
$f->notes = __("Default: 90");
$inputfields->add($f);
return $inputfields;
}
}

View file

@ -0,0 +1,339 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc., <http://fsf.org/>
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Lesser General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
{description}
Copyright (C) {year} {fullname}
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License along
with this program; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
{signature of Ty Coon}, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Lesser General
Public License instead of this License.

View file

@ -0,0 +1,50 @@
ImageRasterizer
===============
ProcessWire module for admin and front-end resizing and rasterizing of vector SVG images
###Requirements
IMPORTANT: This module requires Imagemagick and the pecl imagick extension. For anything but simple SVGs, you must make sure imagemagick was compiled with a relatively recent version of rsvg (I know that 2.32.1 works well and presumably anything more recent should also be fine).
If you don't manage your own server and the results are not good, check with your host. If everything is set up correctly, the rendered PNGs will be "perfect" representations of the SVGs.
###How to use
You must add SVG as an allowed file type for an images field.
Check the module configuration for a variety of settings for both PNG and JPG output options.
In particular be aware of the Rasterized Images Field selector:
* If you choose "None" only the SVG will be stored in the images field. You can still access rasterized versions via the rasterize() method - see below for details.
* If you choose 'Replace the source image thumbnail' it will replace the SVG with a rasterized version when viewing the thumbnails in the admin. This can significantly speed things up with complex SVG files.
Once the module configuration settings are completed:
* Upload an SVG image and the module will create a rasterized version.
* You need to save the page to see the rasterized version which can then be accessed via the API like any other image.
* The module also adds a new method: rasterize() which can be called from your templates like:
```
$image->rasterize(200,0)->url
```
* This method optionally resizes the vector version of the image and then rasterizes it so you can scale it infinitely and there will be no loss of quality. Make sure you point it to the svg version in your images field.
####Support Forum
http://processwire.com/talk/topic/4632-image-rasterizer/
## License
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
(See included LICENSE file for full license text.)

View file

@ -0,0 +1,236 @@
<?php
/**
* ProcessWire External RSS Feed Fetch
*
* For ProcessWire 3.x
*
* @author Laegnur
*
*/
class ProcessRSSFetch extends Process
{
protected $items = null;
protected $replacements = array(
'<br />' => ' ',
'<br>' => ' ',
'</p>' => ' ',
"\n" => ' ',
"\r" => ' ',
);
public static function getModuleInfo()
{
return array(
'title' => 'ProcessWire RSS Fetch',
'summary' => 'ProcessWire External RSS Feed Fetch',
'version' => 001,
'author' => 'Laegnur',
'href' => 'https://laegnur.artabro.org/',
'icon' => 'rss'
);
}
public function ___execute()
{
$form = $this->modules->get("InputfieldForm");
$form->action = "./";
$form->method = "post";
$form->attr("id+name",'rssfetch-form');
$fieldText = $this->modules->get("InputfieldText");
$fieldText->label = "RSS feed";
$fieldText->name = 'rss';
$fieldText->description = "URL del feed RSS";
$fieldText->columnWidth = 100;
$fieldText->required = 1;
$form->append($fieldText);
$submit = $this->modules->get("InputfieldSubmit");
$submit->attr("value","Traer posts");
$submit->attr("id+name","submit");
$form->append($submit);
$out = $form->render();
if($this->input->post->submit)
{
set_time_limit(600);
$form->processInput($this->input->post);
if(!$form->getErrors())
{
$this->items = new WireArray();
$xmlData = $this->loadXmlData($this->input->post->rss);
$rss = simplexml_load_string($xmlData);
if(!$rss)
{
$msg = "Unable to load RSS feed at $url: \n";
foreach(libxml_get_errors() as $error) $msg .= $error . " \n";
$out .= $msg;
return $out;
}
foreach($rss->channel->category as $category)
{
$name = $this->sanitizer->pageNameTranslate($category);
if(($this->pages->findOne("template=etiqueta,name=$name") instanceof NullPage))
{
$t = new Page();
$t->template = 'etiqueta';
$t->parent = wire('pages')->get('/noticias/etiquetas/');
$t->name = $name;
$t->title = $category;
$t->save();
$this->log('Creada etiqueta: ' . $category, ['name' => 'rssfetch']);
}
else
{
$this->log('Etiqueta ya existente: ' . $category, ['name' => 'rssfetch']);
}
}
foreach($rss->channel->item as $item)
{
$title = '';
$date = '';
$img = '';
$content = '';
$category = array();
$tags = array();
foreach($item as $key => $value)
{
switch ($key)
{
case 'pubDate':
$date = $value;
break;
case 'title':
$title = $value;
break;
case 'description':
$content = $this->cleanText($value);
break;
case 'media:thumbnail':
$attributes = $key->attributes();
$img = $attributes['url'];
break;
case 'category':
$tags[] = $value;
break;
default:
break;
}
}
$out .= '[ '. "\n" . 'Data: ' . $date . "\n" . 'Titulo: ' . $title . "\n" . 'Contenido: ' . $content . "\n" . 'Img: ' . $img . "\n" . 'Etiquetas: ' . implode(', ', $tags) . "\n" . ']'. "\n";
/*$p = new Page();
$p->template = 'publicacion';
$p->parent = wire('pages')->get('/noticias/publicaciones/');
$p->addStatus(Page::statusUnpublished);
$p
$p->save();*/
}
}
return $out;
}
return $out;
}
public function install()
{
$page = new Page();
$page->template = "admin";
$page->name = "feed-fetch";
$page->title = "RSS Feed Fetch";
$page->save();
$page->process = 'ProcessRSSFetch';
$admin = $this->pages->get("id=2");
$page->parent = $admin;
$page->save();
}
public function uninstall()
{
$page = $this->pages->get("name=feed-fetch");
if(count($page)) $this->pages->delete($page, true);
}
/**
* Load XML data from either the RSS URL or the cache file
*
* @param string $url
* @return bool|string
*
*/
protected function loadXmlData($url)
{
$cacheFile = $this->config->paths->cache . $this->className() . '/' . md5($url) . '.xml.cache';
if(!is_file($cacheFile) || time() - filemtime($cacheFile) > 120)
{
$http = new WireHttp();
$this->wire($http);
$xmlData = $http->get($url);
if(empty($xmlData))
{
$this->error("Unable to load: $url");
return false;
}
else
{
@file_put_contents($cacheFile, $xmlData, LOCK_EX);
}
}
else
{
$xmlData = file_get_contents($cacheFile);
if($xmlData === false)
{
$this->error("Unable to load XML data cache");
return false;
}
}
return $xmlData;
}
/**
* Cleans text string from a feed before storage in our object
*
* @param string $value
* @return string
*
*/
protected function cleanText($value)
{
if(count($this->replacements))
{
$value = str_ireplace(array_keys($this->replacements), array_values($this->replacements), $value);
}
$value = trim(strip_tags($value));
if(mb_strlen($value, "UTF-8") > 2048)
{
$value = mb_substr($value, 0, 2048, "UTF-8");
}
$sanitizer = $this->wire('sanitizer');
$value = $sanitizer->unentities($value);
$value = $sanitizer->entities($value);
return $value;
}
}

View file

@ -0,0 +1,97 @@
<?php
/**
* FieldtypeAdminCustomPagesSelect
*
* This Fieldtype creates a template selector for "Admin Custom Pages".
*
* For documentation about the fields used in this class, please see:
* /wire/core/Fieldtype.php
*
* Module by Nico Knoll
*
* ProcessWire 2.x
* Copyright (C) 2010 by Ryan Cramer
* Licensed under GNU/GPL v2, see LICENSE.TXT
*
* http://www.processwire.com
* http://www.ryancramer.com
*
*/
class FieldtypeAdminCustomPagesSelect extends Fieldtype {
public static $defaultOptionValues = array ();
public static function getModuleInfo() {
return array(
'title' => 'Admin Custom Pages Select',
'version' => 100,
'summary' => __('This Fieldtype creates a template selector for "Admin Custom Pages".')
);
}
public function getInputfield(Page $page, Field $field) {
$inputfield = $this->modules->get('InputfieldSelect');
$inputfield->showIf = 'process=ProcessAdminCustomPages';
$inputfield->addOption(''); // blank or unselected option
$options = $this->getOptions();
foreach($options as $option) {
$inputfield->addOption($option['path'],$option['basename']);
}
return $inputfield;
}
private function getOptions() {
// Not sure but I think it's easier if choose the file directly instead of creating a template first
$globPath = $this->config->paths->templates;
$files = $this->rglob('*.php', 0, $globPath);
foreach($files as $file) {
$templateFiles[] = array(
'path' => str_replace(wire('config')->paths->root, '', $file), // Make path relative
'basename' => str_replace($globPath, '', $file)
);
}
return $templateFiles;
}
// recursive looking for templates
private function rglob($pattern = '*', $flags = 0, $path = '') {
$paths = @glob($path.'*', GLOB_MARK|GLOB_ONLYDIR|GLOB_NOSORT);
$files = array();
$files = @glob($path.$pattern, $flags);
foreach ($paths as $path) { $files = @array_merge((array)$files,(array)$this->rglob($pattern, $flags, $path)); }
foreach($files as $key => $file) {
if($file == '' || $file == false || !$file) {
unset($files[$key]);
}
}
return $files;
}
public function sanitizeValue(Page $page, Field $field, $value) {
return $value;
}
public function getDatabaseSchema(Field $field) {
$schema = parent::getDatabaseSchema($field);
$schema['data'] = 'text NOT NULL';
$schema['keys']['data_exact'] = 'KEY `data_exact` (`data`(255))';
$schema['keys']['data'] = 'FULLTEXT KEY `data` (`data`)';
return $schema;
}
}

View file

@ -0,0 +1,155 @@
<?php
/*
* Admin Custom Pages Module v 1.0.5
* Create custom admin pages without building a Process Module
*
* @author Diogo Oliveira
*
* @modified Nico Knoll
*
* ProcessWire 3.x
* Copyright (C) 2011 by Ryan Cramer
* Licensed under GNU/GPL v2, see LICENSE.TXT
*
* http://www.processwire.com
*
*/
class ProcessAdminCustomPages extends Process {
static public function getModuleInfo() {
return array(
'title' => 'Admin Custom Pages',
'summary' => __('Create custom admin pages without building a Process Module'),
'version' => 111,
'author' => 'Diogo Oliveira',
'permission' => 'page-view',
'installs' => array('FieldtypeAdminCustomPagesSelect'),
'requires' => array('FieldtypeAdminCustomPagesSelect')
);
}
public function init() {
parent::init();
// load script and style files for this page (expects a ACP_scripts_and_styles field with one url per line)
if ($this->page->ACP_scripts_and_styles != "") {
// get one url for each line of the field
$files = explode("\n", $this->page->ACP_scripts_and_styles);
foreach ($files as $f) {
// get the file extension
$extension = trim(substr(strrchr($f,'.'),1));
// check if url is absolute, if not concatenate it with the site root url
if (strpos($f, "http://") === false) {
$f = $this->config->urls->root . $f;
}
// load the correct type of file
switch ($extension) {
case "js":
$this->config->scripts->add($f);
break;
case "css":
$this->config->styles->add($f);
break;
}
}
}
}
public function ___execute() {
$template_file = wire('config')->paths->root . $this->page->ACP_template;
if (file_exists($template_file)) {
// only works with dev version of ProcessWire May 8 2013
return $this->page->render($template_file);
} elseif ($this->page->child->id) {
// for the current stable version use this method
// 'include=hidden' added by suggestion of Macrura and kongondo at the forum
// http://processwire.com/talk/topic/3474-admin-custom-pages-module/?p=38304
return $this->page->child('include=hidden')->render();
} else {
return $this->error(__("You have to assign a template file to this 'Admin Custom Page'."));
}
}
// install method created by Pete (https://github.com/Notanotherdotcom)
public function ___install() {
// Check if PW 2.4 or higher is installed
if(ProcessWire::versionMajor == 2 && ProcessWire::versionMinor < 4) {
throw new WireException(__("This module requires ProcessWire 2.4 or newer"));
}
// Check for existence of the field below, throw a message if it already exists
if($this->fields->get('ACP_scripts_and_styles') == NULL) {
// If it doesn't exist then carry on and create it
$field = new Field();
$field->type = $this->modules->get("FieldtypeTextarea");
$field->name = 'ACP_scripts_and_styles';
$field->label = __('Scripts and styles for admin pages');
$field->description = __('Add the .js and .css URLs in this field textarea, one in each line. can be absolute or relative (relative is assumed from the site root eg: site/templates/styles/my.css)');
$field->save();
$this->message(__("Added field 'ACP_scripts_and_styles'. Add this field to the page template of your custom admin pages when needed."));
}
if($this->fields->get('ACP_template') == NULL) {
// If it doesn't exist then carry on and create it
$field = new Field();
$field->type = $this->modules->get("FieldtypeAdminCustomPagesSelect");
$field->name = 'ACP_template';
$field->label = 'Template';
$field->description = __('Select the template which should get rendered. Templates have to be in /site/templates/.');
$field->save();
// Add field to admin template
$adminTemplate = $this->templates->get('admin');
$adminTemplate->fields->add($field);
$adminTemplate->fields->save();
$this->message(__("Added field 'ACP_template' to admin."));
}
}
public function ___uninstall() {
// Remove the select field
$adminTemplate = $this->templates->get('admin');
if($adminTemplate->fields->get('ACP_template')) {
$adminTemplate->fields->remove($adminTemplate->fields->get('ACP_template'));
$adminTemplate->fields->save();
}
// Remove ACP_template
if($this->fields->get('ACP_template')) {
$field = $this->fields->get('ACP_template');
$this->fields->delete($field);
}
// Remove ACP_scripts_and_styles
if($this->fields->get('ACP_scripts_and_styles')) {
$field = $this->fields->get('ACP_scripts_and_styles');
$this->fields->delete($field);
}
}
}

View file

@ -0,0 +1,46 @@
# Admin Custom Pages Module for ProcessWire
### Create custom admin pages easily without having to build a Process Module.
The new version of this module works only with ProcessWire 2.4 and higher.
Differences are explained bellow.
Since version 1.1.0 the installation process automatically adds a custom Fieldtype to the admin template. This creates a select field where you can choose the template file to render. This functionality was added by [Nico](http://nico.is)
☞ This module makes it easy to create simple admin pages but you can also create them in much more powerfull way without the need of a module. Have a look at this post written by Bernhard Baumrock to know how it's done https://processwire.com/blog/posts/building-custom-admin-pages-with-process-modules/
### To prepare the module:
1. Place the module folder in /site/modules/
2. Install the module in the modules page from the admin
### To create the pages:
1. Create a new page under "Admin" and give it the "admin" template. As "process" you have to choose "ProcessAdminCustomPages".
2. A field called "Template file" will appear. Select the file you want (we recommend that the file name starts with underscore "\_" so it doesn't appear in new template sugestions, ex: "\_custom.php").
3. That's all.
### To add custom script and style files to the page:
1. Add the "ACP_scripts_and_styles" to the page template (the field that was created automaticaly on instalation)
2. Add the .js and .css URLs in this field textarea, one in each line. can be absolute or relative (relative is assumed from the site root on eg: site/templates/styles/my.css)
--
### Troubleshooting:
> This page has no Process assigned.
You probably forgot to choose "ProcessCustomPages" as Process. (See step 1)
--
Module home: http://modules.processwire.com/modules/process-admin-custom-pages/
Support forum: http://processwire.com/talk/topic/3474-admin-custom-pages-module/
--
That's it! Hope you enjoy the module ;)

View file

@ -2,7 +2,7 @@
* @FONTS
* =============================================================================
*
* fonts.css v0.1.20 | GNU GPL License |
* fonts.css v0.1.23 | GNU GPL License |
*
*/
@ -17,128 +17,16 @@
6. Legacy iOS
*/
@font-face
{
font-family: 'Josefin Sans';
src: url('../fonts/Josefin_Sans_Light.eot'); /* 1 */
src: url('../fonts/Josefin_Sans_Light.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Josefin_Sans_Light.woff2') format('woff2'), /* 3 */
url('../fonts/Josefin_Sans_Light.woff') format('woff'), /* 4 */
url('../fonts/Josefin_Sans_Light.otf') format('opentype'), /* 5 */
url('../fonts/Josefin_Sans_Light.ttf') format('truetype'), /* 5 */
url('../fonts/Josefin_Sans_Light.svg#josefinsans') format('svg'); /* 6 */
font-weight: normal;
font-style: normal;
}
@font-face
{
font-family: 'Josefin Sans';
src: url('../fonts/Josefin_Sans_Light_Italic.eot'); /* 1 */
src: url('../fonts/Josefin_Sans_Light_Italic.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Josefin_Sans_Light_Italic.woff2') format('woff2'), /* 3 */
url('../fonts/Josefin_Sans_Light_Italic.woff') format('woff'), /* 4 */
url('../fonts/Josefin_Sans_Light_Italic.otf') format('opentype'), /* 5 */
url('../fonts/Josefin_Sans_Light_Italic.ttf') format('truetype'), /* 5 */
url('../fonts/Josefin_Sans_Light_Italic.svg#josefinsanst') format('svg'); /* 6 */
font-weight: normal;
font-style: italic;
}
@font-face
{
font-family: 'Josefin Sans';
src: url('../fonts/Josefin_Sans_Regular.eot'); /* 1 */
src: url('../fonts/Josefin_Sans_Regular.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Josefin_Sans_Regular.woff2') format('woff2'), /* 3 */
url('../fonts/Josefin_Sans_Regular.woff') format('woff'), /* 4 */
url('../fonts/Josefin_Sans_Regular.otf') format('opentype'), /* 5 */
url('../fonts/Josefin_Sans_Regular.ttf') format('truetype'), /* 5 */
url('../fonts/Josefin_Sans_Regular.svg#josefinsans') format('svg'); /* 6 */
font-weight: bold;
font-style: normal;
}
@font-face
{
font-family: 'Josefin Sans';
src: url('../fonts/Josefin_Sans_Reguar_Italic.eot'); /* 1 */
src: url('../fonts/Josefin_Sans_Reguar_Italic.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Josefin_Sans_Reguar_Italic.woff2') format('woff2'), /* 3 */
url('../fonts/Josefin_Sans_Reguar_Italic.woff') format('woff'), /* 4 */
url('../fonts/Josefin_Sans_Reguar_Italic.otf') format('opentype'), /* 5 */
url('../fonts/Josefin_Sans_Reguar_Italic.ttf') format('truetype'), /* 5 */
url('../fonts/Josefin_Sans_Reguar_Italic.svg#josefinsans') format('svg'); /* 6 */
font-weight: bold;
font-style: italic;
}
@font-face
{
font-family: 'Source Sans Pro';
src: url('../fonts/Source_Sans_Pro_Regular.eot'); /* 1 */
src: url('../fonts/Source_Sans_Pro_Regular.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Source_Sans_Pro_Regular.woff2') format('woff2'), /* 3 */
url('../fonts/Source_Sans_Pro_Regular.woff') format('woff'), /* 4 */
url('../fonts/Source_Sans_Pro_Regular.otf') format('opentype'), /* 5 */
url('../fonts/Source_Sans_Pro_Regular.ttf') format('truetype'), /* 5 */
url('../fonts/Source_Sans_Pro_Regular.svg#sourcesansproregular') format('svg'); /* 6 */
font-weight: normal;
font-style: normal;
}
@font-face
{
font-family: 'Source Sans Pro';
src: url('../fonts/Source_Sans_Pro_Italic.eot'); /* 1 */
src: url('../fonts/Source_Sans_Pro_Italic.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Source_Sans_Pro_Italic.woff2') format('woff2'), /* 3 */
url('../fonts/Source_Sans_Pro_Italic.woff') format('woff'), /* 4 */
url('../fonts/Source_Sans_Pro_Italic.otf') format('opentype'), /* 5 */
url('../fonts/Source_Sans_Pro_Italic.ttf') format('truetype'), /* 5 */
url('../fonts/Source_Sans_Pro_Italic.svg#sourcesansproitalic') format('svg'); /* 6 */
font-weight: normal;
font-style: italic;
}
@font-face
{
font-family: 'Source Sans Pro';
src: url('../fonts/Source_Sans_Pro_SemiBold.eot'); /* 1 */
src: url('../fonts/Source_Sans_Pro_SemiBold.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Source_Sans_Pro_SemiBold.woff2') format('woff2'), /* 3 */
url('../fonts/Source_Sans_Pro_SemiBold.woff') format('woff'), /* 4 */
url('../fonts/Source_Sans_Pro_SemiBold.otf') format('opentype'), /* 5 */
url('../fonts/Source_Sans_Pro_SemiBold.ttf') format('truetype'), /* 5 */
url('../fonts/Source_Sans_Pro_SemiBold.svg#sourcesansprosemibold') format('svg'); /* 6 */
font-weight: bold;
font-style: normal;
}
@font-face
{
font-family: 'Source Sans Pro';
src: url('../fonts/Source_Sans_Pro_SemiBold_Italic.eot'); /* 1 */
src: url('../fonts/Source_Sans_Pro_SemiBold_Italic.eot?#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/Source_Sans_Pro_SemiBold_Italic.woff2') format('woff2'), /* 3 */
url('../fonts/Source_Sans_Pro_SemiBold_Italic.woff') format('woff'), /* 4 */
url('../fonts/Source_Sans_Pro_SemiBold_Italic.otf') format('opentype'), /* 5 */
url('../fonts/Source_Sans_Pro_SemiBold_Italic.ttf') format('truetype'), /* 5 */
url('../fonts/Source_Sans_Pro_SemiBold_Italic.svg#sourcesansprobolditalic') format('svg'); /* 6 */
font-weight: bold;
font-style: italic;
}
@font-face
{
font-family: 'icomoon';
src: url('../fonts/icomoon_Regular.eot?qri1u5'); /* 1 */
src: url('../fonts/icomoon_Regular.eot?qri1u5#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/icomoon_Regular.woff2?qri1u5') format('woff2'), /* 3 */
url('../fonts/icomoon_Regular.woff?qri1u5') format('woff'), /* 4 */
url('../fonts/icomoon_Regular.otf?qri1u5') format('opentype'), /* 5 */
url('../fonts/icomoon_Regular.ttf?qri1u5') format('truetype'), /* 5 */
url('../fonts/icomoon_Regular.svg?qri1u5#icomoon') format('svg'); /* 6 */
src: url('../fonts/icomoon.eot?rwmkoy'); /* 1 */
src: url('../fonts/icomoon.eot?rwmkoy#iefix') format('embedded-opentype'), /* 2 */
url('../fonts/icomoon.woff2?rwmkoy') format('woff2'), /* 3 */
url('../fonts/icomoon.woff?rwmkoy') format('woff'), /* 4 */
url('../fonts/icomoon.otf?rwmkoy') format('opentype'), /* 5 */
url('../fonts/icomoon.ttf?rwmkoy') format('truetype'), /* 5 */
url('../fonts/icomoon.svg?rwmkoy#icomoon') format('svg'); /* 6 */
font-display: block;
font-style: normal;
font-weight: normal;
@ -155,10 +43,15 @@
font-family: 'icomoon' !important;
font-variant: normal;
font-style: normal;
font-weight: normal;
line-height: 1;
text-transform: none;
speak: never;
/* Better Font Rendering =========== */
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
.icon-chevrons-right:before
@ -171,112 +64,112 @@
content: "\e901";
}
.icon-document-file-txt:before
.icon-corner-right-down:before
{
content: "\e902";
}
.icon-corner-right-down:before
.icon-folder:before
{
content: "\e903";
}
.icon-folder:before
.icon-book:before
{
content: "\e904";
}
.icon-tag:before
.icon-book-open:before
{
content: "\e905";
}
.icon-book-open:before
.icon-tag:before
{
content: "\e906";
}
.icon-book:before
.icon-arrow-right:before
{
content: "\e907";
}
.icon-arrow-right:before
.icon-alert-circle:before
{
content: "\e908";
}
.icon-user:before
.icon-check-circle:before
{
content: "\e909";
}
.icon-skip-back:before
.icon-facebook:before
{
content: "\e90a";
}
.icon-skip-forward:before
.icon-home:before
{
content: "\e90b";
}
.icon-play:before
.icon-instagram:before
{
content: "\e90c";
}
.icon-search:before
.icon-play:before
{
content: "\e90d";
}
.icon-settings:before
.icon-search:before
{
content: "\e90e";
}
.icon-home:before
.icon-settings:before
{
content: "\e90f";
}
.icon-alert-circle:before
.icon-skip-back:before
{
content: "\e910";
}
.icon-check-circle:before
.icon-skip-forward:before
{
content: "\e911";
}
.icon-x-circle:before
.icon-user:before
{
content: "\e912";
}
.icon-facebook:before
.icon-x:before
{
content: "\e913";
}
.icon-instagram:before
.icon-x-circle:before
{
content: "\e914";
}
.icon-x:before
.icon-home3:before
{
content: "\e915";
}
.icon-home3:before
.icon-chevrons-down:before
{
content: "\e916";
}
.icon-chevron-down:before
.icon-mail:before
{
content: "\e917";
}
@ -291,16 +184,66 @@
content: "\e919";
}
.icon-mail:before
.icon-menu:before
{
content: "\e91a";
}
.icon-airplay:before
{
content: "\e91b";
}
.icon-chevron-left:before
{
content: "\e91c";
}
.icon-chevron-right:before
{
content: "\e91d";
}
.icon-square:before
{
content: "\e91e";
}
.icon-picture:before
{
content: "\eaa1";
}
.icon-washing-machine:before
{
content: "\eb07";
}
.icon-tv:before
{
content: "\ebce";
}
.icon-cake:before
{
content: "\ec50";
}
.icon-refrigerator:before
{
content: "\ec72";
}
.icon-burger:before
{
content: "\ec80";
}
.icon-coffee-pot:before
{
content: "\ec92";
}
.icon-leaf:before
{
content: "\ec9b";
@ -316,41 +259,6 @@
content: "\eccb";
}
.icon-wifi-100:before
{
content: "\ed65";
}
.icon-picture:before
{
content: "\eaa1";
}
.icon-washing-machine:before
{
content: "\eb07";
}
.icon-refrigerator:before
{
content: "\ec72";
}
.icon-burger:before
{
content: "\ec80";
}
.icon-cake:before
{
content: "\ec50";
}
.icon-coffee-pot:before
{
content: "\ec92";
}
.icon-bicycle-riding:before
{
content: "\ece4";
@ -360,3 +268,8 @@
{
content: "\ece7";
}
.icon-wifi-100:before
{
content: "\ed65";
}

747
site/templates/css/main.css Normal file
View file

@ -0,0 +1,747 @@
*, *::before, *::after
{
box-sizing: border-box;
}
.grella
{
display: grid;
grid-template-columns:
[completo-start] minmax(var(--separacion), 1fr)
[destacado-start] minmax(0, var(--destacado))
[contido-start] min(100% - (var(--separacion) * 2), var(--contido-max)) [contido-end]
minmax(0, var(--destacado)) [destacado-end]
minmax(var(--separacion), 1fr) [completo-end]
;
}
.grella > :not(.destacado, .completo),
.completo > :not(.destacado, .completo)
{
grid-column: contido;
}
.grella > .completo
{
display: grid;
grid-column: completo;
grid-template-columns: inherit;
}
.completo > .completo
{
display: grid;
grid-column: completo;
grid-template-columns: inherit;
}
.grella > .destacado,
.completo > .destacado
{
grid-column: destacado;
}
html, body
{
height: 100%;
}
body
{
display: grid;
grid-template-rows: auto 1fr auto;
color: rgb(var(--cor_10));
font-family: Avenir, Montserrat, Corbel, 'URW Gothic', source-sans-pro, sans-serif;
font-size: 1rem;
font-weight: normal;
background-color: rgb(var(--cor_60));
}
a
{
color: rgb(var(--cor_30));
text-decoration-line: underline;
text-decoration-style: dotted;
}
h1, h2, h3, h4, h5, h6
{
color: rgb(var(--cor_30));
font-family: ui-rounded, 'Hiragino Maru Gothic ProN', Quicksand, Comfortaa, Manjari, 'Arial Rounded MT', 'Arial Rounded MT Bold', Calibri, source-sans-pro, sans-serif;
font-weight: bold;
text-wrap: balance;
}
figure
{
margin: 0;
}
figure img
{
width: 100%;
}
ul,
ol
{
display: flex;
flex-direction: row;
margin: 0;
padding: 0;
list-style: none;
}
ul a,
ol a
{
text-decoration: none;
}
section h3,
section p
{
margin: 0;
}
header#cabeceira
{
grid-template-rows: auto 1fr auto;
margin-bottom: var(--separacion);
padding-bottom: var(--separacion);
border-bottom: 1px solid rgba(var(--cor_10), 0.5);
}
div#cabeceira-superior
{
margin-bottom: var(--separacion);
padding-block: 0.5rem;
border-bottom: 1px solid rgba(var(--cor_10), 0.5);
background-color: #eeeeee;
}
nav#menu-usuario
{
display: grid;
grid-template-columns: auto auto;
justify-content: space-between;
}
nav#menu-usuario ul
{
grid-column: 2;
justify-content: flex-end;
}
div#cabeceira-inferior
{
display: grid;
grid-template-columns: minmax(0, 1fr) auto var(--separacion) auto minmax(0, 1fr);
justify-content: center;
align-items: center;
gap: var(--separacion) 0;
}
div#cabeceira-inferior a#logo
{
grid-column: 1 / span 5;
}
form#atopar
{
grid-column: 2;
position: relative;
}
form#atopar input
{
display: block;
appearance: none;
width: 100%;
padding: 0.5rem 0.75rem;
border: 1px solid rgb(var(--cor_10));
border-radius: 0;
color: rgb(var(--cor_10));
transition: border-color 0.15s ease-in-out,
}
form#atopar label
{
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
overflow: hidden;
padding: 0.5rem 0.75rem;
border: 1PX solid transparent;
text-align: start;
text-overflow: ellipsis;
white-space: nowrap;
pointer-events: none;
transform-origin: 0 0;
transition: opacity 0.1s ease-in-out,
transform 0.1s ease-in-out;
}
form#atopar input:focus
{
border-color: rgb(var(--cor_30));
outline: 0;
color: var(--bs-body-color);
}
form#atopar input:focus ~ label
{
height: unset;
width: unset;
padding: 0;
background-color: rgb(var(--cor_60));
opacity: unset;
transform: scale(0.85) translateY(-0.8rem) translateX(0.15rem);
}
form#atopar .boton
{
position: absolute;
top: 0;
right: 0;
}
nav#menu-idiomas
{
grid-column: 4;
}
nav#menu-principal
{
grid-column: 1 / 6;
}
nav#menu-principal div#menu-despregable
{
position: fixed;
top: 0;
left: 0;
bottom: 0;
z-index: 99;
max-width: 100%;
width: 50%;
border-right: 2px solid rgb(var(--cor_30));
background-color: rgb(var(--cor_60));
transform: translateX(-100%);
transition: transform 0.3s ease-in-out;
}
nav#menu-principal div#menu-despregable.despregado
{
transform: translateX(0);
}
nav#menu-principal button.pechar
{
margin: 0.5rem var(--separacion);
}
nav#menu-principal ul
{
flex-direction: column;
}
div#menu-despregable li
{
border-left: 0.625rem solid rgb(var(--cor_60))
}
div#menu-despregable li:has(.activo),
div#menu-despregable li:hover
{
border-left: 0.625rem solid rgb(var(--cor_30));
text-decoration-line: underline;
text-decoration-style: dotted;
}
div#menu-despregable li a
{
display: block;
padding: 0.5rem;
color: rgb(var(--cor_10));
font-size: 1rem;
font-weight: var(--bs-nav-link-font-weight);
text-decoration: none;
transition: color 0.15s ease-in-out,
background-color 0.15s ease-in-out,
border-color 0.15s ease-in-out;
}
nav#migas
{
margin-bottom: var(--separacion);
}
article section
{
margin-bottom: var(--separacion);
}
section#mantemento img
{
margin-bottom: 1.5rem;
padding: 3rem;
border: 1px solid rgba(var(--cor_10), 0.3);
border-radius: 8px;
box-shadow: 0 1rem 3rem rgba(var(--cor_10), 0.3);
}
section[id^="galeria-"]
{
grid-column: destacado;
width: 100%;
height: auto;
margin-inline: auto;
}
section[id^="galeria-"] div.swiper-wrapper
{
height: auto;
}
section[id^="galeria-"] figure img
{
display: block;
width: 100%;
height: auto;
object-fit: contain;
background-color: rgb(var(--cor_60));
}
section[id^="galeria-"] figure figcaption
{
padding: 10px 40px 20px;
color: rgb(var(--cor_30));
font-family: ui-rounded, 'Hiragino Maru Gothic ProN', Quicksand, Comfortaa, Manjari, 'Arial Rounded MT', 'Arial Rounded MT Bold', Calibri, source-sans-pro, sans-serif;
font-weight: normal;
font-size: 1rem;
text-align: center;
}
section[id^="galeria-"] p.controis
{
display: flex;
justify-content: center;
margin: 0 auto;
}
section[id^="galeria-"] .swiper-button-prev,
section[id^="galeria-"] .swiper-button-next
{
padding: var(--separacion);
}
section[id^="galeria-"] .swiper-pagination
{
padding: var(--separacion) 0;
}
section[id^="galeria-"] .swiper-button-prev,
section[id^="galeria-"] .swiper-button-next,
section[id^="galeria-"] .swiper-pagination
{
display: inline;
position: relative;
bottom: initial;
top: initial;
left: initial;
right: initial;
width: fit-content;
height: auto;
margin: -20px 0 0;
color: rgb(var(--cor_10));
}
section[id^="galeria-"] .swiper-button-next::after,
section[id^="galeria-"] .swiper-button-prev::after
{
font-family: 'icomoon' !important;;
font-size: 1.5rem;
text-transform: none !important;
letter-spacing: 0;
font-variant: initial;
line-height: 1.5;
}
section[id^="galeria-"] .swiper-button-prev::after,
section[id^="galeria-"] .swiper-rtl .swiper-button-next::after
{
content: '\e91c';
}
section[id^="galeria-"] .swiper-button-next::after,
section[id^="galeria-"] .swiper-rtl .swiper-button-prev::after
{
content: '\e91d';
}
section[id^="galeria-"] .swiper-pagination-bullet
{
display: inline;
width: fit-content;
margin: 0;
padding: var(--separacion);
background-color: transparent;
}
section[id^="galeria-"] .swiper-pagination-bullet:after
{
font-family: 'icomoon' !important;;
font-size: 1.5rem;
text-transform: none !important;
letter-spacing: 0;
font-variant: initial;
line-height: 1.5;
content: "\e91e";
}
section[id^="galeria-"] .swiper-pagination-bullet-active:after
{
content: "\e91b";
}
section[id^="imaxe-"],
div[id^="imaxe-"]
{
display: grid;
align-items: center;
gap: var(--separacion);
}
section[id^="imaxe-"] div.artigo
{
align-self: start;
}
footer#pe
{
padding-block: 1.5rem;
border-top: 1px solid ;
color: rgb(var(--cor_60));
font-size: 0.875rem;
background-color: rgb(var(--cor_30));
}
footer#pe a
{
color: rgb(var(--cor_60));
}
footer#pe div#info
{
display: grid;
grid-template-columns: auto var(--separacion) auto
}
footer#pe p#copy
{
grid-column: 3;
}
footer#pe ul#redes
{
grid-column: 1 / 4;
}
footer#pe p#banners
{
grid-column: 1 / 4;
}
footer#pe p#desenrolo
{
grid-column: 1 / 4;
}
footer#pe p#banners img
{
padding: var(--separacion);
}
footer#pe ul#redes
{
justify-content: center;
}
footer#pe ul#redes li a
{
padding: var(--separacion);
font-size: 2rem;
}
footer#pe p#desenrolo
{
grid-column: 1 / 7;
}
footer#pe p#desenrolo span
{
font-size: 0.75rem;
}
.boton
{
display: inline-block;
padding: 0.5rem;
border: 1px solid rgb(var(--cor_10));
color: rgb(var(--cor_10));
background-color: transparent;
cursor: pointer;
}
.boton.primario
{
border-color: transparent;
color: rgb(var(--cor_60));
background-color: rgb(var(--cor_30));
}
.boton.activo
{
color: rgb(var(--cor_60));
background-color: rgb(var(--cor_10));
}
.centrado
{
text-align: center;
}
.visually-hidden
{
position: absolute;
width: 1px;
height: 1px;
padding: 0;
margin: -1px;
white-space: nowrap;
overflow: hidden;
clip: rect(1px, 1px, 1px, 1px);
border: 0;
}
.element-focusable:focus
{
clip: auto;
overflow: visible;
height: auto;
}
.bypass-to-main:focus
{
top: 0;
left: 0;
width: 100%;
height: 40px;
line-height: 40px;
text-align: center;
background: rgb(var(--cor_30));
color: rgb(var(--cor_60));
}
@media (min-width: 640px)
{
footer#pe div#info
{
grid-template-columns: auto var(--separacion) auto 1fr auto;
}
footer#pe ul#redes
{
grid-column: 5;
}
footer#pe p#banners
{
grid-column: 1 / 6;
}
footer#pe p#desenrolo
{
grid-column: 1 / 6;
}
}
@media (min-width: 768px)
{
div#cabeceira-inferior
{
grid-template-columns: auto 1fr auto var(--separacion) auto;
}
div#cabeceira-inferior a#logo
{
grid-column: 1;
}
form#atopar
{
grid-column: 3;
}
nav#menu-idiomas
{
grid-column: 5;
}
section[id^="imaxe-"],
div[id^="imaxe-"]
{
grid-template-columns: 1fr 1fr;
}
section[id^="imaxe-"].superior,
div[id^="imaxe-"].superior
{
grid-template-columns: 1fr;
}
section[id^="imaxe-"].esquerda figure,
div[id^="imaxe-"].esquerda figure
{
grid-column: 1;
grid-row: 2;
}
section[id^="imaxe-"].esquerda div.artigo,
div[id^="imaxe-"].esquerda figure div.artigo
{
grid-column: 2;
grid-row: 2;
}
section[id^="imaxe-"].dereita figure,
div[id^="imaxe-"].dereita figure
{
grid-column: 2;
grid-row: 2;
}
section[id^="imaxe-"].dereita div.artigo,
div[id^="imaxe-"].dereita div.artigo
{
grid-column: 1;
grid-row: 2;
}
section[id^="imaxe-"] h3
{
grid-column: 1 / 3;
grid-row: 1;
}
}
@media (min-width: 1024px)
{
nav#menu-usuario button.boton,
nav#menu-principal div#menu-despregable button.boton
{
display: none;
}
nav#menu-principal div#menu-despregable
{
flex-grow: 1;
position: static;
z-index: auto;
width: auto;
height: auto;
border: 0;
background-color: transparent;
transform: none;
transition: none;
}
nav#menu-principal ul
{
flex-direction: row;
justify-content: center;
}
nav#menu-principal ul li,
nav#menu-principal ul li:has(.activo),
nav#menu-principal ul li:hover
{
border-left: 0;
}
}

View file

@ -1,510 +0,0 @@
*, *::before, *::after
{
box-sizing: border-box;
}
body
{
color: rgb(var(--cor_10));
font-family: 'Source Sans Pro', sans-serif;
font-size: 1rem;
}
body.signin
{
display: flex;
align-items: center;
padding-top: 40px;
padding-bottom: 40px;
background-color: #f5f5f5;
}
a
{
color: rgba(var(--cor_30), var(--bs-link-opacity, 1));
text-decoration-line: underline;
text-decoration-style: dotted;
}
h1, h2, h3, h4, h5, h6
{
color: rgb(var(--cor_30));
font-family: 'Josefin Sans', serif;
}
dl
{
display: flex;
flex-direction: row;
flex-wrap: wrap;
gap: 10%;
max-width: 18.75rem;
margin: 0;
}
dt
{
width: 10%;
color: rgb(var(--cor_30));
}
dt::after
{
content: ": ";
}
dd
{
width: 80%;
margin: 0;
padding: 0;
}
figure
{
margin: 0;
}
figure figcaption
{
padding: 10px 40px 20px;
color: rgb(var(--cor_30));
font-family: 'Source Sans Pro', sans-serif;
font-weight: normal;
font-size: 1rem;
text-align: center;
}
figure img
{
display: block;
width: 100%;
height: auto;
object-fit: contain;
background-color: rgb(var(--cor_60));
}
figure.effect-ming
{
background: #030c17;
position: relative;
float: left;
overflow: hidden;
margin: 10px 1%;
padding: 0;
min-width: 320px;
max-width: 480px;
max-height: 360px;
width: 100%;
height: auto;
background: rgb(var(--cor_30));
text-align: center;
cursor: pointer;
}
figure.effect-ming img
{
position: relative;
display: block;
min-height: 100%;
max-width: 100%;
opacity: 0.9;
transition: opacity 0.35s;
}
figure.effect-ming:hover img
{
opacity: 0.4;
}
figure.effect-ming figcaption
{
padding: 2em;
color: #fff;
text-transform: uppercase;
font-size: 1.25em;
backface-visibility: hidden;
}
figure.effect-ming figcaption > a
{
z-index: 1000;
text-indent: 200%;
white-space: nowrap;
font-size: 0;
opacity: 0;
}
figure.effect-ming figcaption,
figure.effect-ming figcaption > a
{
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
figure.effect-ming h3
{
margin: 20% 0 10px 0;
word-spacing: -0.15em;
font-weight: 700;
transition: transform 0.35s;
background: rgba(255,255,255,0.5);
color: rgb(var(--cor_30));
}
figure.effect-ming:hover h3
{
transform: scale(0.9);
}
figure.effect-ming p
{
padding: 1em;
opacity: 0;
letter-spacing: 1px;
font-size: 68.5%;
transition: opacity 0.35s, transform 0.35s;
transform: scale(1.5);
}
figure.effect-ming figcaption::before
{
position: absolute;
top: 30px;
right: 30px;
bottom: 30px;
left: 30px;
border: 2px solid #fff;
box-shadow: 0 0 0 30px rgba(255,255,255,0.2);
content: '';
opacity: 0;
transition: opacity 0.35s, transform 0.35s;
transform: scale3d(1.4,1.4,1);
}
figure.effect-ming:hover figcaption::before,
figure.effect-ming:hover p
{
opacity: 1;
transform: scale3d(1,1,1);
}
figure.effect-ming figcaption::before, figure.effect-ming figcaption::after
{
pointer-events: none;
}
time
{
display: block;
position: relative;
height: 5rem;
overflow: hidden;
width: 5rem;
border-radius: 0.6em;
box-shadow: 0 1px 0 #bdbdbd, 0 2px 0 #fff, 0 3px 0 #bdbdbd, 0 4px 0 #fff, 0 5px 0 #bdbdbd, 0 0 0 1px #bdbdbd;
font-size: 0.75rem;
background-color: #fff;
}
time *
{
display: block;
width: 100%;
font-size: 0.8rem;
font-style: normal;
font-weight: bold;
text-align: center;
}
time em
{
position: absolute;
bottom: 0;
color: rgb(var(--cor_30));
}
time strong
{
position: absolute;
top: 0;
padding: 0.3rem 0;
box-shadow: 0 2px 0 rgb(var(--cor_30));
color: white;
background-color: rgb(var(--cor_30));
}
time span
{
padding-top: 1.4rem;
color: black;
font-size: 2rem;
letter-spacing: -0.05rem;
}
.btn-primary
{
--bs-btn-bg: rgb(var(--cor_30));
--bs-btn-border-color: rgb(var(--cor_30));
--bs-btn-hover-bg: rgb(var(--cor_30));
--bs-btn-hover-border-color: rgb(var(--cor_30));
--bs-btn-active-bg: rgb(var(--cor_30));
--bs-btn-active-border-color: rgb(var(--cor_30));
--bs-btn-disabled-bg: rgb(var(--cor_30));
--bs-btn-disabled-border-color: rgb(var(--cor_30));
}
.breadcrumb-item + .breadcrumb-item::before
{
padding-right: unset;
}
#search .form-floating > .form-control,
#search .form-floating > .form-control-plaintext,
#search .form-floating > .form-select
{
height: calc(2.25rem + 2px);
line-height: 1.25;
}
#search .form-floating > .form-control:focus ~ label,
#search .form-floating > .form-control:not(:placeholder-shown) ~ label,
#search .form-floating > .form-control-plaintext ~ label,
#search .form-floating > .form-select ~ label
{
height: unset;
width: unset;
padding: 0 !important;
background-color: #fff;
opacity: unset;
transform: scale(0.85) translateY(-0.8rem) translateX(0.15rem);
}
#menu-desplegable .nav-item
{
border-left: 0.625rem solid rgb(var(--cor_60));
}
#menu-desplegable .nav-item.active,
#menu-desplegable .nav-item:hover
{
border-left: 0.625rem solid rgb(var(--cor_30));
text-decoration-line: underline;
text-decoration-style: dotted;
}
.navbar-toggler-icon
{
color: rgba(var(--cor_10));
background-image: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba%280, 0, 0, 0.55%29' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e");
}
.btn-close:focus
{
outline: 2px dotted rgb(var(--cor_10)) !important;
box-shadow: none;
}
.swiper
{
width: 100%;
height: auto;
margin-left: auto;
margin-right: auto;
}
.galeria .swiper-slide
{
display: flex;
justify-content: center;
align-items: center;
padding: 10px;
text-align: center;
font-size: 18px;
background: #fff;
}
.swiper-button-prev,
.swiper-button-next
{
bottom: 15px;
top: unset;
color: rgb(var(--cor_10));
}
.swiper-pagination-bullet-active
{
background: rgb(var(--cor_30));
}
.reixa-item
{
cursor: pointer;
}
.feature-icon
{
width: 3rem;
height: 3rem;
border-radius: .75rem;
}
a.collapse-head::before
{
font-family: 'icomoon';
content: "\e917";
float: right;
transition: all 0.5s;
}
a.collapse-head.active:before
{
transform: rotate(180deg);
}
.text-bg-primary
{
background-color: rgba(var(--cor_30), var(--bs-bg-opacity, 1)) !important;
}
.text-bg-secondary
{
background-color: rgba(var(--cor_10), var(--bs-bg-opacity, 1)) !important;
}
.bg-primary
{
background-color: rgba(var(--cor_30), var(--bs-bg-opacity)) !important;
}
.border-primary
{
border-color: rgba(var(--cor_30), var(--bs-border-opacity)) !important;
}
.form-signin
{
max-width: 330px;
padding: 15px;
}
.form-signin .form-floating:focus-within
{
z-index: 2;
}
.form-signin input[type="text"]
{
margin-bottom: -1px;
border-bottom-right-radius: 0;
border-bottom-left-radius: 0;
}
.form-signin input[type="password"]
{
margin-bottom: 10px;
border-top-left-radius: 0;
border-top-right-radius: 0;
}
@media (min-width: 992px)
{
#menu-desplegable .nav-item,
#menu-desplegable .nav-item.active,
#menu-desplegable .nav-item:hover
{
border-left: 0;
}
.navbar-toggler
{
display: none;
}
}
@media (min-width: 1024px)
{
dl
{
gap: 0;
}
dt
{
width: 60%;
}
dd
{
width: 40%;
}
}
.visually-hidden
{
position: absolute;
width: 1px;
height: 1px;
padding: 0;
margin: -1px;
white-space: nowrap;
overflow: hidden;
clip: rect(1px, 1px, 1px, 1px);
border: 0;
}
.element-focusable:focus
{
clip: auto;
overflow: visible;
height: auto;
}
.bypass-to-main:focus
{
top: 0;
left: 0;
width: 100%;
height: 40px;
line-height: 40px;
text-align: center;
background: rgb(var(--cor_30));
color: rgb(var(--cor_60));
}

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

Before

Width:  |  Height:  |  Size: 274 KiB

File diff suppressed because it is too large Load diff

Before

Width:  |  Height:  |  Size: 276 KiB

File diff suppressed because it is too large Load diff

Before

Width:  |  Height:  |  Size: 277 KiB

File diff suppressed because it is too large Load diff

Before

Width:  |  Height:  |  Size: 275 KiB

File diff suppressed because it is too large Load diff

Before

Width:  |  Height:  |  Size: 488 KiB

Some files were not shown because too many files have changed in this diff Show more