PluginProbe
Autoptimize / 3.1.11
Autoptimize v3.1.11
2.2.2 2.3.0 2.3.1 2.3.2 2.3.3 2.3.4 2.4.0 2.4.1 2.4.2 2.4.3 2.4.4 2.5.0 2.5.1 2.6.0 2.6.1 2.6.2 2.7.0 2.7.1 2.7.2 2.7.3 2.7.4 2.7.5 2.7.6 2.7.7 2.7.8 All 107 releases
autoptimize / classes / autoptimizeConfig.php

autoptimizeConfig.php in Autoptimize 3.1.11, at classes/autoptimizeConfig.php

1,104 lines 53.9 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Main configuration logic.
4 */
5
6 if ( ! defined( 'ABSPATH' ) ) {
7 exit;
8 }
9
10 class autoptimizeConfig
11 {
12 /**
13 * Options.
14 *
15 * @var array
16 */
17 private $config = null;
18
19 /**
20 * Singleton instance.
21 *
22 * @var self|null
23 */
24 static private $instance = null;
25
26 /**
27 * Options.
28 *
29 * @var bool
30 */
31 private $settings_screen_do_remote_http = true;
32
33 /**
34 * Singleton.
35 */
36 private function __construct()
37 {
38 if ( is_admin() ) {
39 // Add the admin page and settings.
40 if ( autoptimizeOptionWrapper::is_ao_active_for_network() ) {
41 add_action( 'network_admin_menu', array( $this, 'addmenu' ) );
42 }
43
44 add_action( 'admin_menu', array( $this, 'addmenu' ) );
45 add_action( 'admin_init', array( $this, 'registersettings' ) );
46 add_action( 'admin_init', array( 'PAnD', 'init' ) );
47
48 // Set meta info.
49 if ( function_exists( 'plugin_row_meta' ) ) {
50 // 2.8 and higher.
51 add_filter( 'plugin_row_meta', array( $this, 'setmeta' ), 10, 2 );
52 } elseif ( function_exists( 'post_class' ) ) {
53 // 2.7 and lower.
54 $plugin = plugin_basename( AUTOPTIMIZE_PLUGIN_DIR . 'autoptimize.php' );
55 add_filter( 'plugin_action_links_' . $plugin, array( $this, 'setmeta' ) );
56 }
57
58 // Clean cache?
59 if ( autoptimizeOptionWrapper::get_option( 'autoptimize_cache_clean' ) ) {
60 autoptimizeCache::clearall();
61 autoptimizeOptionWrapper::update_option( 'autoptimize_cache_clean', 0 );
62 }
63
64 $this->settings_screen_do_remote_http = apply_filters( 'autoptimize_settingsscreen_remotehttp', $this->settings_screen_do_remote_http );
65
66 if ( $this->is_ao_meta_settings_active() ) {
67 $meta_box = new autoptimizeMetabox();
68 }
69 }
70
71 // Adds the Autoptimize Toolbar to the Admin bar.
72 // (we load outside the is_admin check so it's also displayed on the frontend toolbar).
73 $toolbar = new autoptimizeToolbar();
74 }
75
76 /**
77 * Instantiates aoconfig.
78 *
79 * @return autoptimizeConfig
80 */
81 static public function instance()
82 {
83 // Only one instance.
84 if ( null === self::$instance ) {
85 self::$instance = new autoptimizeConfig();
86 }
87
88 return self::$instance;
89 }
90
91 public function show_network_message() {
92 ?>
93 <div class="wrap">
94 <h1><?php esc_html_e( 'Autoptimize Settings', 'autoptimize' ); ?></h1>
95 <?php echo $this->ao_admin_tabs(); ?>
96 <p style="font-size:120%;"><?php echo apply_filters( 'autoptimize_filter_settingsscreen_multisite_network_message', esc_html__( 'Autoptimize is enabled and configured on a WordPress network level. Please contact your network administrator if you need Autoptimize settings changed.', 'autoptimize' ) ); ?></p>
97 </div>
98 <?php
99 }
100
101 public function show_config()
102 {
103 // phpcs:disable Generic.WhiteSpace.ScopeIndent.IncorrectExact
104 // phpcs:disable Generic.WhiteSpace.ScopeIndent.Incorrect
105 $conf = self::instance();
106 ?>
107 <style>
108 /* title and button */
109 #ao_title_and_button:after {content:''; display:block; clear:both;}
110
111 /* form */
112 .itemDetail {
113 background: #fff;
114 border: 1px solid #ccc;
115 padding: 15px;
116 margin: 15px 10px 10px 0;
117 }
118 .itemTitle {
119 margin-top: 0;
120 }
121
122 .form-table th{font-weight:normal;}
123 #autoptimize_main form input:invalid {box-shadow: 0 0 1px 1px red;}
124 #autoptimize_main .cb_label {display: block; padding-left: 25px; text-indent: -25px;}
125 #autoptimize_main .form-table th {padding-top: 15px; padding-bottom: 15px;}
126 #autoptimize_main .js_aggregate td, #autoptimize_main .js_aggregate th, #autoptimize_main .js_not_aggregate td, #autoptimize_main .js_not_aggregate th{padding-top:0px;}
127
128 /* rss block */
129 #futtta_feed ul{list-style:outside;}
130 #futtta_feed {font-size:medium; margin:0px 20px;}
131
132 /* banner + unslider */
133 .autoptimize_banner {
134 margin: 0 38px;
135 padding-bottom: 5px;
136 }
137 .autoptimize_banner ul li {
138 font-size:medium;
139 text-align:center;
140 }
141 .unslider {
142 position:relative;
143 }
144 .unslider-arrow {
145 display: block;
146 left: unset;
147 margin-top: -35px;
148 margin-left: 7px;
149 margin-right: 7px;
150 border-radius: 32px;
151 background: rgba(0, 0, 0, 0.10) no-repeat 50% 50%;
152 color: rgba(255, 255, 255, 0.8);
153 font: normal 20px/1 dashicons;
154 speak: none;
155 padding: 3px 2px 3px 4px;
156 -webkit-font-smoothing: antialiased;
157 -moz-osx-font-smoothing: grayscale;
158 }
159 .unslider-arrow:hover {
160 background-color: rgba(0, 0, 0, 0.20);
161 color: #FFF;
162 }
163 .unslider-arrow.prev {
164 padding: 3px 4px 3px 2px;
165 }
166 .unslider-arrow.next {
167 right: 0px;
168 }
169 .unslider-arrow.prev::before {
170 content: "\f341";
171 }
172 .unslider-arrow.next::before {
173 content: "\f345";
174 }
175
176 /* responsive stuff: hide admin-feed on smaller screens */
177 @media (min-width: 961px) {
178 #autoptimize_main {float:left;width:69%;}
179 #autoptimize_admin_feed{float:right;width:30%;display:block !important;}
180 }
181 @media (max-width: 960px) {
182 #autoptimize_main {width:100%;}
183 #autoptimize_admin_feed {width:0%;display:none !important;}
184 }
185 @media (max-width: 782px) {
186 #autoptimize_main input[type="checkbox"] {margin-left: 10px;}
187 #autoptimize_main .cb_label {display: block; padding-left: 45px; text-indent: -45px;}
188 }
189 </style>
190
191 <div class="wrap">
192 <div id="autoptimize_main">
193 <h1 id="ao_title"><?php apply_filters( 'autoptimize_filter_settings_is_pro', false ) ? esc_html_e( 'Autoptimize Pro Settings', 'autoptimize' ) : esc_html_e( 'Autoptimize Settings', 'autoptimize' ); ?></h1>
194 <?php echo $this->ao_admin_tabs(); ?>
195
196 <form method="post" action="<?php echo admin_url( 'options.php' ); ?>">
197 <?php settings_fields( 'autoptimize' ); ?>
198
199 <ul>
200
201 <?php
202 // Only show enable site configuration in network site option.
203 if ( is_network_admin() && autoptimizeOptionWrapper::is_ao_active_for_network() ) {
204 ?>
205 <li class="itemDetail multiSite">
206 <h2 class="itemTitle"><?php esc_html_e( 'Multisite Options', 'autoptimize' ); ?></h2>
207 <table class="form-table">
208 <tr valign="top">
209 <th scope="row"><?php esc_html_e( 'Enable site configuration?', 'autoptimize' ); ?></th>
210 <td><label class="cb_label"><input type="checkbox" id="autoptimize_enable_site_config" name="autoptimize_enable_site_config" <?php echo autoptimizeOptionWrapper::get_option( 'autoptimize_enable_site_config' ) ? 'checked="checked" ' : ''; ?>/>
211 <?php esc_html_e( 'Enable Autoptimize configuration per site.', 'autoptimize' ); ?></label></td>
212 </tr>
213 </table>
214 </li>
215 <?php } else { ?>
216 <input type="hidden" id="autoptimize_enable_site_config" name="autoptimize_enable_site_config" value="on" />
217 <?php } ?>
218
219 <li class="itemDetail">
220 <h2 class="itemTitle"><?php esc_html_e( 'JavaScript Options', 'autoptimize' ); ?></h2>
221 <table class="form-table">
222 <tr valign="top">
223 <th scope="row"><?php esc_html_e( 'Optimize JavaScript Code?', 'autoptimize' ); ?></th>
224 <td><input type="checkbox" id="autoptimize_js" name="autoptimize_js" <?php echo $conf->get( 'autoptimize_js' ) ? 'checked="checked" ' : ''; ?>/></td>
225 </tr>
226 <tr valign="top" class="js_sub js_aggregate_master">
227 <th scope="row"><?php esc_html_e( 'Aggregate JS-files?', 'autoptimize' ); ?></th>
228 <td><label class="cb_label"><input type="checkbox" id="autoptimize_js_aggregate" name="autoptimize_js_aggregate" <?php echo $conf->get( 'autoptimize_js_aggregate' ) ? 'checked="checked" ' : ''; ?>/>
229 <?php esc_html_e( 'Aggregate all linked JS-files to have them loaded non-render blocking?', 'autoptimize' ); ?></label></td>
230 </tr>
231 <tr valign="top" class="js_sub js_aggregate hidden">
232 <th scope="row">&emsp;<?php esc_html_e( 'Also aggregate inline JS?', 'autoptimize' ); ?></th>
233 <td><label class="cb_label"><input type="checkbox" name="autoptimize_js_include_inline" <?php echo $conf->get( 'autoptimize_js_include_inline' ) ? 'checked="checked" ' : ''; ?>/>
234 <?php esc_html_e( 'Let Autoptimize also extract JS from the HTML (discouraged as it can make Autoptimize\'s cache size grow quickly)', 'autoptimize' ); ?></label></td>
235 </tr>
236 <tr valign="top" class="js_sub js_aggregate hidden">
237 <th scope="row">&emsp;<?php esc_html_e( 'Force JavaScript in &lt;head&gt;?', 'autoptimize' ); ?></th>
238 <td><label class="cb_label"><input type="checkbox" name="autoptimize_js_forcehead" <?php echo $conf->get( 'autoptimize_js_forcehead' ) ? 'checked="checked" ' : ''; ?>/>
239 <?php esc_html_e( 'Load JavaScript early (discouraged as it makes the JS render blocking)', 'autoptimize' ); ?></label></td>
240 </tr>
241 <tr valign="top" class="js_sub js_aggregate hidden">
242 <th scope="row">&emsp;<?php esc_html_e( 'Add try-catch wrapping?', 'autoptimize' ); ?></th>
243 <td><label class="cb_label"><input type="checkbox" name="autoptimize_js_trycatch" <?php echo $conf->get( 'autoptimize_js_trycatch' ) ? 'checked="checked" ' : ''; ?>/>
244 <?php esc_html_e( 'If your aggregated scripts break because of a JS-error, you might want to try this, but generally discouraged.', 'autoptimize' ); ?></label></td>
245 </tr>
246 <tr valign="top" class="js_sub js_not_aggregate_master">
247 <th scope="row"><?php esc_html_e( 'Do not aggregate but defer?', 'autoptimize' ); ?></th>
248 <td><label class="cb_label"><input type="checkbox" id="autoptimize_js_defer_not_aggregate" name="autoptimize_js_defer_not_aggregate" <?php echo $conf->get( 'autoptimize_js_defer_not_aggregate' ) ? 'checked="checked" ' : ''; ?>/>
249 <?php esc_html_e( 'Individual JS-files will be minified and deferred, making them non-render-blocking.', 'autoptimize' ); ?></label></td>
250 </tr>
251 <tr valign="top" id="js_defer_inline" class="js_sub js_not_aggregate hidden">
252 <th scope="row">&emsp;<?php esc_html_e( 'Also defer inline JS?', 'autoptimize' ); ?></th>
253 <td><label class="cb_label"><input type="checkbox" name="autoptimize_js_defer_inline" <?php echo $conf->get( 'autoptimize_js_defer_inline' ) ? 'checked="checked" ' : ''; ?>/>
254 <?php esc_html_e( 'Also defer inline JS. Generally this will allow all JS to be deferred, so you should remove default exclusions, test and only exclude specific items if still needed.', 'autoptimize' ); ?></label></td>
255 </tr>
256 <?php if ( autoptimizeOptionWrapper::get_option( 'autoptimize_js_justhead' ) ) { ?>
257 <tr valign="top" class="js_sub js_aggregate">
258 <th scope="row">
259 <?php
260 esc_html_e( 'Look for scripts only in &lt;head&gt;?', 'autoptimize' );
261 echo ' <i>' . esc_html__( '(deprecated)', 'autoptimize' ) . '</i>';
262 ?>
263 </th>
264 <td><label class="cb_label"><input type="checkbox" name="autoptimize_js_justhead" <?php echo $conf->get( 'autoptimize_js_justhead' ) ? 'checked="checked" ' : ''; ?>/>
265 <?php esc_html_e( 'Mostly useful in combination with previous option when using jQuery-based templates, but might help keeping cache size under control.', 'autoptimize' ); ?></label></td>
266 </tr>
267 <?php } ?>
268 <tr valign="top" class="js_sub">
269 <th scope="row"><?php esc_html_e( 'Exclude scripts from Autoptimize:', 'autoptimize' ); ?></th>
270 <td><label><input type="text" pattern="[^\*]*" style="width:100%;" name="autoptimize_js_exclude" value="<?php echo esc_attr( autoptimizeOptionWrapper::get_option( 'autoptimize_js_exclude', '' ) ); ?>"/><br />
271 <?php
272 echo esc_html__( 'A comma-separated list of scripts you do not want optimized, for example \'whatever.js, my_var\' (without the quotes).', 'autoptimize' ) . ' ' . esc_html__( 'Important: when "aggregate JS-files" is on, excluded non-minified files are still minified by Autoptimize unless that option under "misc" is disabled.', 'autoptimize' );
273 ?>
274 </label></td>
275 </tr>
276 <tr valign="top">
277 <th scope="row"><?php esc_html_e( 'Remove Unused JavaScript?', 'autoptimize' ); ?></th>
278 <td><?php esc_html_e( 'Autoptimize combines your theme & plugins\' JavaScript, but does not know what is used and what not. If Google Pagespeed Insights detects unused JavaScript, consider using a plugin like "Plugin Organizer" or similar to manage what JavaScript is added where.', 'autoptimize' ); ?></td>
279 </tr>
280 </table>
281 </li>
282
283 <li class="itemDetail">
284 <h2 class="itemTitle"><?php esc_html_e( 'CSS Options', 'autoptimize' ); ?></h2>
285 <table class="form-table">
286 <tr valign="top">
287 <th scope="row"><?php esc_html_e( 'Optimize CSS Code?', 'autoptimize' ); ?></th>
288 <td><input type="checkbox" id="autoptimize_css" name="autoptimize_css" <?php echo $conf->get( 'autoptimize_css' ) ? 'checked="checked" ' : ''; ?>/></td>
289 </tr>
290 <tr class="css_sub" valign="top">
291 <th scope="row"><?php esc_html_e( 'Aggregate CSS-files?', 'autoptimize' ); ?></th>
292 <td><label class="cb_label"><input type="checkbox" id="autoptimize_css_aggregate" name="autoptimize_css_aggregate" <?php echo $conf->get( 'autoptimize_css_aggregate' ) ? 'checked="checked" ' : ''; ?>/>
293 <?php esc_html_e( 'Aggregate all linked CSS-files? If this option is off, the individual CSS-files will remain in place but will be minified.', 'autoptimize' ); ?></label></td>
294 </tr>
295 <tr valign="top" class="css_sub css_aggregate">
296 <th scope="row"><?php esc_html_e( 'Also aggregate inline CSS?', 'autoptimize' ); ?></th>
297 <td><label class="cb_label"><input type="checkbox" name="autoptimize_css_include_inline" <?php echo $conf->get( 'autoptimize_css_include_inline', '1' ) ? 'checked="checked" ' : ''; ?>/>
298 <?php esc_html_e( 'Check this option for Autoptimize to also aggregate CSS in the HTML.', 'autoptimize' ); ?></label></td>
299 </tr>
300 <tr class="css_sub css_aggregate" valign="top">
301 <th scope="row"><?php esc_html_e( 'Generate data: URIs for images?', 'autoptimize' ); ?></th>
302 <td><label class="cb_label"><input type="checkbox" name="autoptimize_css_datauris" <?php echo $conf->get( 'autoptimize_css_datauris' ) ? 'checked="checked" ' : ''; ?>/>
303 <?php esc_html_e( 'Enable this to include small background-images in the CSS itself instead of as separate downloads.', 'autoptimize' ); ?></label></td>
304 </tr>
305 <?php if ( autoptimizeOptionWrapper::get_option( 'autoptimize_css_justhead' ) ) { ?>
306 <tr valign="top" class="css_sub css_aggregate">
307 <th scope="row">
308 <?php
309 esc_html_e( 'Look for styles only in &lt;head&gt;?', 'autoptimize' );
310 echo ' <i>' . esc_html__( '(deprecated)', 'autoptimize' ) . '</i>';
311 ?>
312 </th>
313 <td><label class="cb_label"><input type="checkbox" name="autoptimize_css_justhead" <?php echo $conf->get( 'autoptimize_css_justhead' ) ? 'checked="checked" ' : ''; ?>/>
314 <?php esc_html_e( 'Don\'t autoptimize CSS outside the head-section. If the cache gets big, you might want to enable this.', 'autoptimize' ); ?></label></td>
315 </tr>
316 <?php } ?>
317 <tr valign="top" class="css_sub">
318 <th scope="row"><?php esc_html_e( 'Eliminate render-blocking CSS?', 'autoptimize' ); ?></th>
319 <td><label class="cb_label"><input type="checkbox" name="autoptimize_css_defer" id="autoptimize_css_defer" <?php echo $conf->get( 'autoptimize_css_defer' ) ? 'checked="checked" ' : ''; ?>/>
320 <?php
321 _e( 'Inline "above the fold CSS" while loading the main autoptimized CSS only after page load. <a href="https://wordpress.org/plugins/autoptimize/faq/" target="_blank">Check the FAQ</a> for more info.', 'autoptimize' );
322 echo ' ';
323 $critcss_settings_url = get_admin_url( null, 'options-general.php?page=ao_critcss' );
324 // translators: links "autoptimize critical CSS" tab.
325 echo sprintf( esc_html__( 'You can manually create rules for different types of pages or have this done fully automated on the %s tab.', 'autoptimize' ), '<a href="' . $critcss_settings_url . '">CriticalCSS</a>' );
326 ?>
327 </label></td>
328 </tr>
329 <tr valign="top" class="css_sub" id="autoptimize_css_defer_inline">
330 <th scope="row"></th>
331 <td><label><textarea rows="10" cols="10" style="width:100%;" spellcheck="false" placeholder="<?php esc_html_e( 'Paste the above the fold CSS here. You can leave this empty when using the automated Critical CSS integration.', 'autoptimize' ); ?>" name="autoptimize_css_defer_inline"><?php echo autoptimizeStyles::sanitize_css( autoptimizeOptionWrapper::get_option( 'autoptimize_css_defer_inline' ) ); ?></textarea></label></td>
332 </tr>
333 <tr valign="top" class="css_sub css_aggregate">
334 <th scope="row"><?php esc_html_e( 'Inline all CSS?', 'autoptimize' ); ?></th>
335 <td><label class="cb_label"><input type="checkbox" id="autoptimize_css_inline" name="autoptimize_css_inline" <?php echo $conf->get( 'autoptimize_css_inline' ) ? 'checked="checked" ' : ''; ?>/>
336 <?php esc_html_e( 'Inlining all CSS is an easy way to stop the CSS from being render-blocking, but is generally not recommended because the size of the HTML increases significantly. Additionally it might push meta-tags down to a position where e.g. Facebook and Whatsapp will not find them any more, breaking thumbnails when sharing.', 'autoptimize' ); ?></label></td>
337 </tr>
338 <tr valign="top" class="css_sub">
339 <th scope="row"><?php esc_html_e( 'Exclude CSS from Autoptimize:', 'autoptimize' ); ?></th>
340 <td><label><input type="text" pattern="[^\*]*" style="width:100%;" name="autoptimize_css_exclude" value="<?php echo esc_attr( $conf->get( 'autoptimize_css_exclude', '' ) ); ?>"/><br />
341 <?php
342 echo esc_html__( 'A comma-separated list of CSS you want to exclude from being optimized.', 'autoptimize' ) . ' ' . esc_html__( 'Important: excluded non-minified files are still minified by Autoptimize unless that option under "misc" is disabled.', 'autoptimize' );
343 ?>
344 </label></td>
345 </tr>
346 <?php if ( false === autoptimizeUtils::is_plugin_active( 'unusedcss/unusedcss.php' ) ) { ?>
347 <tr valign="top">
348 <th scope="row"><?php esc_html_e( 'Remove Unused CSS?', 'autoptimize' ); ?></th>
349 <?php
350 $_rapidload_link = 'https://misc.optimizingmatters.com/partners/?from=csssettings&partner=rapidload';
351 ?>
352 <td><?php
353 // translators: a link to rapidload + strong tags
354 echo sprintf( esc_html__( 'If Google Pagespeed Insights detects unused CSS, consider using %1$sthe premium Rapidload service%2$s to %3$sreduce your site\'s CSS size to up to 90&#37;%4$s, resulting in a slimmer, faster site!', 'autoptimize' ), '<a href="' . $_rapidload_link . '" target="_blank">', '</a>', '<strong>', '</strong>' ); ?></td>
355 </tr>
356 <?php } ?>
357 </table>
358 </li>
359
360 <li class="itemDetail">
361 <h2 class="itemTitle"><?php esc_html_e( 'HTML Options', 'autoptimize' ); ?></h2>
362 <table class="form-table">
363 <tr valign="top">
364 <th scope="row"><?php esc_html_e( 'Optimize HTML Code?', 'autoptimize' ); ?></th>
365 <td><input type="checkbox" id="autoptimize_html" name="autoptimize_html" <?php echo $conf->get( 'autoptimize_html' ) ? 'checked="checked" ' : ''; ?>/></td>
366 </tr>
367 <tr class="html_sub" valign="top">
368 <th scope="row"><?php esc_html_e( 'Also minify inline JS/ CSS?', 'autoptimize' ); ?></th>
369 <td><label class="cb_label"><input type="checkbox" name="autoptimize_html_minify_inline" <?php echo $conf->get( 'autoptimize_html_minify_inline' ) ? 'checked="checked" ' : ''; ?>/>
370 <?php esc_html_e( 'Enable this if you want inline JS or CSS to be minified as well.', 'autoptimize' ); ?></label></td>
371 </tr>
372 <tr class="html_sub" valign="top">
373 <th scope="row"><?php esc_html_e( 'Keep HTML comments?', 'autoptimize' ); ?></th>
374 <td><label class="cb_label"><input type="checkbox" name="autoptimize_html_keepcomments" <?php echo $conf->get( 'autoptimize_html_keepcomments' ) ? 'checked="checked" ' : ''; ?>/>
375 <?php esc_html_e( 'Enable this if you want HTML comments to remain in the page.', 'autoptimize' ); ?></label></td>
376 </tr>
377 </table>
378 </li>
379
380 <li class="itemDetail">
381 <h2 class="itemTitle"><?php esc_html_e( 'CDN Options', 'autoptimize' ); ?></h2>
382 <table class="form-table">
383 <tr valign="top">
384 <th scope="row"><?php esc_html_e( 'CDN Base URL', 'autoptimize' ); ?></th>
385 <?php
386 if ( true === autoptimizeImages::imgopt_active() && true === apply_filters( 'autoptimize_filter_cdn_set_by_imgopt', false ) ) {
387 // cdn set by imgopt, not to be changealbe in the settings.
388 $cdn_editable = 'disabled';
389 $cdn_placeholder = 'placeholder="' . esc_html__( 'The CDN has automatically been set to make use of the image optimization CDN.', 'autoptimize' ) . ' "';
390 $cdn_description = '';
391 } else {
392 $cdn_editable = '';
393 $cdn_placeholder = 'placeholder="' . esc_html__( 'example: //cdn.yoursite.com/', 'autoptimize' ) . ' "';
394 $cdn_description = esc_html__( 'Enter your CDN root URL to enable CDN for Autoptimized files. The URL can be http, https or protocol-relative. This is not needed for Cloudflare.', 'autoptimize' );
395 }
396 ?>
397 <td><label><input id="cdn_url" type="text" name="autoptimize_cdn_url" pattern="^(https?:)?\/\/([\da-z\.-]+)\.([\da-z\.]{2,6})([\/\w \.-]*)*(:\d{2,5})?\/?$" style="width:100%" <?php echo $cdn_placeholder . $cdn_editable; ?> value="<?php echo esc_url( autoptimizeOptionWrapper::get_option( 'autoptimize_cdn_url', '' ), array( 'http', 'https' ) ); ?>" /><br />
398 <?php echo $cdn_description; ?>
399 </label></td>
400 </tr>
401 </table>
402 </li>
403
404 <li class="itemDetail">
405 <h2 class="itemTitle"><?php esc_html_e( 'Cache Info', 'autoptimize' ); ?></h2>
406 <table class="form-table" >
407 <tr valign="top" >
408 <th scope="row"><?php esc_html_e( 'Cache folder', 'autoptimize' ); ?></th>
409 <td><?php echo htmlentities( AUTOPTIMIZE_CACHE_DIR ); ?></td>
410 </tr>
411 <tr valign="top" >
412 <th scope="row"><?php esc_html_e( 'Can we write?', 'autoptimize' ); ?></th>
413 <td><?php echo ( autoptimizeCache::cacheavail() ? esc_html__( 'Yes', 'autoptimize' ) : esc_html__( 'No', 'autoptimize' ) ); ?></td>
414 </tr>
415 <tr valign="top" >
416 <th scope="row"><?php esc_html_e( 'Cached styles and scripts', 'autoptimize' ); ?></th>
417 <td>
418 <?php
419 $ao_stat_arr = autoptimizeCache::stats();
420 if ( ! empty( $ao_stat_arr ) && is_array( $ao_stat_arr ) ) {
421 $ao_cache_size = size_format( $ao_stat_arr[1], 2 );
422 $details = '';
423 if ( $ao_cache_size > 0 ) {
424 $details = ', ~' . $ao_cache_size . ' total';
425 }
426 // translators: Kilobytes + timestamp shown.
427 printf( esc_html__( '%1$s files, totalling %2$s (calculated at %3$s)', 'autoptimize' ), $ao_stat_arr[0], $ao_cache_size, wp_date( 'H:i', $ao_stat_arr[2] ) ); // phpcs:ignore WordPress.DateTime.RestrictedFunctions.date_date
428 }
429 ?>
430 </td>
431 </tr>
432 </table>
433 </li>
434
435 <li class="itemDetail">
436 <h2 class="itemTitle"><?php esc_html_e( 'Misc Options', 'autoptimize' ); ?></h2>
437 <table class="form-table">
438 <tr valign="top">
439 <th scope="row"><?php esc_html_e( 'Save aggregated script/css as static files?', 'autoptimize' ); ?></th>
440 <td><label class="cb_label"><input type="checkbox" name="autoptimize_cache_nogzip" <?php echo $conf->get( 'autoptimize_cache_nogzip' ) ? 'checked="checked" ' : ''; ?>/>
441 <?php esc_html_e( 'By default files saved are static css/js, uncheck this option if your webserver doesn\'t properly handle the compression and expiry.', 'autoptimize' ); ?></label></td>
442 </tr>
443 <?php
444 $_min_excl_class = '';
445 if ( ! $conf->get( 'autoptimize_css_aggregate' ) && ! $conf->get( 'autoptimize_js_aggregate' ) ) {
446 $_min_excl_class = 'hidden';
447 }
448 ?>
449 <tr valign="top" id="min_excl_row" class="<?php echo $_min_excl_class; ?>">
450 <th scope="row"><?php esc_html_e( 'Minify excluded CSS and JS files?', 'autoptimize' ); ?></th>
451 <td><label class="cb_label"><input type="checkbox" name="autoptimize_minify_excluded" <?php echo $conf->get( 'autoptimize_minify_excluded' ) ? 'checked="checked" ' : ''; ?>/>
452 <?php esc_html_e( 'When aggregating JS or CSS, excluded files that are not minified (based on filename) are by default minified by Autoptimize despite being excluded. Uncheck this option if anything breaks despite excluding.', 'autoptimize' ); ?></label></td>
453 </tr>
454 <tr valign="top">
455 <th scope="row"><?php esc_html_e( 'Enable 404 fallbacks?', 'autoptimize' ); ?></th>
456 <td><label class="cb_label"><input type="checkbox" name="autoptimize_cache_fallback" <?php echo $conf->get( 'autoptimize_cache_fallback' ) ? 'checked="checked" ' : ''; ?>/>
457 <?php
458 // translators; just 2 opening and closing <code> tags.
459 printf( esc_html__( 'Sometimes Autoptimized JS/ CSS is referenced in cached HTML but is already removed, resulting in broken sites. With this option on, Autoptimize will try to redirect those not-found files to "fallback"-versions, keeping the page/ site somewhat intact. In some cases this will require extra web-server level configuration to ensure %1$swp-content/autoptimize_404_handler.php%2$s is set to handle 404\'s in %1$swp-content/cache/autoptimize%2$s.', 'autoptimize' ), '<code>', '</code>' );
460 ?>
461 </label></td>
462 </tr>
463 <tr valign="top">
464 <th scope="row"><?php esc_html_e( 'Also optimize for logged in editors/ administrators?', 'autoptimize' ); ?></th>
465 <td><label class="cb_label"><input type="checkbox" name="autoptimize_optimize_logged" <?php echo $conf->get( 'autoptimize_optimize_logged' ) ? 'checked="checked" ' : ''; ?>/>
466 <?php esc_html_e( 'By default Autoptimize is also active for logged on editors/ administrators, uncheck this option if you don\'t want Autoptimize to optimize when logged in e.g. to use a pagebuilder.', 'autoptimize' ); ?></label></td>
467 </tr>
468 <?php
469 if ( function_exists( 'is_checkout' ) || function_exists( 'is_cart' ) || function_exists( 'edd_is_checkout' ) || function_exists( 'wpsc_is_cart' ) || function_exists( 'wpsc_is_checkout' ) ) {
470 ?>
471 <tr valign="top" >
472 <th scope="row"><?php esc_html_e( 'Also optimize shop cart/ checkout?', 'autoptimize' ); ?></th>
473 <td><label class="cb_label"><input type="checkbox" name="autoptimize_optimize_checkout" <?php echo $conf->get( 'autoptimize_optimize_checkout' ) ? 'checked="checked" ' : ''; ?>/>
474 <?php esc_html_e( 'By default Autoptimize is also active on your shop\'s cart/ checkout, uncheck not to optimize those.', 'autoptimize' ); ?></label>
475 </td>
476 </tr>
477 <?php } ?>
478 <?php
479 if ( true === apply_filters( 'autoptimize_filter_enable_meta_ao_settings', true ) ) {
480 ?>
481 <tr valign="top">
482 <th scope="row"><?php esc_html_e( 'Enable configuration per post/ page?', 'autoptimize' ); ?></th>
483 <td><label class="cb_label"><input type="checkbox" name="autoptimize_enable_meta_ao_settings" <?php echo $conf->get( 'autoptimize_enable_meta_ao_settings' ) ? 'checked="checked" ' : ''; ?>/>
484 <?php esc_html_e( 'Add a "metabox" to the post/ page edit screen allowing different optimizations to be turned off on a per post/ page level?', 'autoptimize' ); ?></label></td>
485 </tr>
486 <?php } ?>
487 <tr valign="top">
488 <th scope="row"><?php esc_html_e( 'Disable extra compatibilty logic?', 'autoptimize' ); ?></th>
489 <td><label class="cb_label"><input type="checkbox" name="autoptimize_installed_before_compatibility" <?php echo $conf->get( 'autoptimize_installed_before_compatibility' ) ? 'checked="checked" ' : ''; ?>/>
490 <?php esc_html_e( 'Autoptimize applies extra "compatibiity logic" to prevent issues with JS optimization (for e.g. Gutenberg blocks, Revolution Slider, jQuery-heavy plugins, ...) but may sometimes be a bit too careful. If you have render-blocking JS issues, you can try disabling this logic here. Make sure to test your site thoroughly though!', 'autoptimize' ); ?></label></td>
491 </tr>
492 </table>
493 </li>
494
495 </ul>
496
497 <p class="submit">
498 <input type="submit" class="button-secondary" value="<?php esc_html_e( 'Save Changes', 'autoptimize' ); ?>" />
499 <input type="submit" class="button-primary" name="autoptimize_cache_clean" value="<?php esc_html_e( 'Save Changes and Empty Cache', 'autoptimize' ); ?>" />
500 </p>
501
502 </form>
503 </div>
504 <div id="autoptimize_admin_feed">
505 <?php if ( apply_filters( 'autoptimize_filter_show_partner_tabs', true ) ) { ?>
506 <div class="autoptimize_banner hidden">
507 <ul>
508 <?php
509 if ( $this->settings_screen_do_remote_http ) {
510 $ao_banner = get_transient( 'autoptimize_banner' );
511 if ( empty( $ao_banner ) ) {
512 $banner_resp = wp_remote_get( 'https://misc.optimizingmatters.com/autoptimize_news.html?ao_ver=' . AUTOPTIMIZE_PLUGIN_VERSION );
513 if ( ! is_wp_error( $banner_resp ) ) {
514 if ( '200' == wp_remote_retrieve_response_code( $banner_resp ) ) {
515 $ao_banner = wp_kses_post( wp_remote_retrieve_body( $banner_resp ) );
516 set_transient( 'autoptimize_banner', $ao_banner, WEEK_IN_SECONDS );
517 }
518 }
519 }
520 echo $ao_banner;
521 }
522 ?>
523 <li>
524 <?php
525 // translators: link to the AO FAQ.
526 printf( esc_html__( 'Need help? %1$sCheck out the FAQ here%2$s.', 'autoptimize' ), '<a href=\'https://wordpress.org/plugins/autoptimize/faq/\'>', '</a>' );
527 ?>
528 </li>
529 <li><?php esc_html_e( 'Happy with Autoptimize?', 'autoptimize' ); ?><br /><a href="<?php echo network_admin_url(); ?>plugin-install.php?tab=search&type=author&s=optimizingmatters"><?php esc_html_e( 'Try my other plugins!', 'autoptimize' ); ?></a></li>
530 </ul>
531 </div>
532 <?php } ?>
533 <div style="margin-left:10px;margin-top:-5px;">
534 <h2>
535 <?php esc_html_e( 'Autoptimize news', 'autoptimize' ); ?>
536 </h2>
537 <div id="futtta_feed">
538 <div id="autoptimizefeed">
539 <?php $this->get_futtta_feeds( 'http://feeds.feedburner.com/futtta_autoptimize' ); ?>
540 </div>
541 </div>
542 </div>
543 <?php if ( apply_filters( 'autoptimize_filter_show_partner_tabs', true ) ) { ?>
544 <div style="float:right;margin:50px 15px;"><a href="https://blog.futtta.be/2013/10/21/do-not-donate-to-me/" target="_blank"><img width="100px" height="85px" src="<?php echo plugins_url() . '/' . plugin_basename( dirname( __FILE__ ) ) . '/external/do_not_donate_smallest.png'; ?>" title="<?php esc_html_e( 'Do not donate for this plugin!', 'autoptimize' ); ?>"></a></div>
545 <?php } ?>
546 </div>
547 <script type="text/javascript">
548 jQuery(document).ready(function() {
549 check_ini_state();
550
551 jQuery('.autoptimize_banner').unslider({autoplay:true, delay:3500, infinite: false, arrows:{prev:'<a class="unslider-arrow prev"></a>', next:'<a class="unslider-arrow next"></a>'}}).fadeTo("slow",1).show();
552
553 jQuery( "#autoptimize_html" ).change(function() {
554 if (this.checked) {
555 jQuery(".html_sub:visible").fadeTo("fast",1);
556 } else {
557 jQuery(".html_sub:visible").fadeTo("fast",.33);
558 }
559 });
560
561 jQuery( "#autoptimize_js" ).change(function() {
562 if (this.checked) {
563 jQuery(".js_sub:visible").fadeTo("fast",1);
564 } else {
565 jQuery(".js_sub:visible").fadeTo("fast",.33);
566 }
567 });
568
569 jQuery( "#autoptimize_js_aggregate" ).change(function() {
570 if (this.checked && jQuery("#autoptimize_js").prop('checked')) {
571 jQuery( "#autoptimize_js_defer_not_aggregate" ).prop( 'checked', false ); // uncheck "defer not aggregate"
572 jQuery( ".js_aggregate_master:visible" ).fadeTo( 'slow', 1 ); // ungrey self
573 jQuery( ".js_aggregate" ).show( 'slow' ); // show sub-items
574 jQuery( ".js_not_aggregate_master:visible" ).fadeTo( 'slow', .33 ); // grey out "not aggregate"
575 jQuery( ".js_not_aggregate" ).hide( 'slow' ); // hide not aggregate sub-items
576 jQuery( "#min_excl_row" ).show(); // make sure "minify excluded" is visible
577 check_exclusions( "js", "on" );
578 } else {
579 jQuery( ".js_aggregate" ).hide( 'slow' ); // hide sub-itmes
580 jQuery( ".js_not_aggregate_master:visible" ).fadeTo( 'slow', 1 ); // un-grey-out "not aggregate"
581 if ( jQuery( "#autoptimize_css_aggregate" ).prop( 'checked' ) == false ) { // hide "minify excluded"
582 jQuery( "#min_excl_row" ).hide();
583 }
584 check_exclusions( "js", "off" );
585 }
586 });
587
588 jQuery( "#autoptimize_js_defer_not_aggregate" ).change(function() {
589 if (this.checked && jQuery("#autoptimize_js").prop('checked')) {
590 jQuery( "#autoptimize_js_aggregate" ).prop( 'checked', false ); // uncheck "aggregate JS"
591 jQuery( ".js_not_aggregate_master:visible" ).fadeTo( 'slow', 1 ); // ungrey self
592 jQuery( ".js_not_aggregate" ).show( 'slow'); // show sub-items
593 jQuery( ".js_aggregate_master:visible" ).fadeTo( 'slow', .33 ); // grey out "aggregate"
594 jQuery( ".js_aggregate" ).hide( 'slow' ); // hide aggregate sub-items
595 check_exclusions( "js", "off" );
596 } else {
597 jQuery( ".js_not_aggregate" ).hide( 'slow' ); // hide sub-items
598 jQuery( ".js_aggregate_master:visible" ).fadeTo( 'slow', 1 ); // un-grey-out "aggregate"
599 }
600 });
601
602 jQuery( "#autoptimize_css" ).change(function() {
603 if (this.checked) {
604 jQuery(".css_sub:visible").fadeTo("fast",1);
605 } else {
606 jQuery(".css_sub:visible").fadeTo("fast",.33);
607 }
608 });
609
610 jQuery( "#autoptimize_css_aggregate" ).change(function() {
611 if (this.checked && jQuery("#autoptimize_css").prop('checked')) {
612 jQuery(".css_aggregate:visible").fadeTo("fast",1);
613 jQuery( "#min_excl_row" ).show();
614 check_exclusions( "css", "on" );
615 } else {
616 jQuery(".css_aggregate:visible").fadeTo("fast",.33);
617 if ( jQuery( "#autoptimize_js_aggregate" ).prop('checked') == false ) {
618 jQuery( "#min_excl_row" ).hide();
619 }
620 check_exclusions( "css", "off" );
621 }
622 });
623
624 jQuery( "#autoptimize_css_inline" ).change(function() {
625 if (this.checked) {
626 jQuery("#autoptimize_css_defer").prop("checked",false);
627 jQuery("#autoptimize_css_defer_inline").hide("slow");
628 }
629 });
630
631 jQuery( "#autoptimize_css_defer" ).change(function() {
632 if (this.checked) {
633 jQuery("#autoptimize_css_inline").prop("checked",false);
634 jQuery("#autoptimize_css_defer_inline").show("slow");
635 } else {
636 jQuery("#autoptimize_css_defer_inline").hide("slow");
637 }
638 });
639
640 jQuery( "#autoptimize_enable_site_config" ).change(function() {
641 if (this.checked) {
642 jQuery("li.itemDetail:not(.multiSite)").fadeTo("fast",.33);
643 } else {
644 jQuery("li.itemDetail:not(.multiSite)").fadeTo("fast",1);
645 }
646 });
647 })
648
649 // validate cdn_url.
650 var cdn_url=document.getElementById("cdn_url");
651 cdn_url_baseCSS=cdn_url.style.cssText;
652 if ("validity" in cdn_url) {
653 jQuery("#cdn_url").focusout(function (event) {
654 if (cdn_url.validity.valid) {
655 cdn_url.style.cssText=cdn_url_baseCSS;
656 } else {
657 cdn_url.style.cssText=cdn_url_baseCSS+"border:1px solid #f00;color:#f00;box-shadow: 0 0 2px #f00;";
658 }});
659 }
660
661 function check_ini_state() {
662 if (!jQuery("#autoptimize_css_defer").prop('checked')) {
663 jQuery("#autoptimize_css_defer_inline").hide();
664 }
665 if (!jQuery("#autoptimize_html").prop('checked')) {
666 jQuery(".html_sub:visible").fadeTo('fast',.33);
667 }
668 if (!jQuery("#autoptimize_css").prop('checked')) {
669 jQuery(".css_sub:visible").fadeTo('fast',.33);
670 }
671 if (!jQuery("#autoptimize_css_aggregate").prop('checked')) {
672 jQuery(".css_aggregate:visible").fadeTo('fast',.33);
673 }
674 if (jQuery("#autoptimize_js_aggregate").prop('checked')) {
675 jQuery( ".js_aggregate" ).show( 'fast' );
676 jQuery( ".js_not_aggregate_master:visible" ).fadeTo( 'fast', .33 );
677 }
678 if (jQuery("#autoptimize_js_defer_not_aggregate").prop('checked')) {
679 jQuery( ".js_not_aggregate" ).show( 'fast' );
680 jQuery( ".js_aggregate_master:visible" ).fadeTo( 'fast', .33 );
681 }
682 if (jQuery("#autoptimize_enable_site_config").prop('checked')) {
683 jQuery("li.itemDetail:not(.multiSite)").fadeTo('fast',.33);
684 }
685 if (!jQuery("#autoptimize_js").prop('checked')) {
686 jQuery(".js_sub:visible").fadeTo('fast',.33);
687 }
688 }
689
690 function check_exclusions( what, state ) {
691 exclusion_node = 'input[name="autoptimize_' + what + '_exclude"]';
692 current_exclusion = jQuery( exclusion_node ).val();
693
694 if ( what == "js" ) {
695 default_exclusion = ", wp-includes/js/dist/, wp-includes/js/tinymce/, js/jquery/jquery.min.js";
696 } else if ( what == "css") {
697 default_exclusion = ", admin-bar.min.css, dashicons.min.css, wp-content/cache/, wp-content/uploads/";
698 }
699
700 default_in_current = current_exclusion.indexOf(default_exclusion);
701
702 if ( state == "on" && default_in_current == -1 ) {
703 jQuery( exclusion_node ).val( current_exclusion + default_exclusion );
704 } else if ( state = "off" && current_exclusion == default_exclusion ) {
705 jQuery( exclusion_node ).val( "" );
706 } else if ( state = "off" && default_in_current != -1 ) {
707 new_exclusion = current_exclusion.substring( 0, default_in_current) + current_exclusion.substring( default_in_current + default_exclusion.length, current_exclusion.length );
708 jQuery( exclusion_node ).val( new_exclusion );
709 }
710 }
711 </script>
712 </div>
713
714 <?php
715 }
716
717 public function addmenu()
718 {
719 $_my_name = apply_filters( 'autoptimize_filter_settings_is_pro', false ) ? esc_html__( 'Autoptimize Pro', 'autoptimize' ) : esc_html__( 'Autoptimize', 'autoptimize' );
720
721 global $title;
722 if ( empty( $title ) && true === autoptimizeUtils::is_ao_settings() ) {
723 $title = $_my_name;
724 }
725
726 if ( is_multisite() && is_network_admin() && autoptimizeOptionWrapper::is_ao_active_for_network() ) {
727 // multisite, network admin, ao network activated: add normal settings page at network level.
728 $hook = add_submenu_page( 'settings.php', esc_html__( 'Autoptimize Options', 'autoptimize' ), $_my_name, 'manage_network_options', 'autoptimize', array( $this, 'show_config' ) );
729 } elseif ( is_multisite() && ! is_network_admin() && autoptimizeOptionWrapper::is_ao_active_for_network() && 'on' !== autoptimizeOptionWrapper::get_option( 'autoptimize_enable_site_config' ) ) {
730 // multisite, ao network activated, not network admin so site specific settings, but "autoptimize_enable_site_config" is off: show "sorry, ask network admin" message iso options.
731 $hook = add_options_page( esc_html__( 'Autoptimize Options', 'autoptimize' ), $_my_name, 'manage_options', 'autoptimize', array( $this, 'show_network_message' ) );
732 } else {
733 // default: show normal options page if not multisite, if multisite but not network activated, if multisite and network activated and "autoptimize_enable_site_config" is on.
734 $hook = add_options_page( esc_html__( 'Autoptimize Options', 'autoptimize' ), $_my_name, 'manage_options', 'autoptimize', array( $this, 'show_config' ) );
735 }
736
737 add_action( 'admin_print_scripts-' . $hook, array( $this, 'autoptimize_admin_scripts' ) );
738 add_action( 'admin_print_styles-' . $hook, array( $this, 'autoptimize_admin_styles' ) );
739 }
740
741 public function autoptimize_admin_scripts()
742 {
743 wp_enqueue_script( 'unslider', plugins_url( '/external/js/unslider.min.js', __FILE__ ), array( 'jquery' ), AUTOPTIMIZE_PLUGIN_VERSION, true );
744 }
745
746 public function autoptimize_admin_styles()
747 {
748 wp_enqueue_style( 'unslider', plugins_url( '/external/js/unslider.css', __FILE__ ), null, AUTOPTIMIZE_PLUGIN_VERSION );
749 wp_enqueue_style( 'unslider-dots', plugins_url( '/external/js/unslider-dots.css', __FILE__ ), null, AUTOPTIMIZE_PLUGIN_VERSION );
750 }
751
752 public function registersettings() {
753 register_setting( 'autoptimize', 'autoptimize_html' );
754 register_setting( 'autoptimize', 'autoptimize_html_keepcomments' );
755 register_setting( 'autoptimize', 'autoptimize_html_minify_inline' );
756 register_setting( 'autoptimize', 'autoptimize_enable_site_config' );
757 register_setting( 'autoptimize', 'autoptimize_js' );
758 register_setting( 'autoptimize', 'autoptimize_js_aggregate' );
759 register_setting( 'autoptimize', 'autoptimize_js_defer_not_aggregate' );
760 register_setting( 'autoptimize', 'autoptimize_js_defer_inline' );
761 register_setting( 'autoptimize', 'autoptimize_js_exclude' );
762 register_setting( 'autoptimize', 'autoptimize_js_trycatch' );
763 register_setting( 'autoptimize', 'autoptimize_js_justhead' );
764 register_setting( 'autoptimize', 'autoptimize_js_forcehead' );
765 register_setting( 'autoptimize', 'autoptimize_js_include_inline' );
766 register_setting( 'autoptimize', 'autoptimize_css' );
767 register_setting( 'autoptimize', 'autoptimize_css_aggregate' );
768 register_setting( 'autoptimize', 'autoptimize_css_exclude' );
769 register_setting( 'autoptimize', 'autoptimize_css_justhead' );
770 register_setting( 'autoptimize', 'autoptimize_css_datauris' );
771 register_setting( 'autoptimize', 'autoptimize_css_defer' );
772 register_setting( 'autoptimize', 'autoptimize_css_defer_inline' );
773 register_setting( 'autoptimize', 'autoptimize_css_inline' );
774 register_setting( 'autoptimize', 'autoptimize_css_include_inline' );
775 register_setting( 'autoptimize', 'autoptimize_cdn_url' );
776 register_setting( 'autoptimize', 'autoptimize_cache_clean' );
777 register_setting( 'autoptimize', 'autoptimize_cache_nogzip' );
778 register_setting( 'autoptimize', 'autoptimize_optimize_logged' );
779 register_setting( 'autoptimize', 'autoptimize_optimize_checkout' );
780 register_setting( 'autoptimize', 'autoptimize_minify_excluded' );
781 register_setting( 'autoptimize', 'autoptimize_cache_fallback' );
782 register_setting( 'autoptimize', 'autoptimize_enable_meta_ao_settings' );
783 register_setting( 'autoptimize', 'autoptimize_installed_before_compatibility' );
784 }
785
786 public function setmeta( $links, $file = null )
787 {
788 // Inspired on http://wpengineer.com/meta-links-for-wordpress-plugins/.
789 // Do it only once - saves time.
790 static $plugin;
791 if ( empty( $plugin ) ) {
792 $plugin = plugin_basename( AUTOPTIMIZE_PLUGIN_DIR . 'autoptimize.php' );
793 }
794
795 if ( null === $file ) {
796 // 2.7 and lower.
797 $settings_link = sprintf( '<a href="options-general.php?page=autoptimize">%s</a>', esc_html__( 'Settings' ) );
798 array_unshift( $links, $settings_link );
799 } else {
800 // 2.8 and higher.
801 // If it's us, add the link.
802 if ( $file === $plugin ) {
803 $newlink = array( sprintf( '<a href="options-general.php?page=autoptimize">%s</a>', esc_html__( 'Settings' ) ) );
804 $links = array_merge( $links, $newlink );
805 }
806 }
807
808 return $links;
809 }
810
811 /**
812 * Provides the default options.
813 *
814 * @return array
815 */
816 public static function get_defaults()
817 {
818 static $config = array(
819 'autoptimize_html' => 1,
820 'autoptimize_html_keepcomments' => 0,
821 'autoptimize_html_minify_inline' => 0,
822 'autoptimize_enable_site_config' => 1,
823 'autoptimize_js' => 1,
824 'autoptimize_js_aggregate' => 0,
825 'autoptimize_js_defer_not_aggregate' => 1,
826 'autoptimize_js_defer_inline' => 1,
827 'autoptimize_js_exclude' => '',
828 'autoptimize_js_trycatch' => 0,
829 'autoptimize_js_justhead' => 0,
830 'autoptimize_js_include_inline' => 0,
831 'autoptimize_js_forcehead' => 0,
832 'autoptimize_css' => 1,
833 'autoptimize_css_aggregate' => 0,
834 'autoptimize_css_exclude' => '',
835 'autoptimize_css_justhead' => 0,
836 'autoptimize_css_include_inline' => 0,
837 'autoptimize_css_defer' => 0,
838 'autoptimize_css_defer_inline' => '',
839 'autoptimize_css_inline' => 0,
840 'autoptimize_css_datauris' => 0,
841 'autoptimize_cdn_url' => '',
842 'autoptimize_cache_nogzip' => 1,
843 'autoptimize_optimize_logged' => 1,
844 'autoptimize_optimize_checkout' => 0,
845 'autoptimize_minify_excluded' => 1,
846 'autoptimize_cache_fallback' => 1,
847 'autoptimize_enable_meta_ao_settings' => 1,
848 'autoptimize_installed_before_compatibility' => 0,
849 );
850
851 return $config;
852 }
853
854 /**
855 * Returns default option values for autoptimizeExtra.
856 *
857 * @return array
858 */
859 public static function get_ao_extra_default_options()
860 {
861 $defaults = array(
862 'autoptimize_extra_checkbox_field_1' => '0',
863 'autoptimize_extra_checkbox_field_0' => '0',
864 'autoptimize_extra_radio_field_4' => '1',
865 'autoptimize_extra_text_field_2' => '',
866 'autoptimize_extra_text_field_3' => '',
867 'autoptimize_extra_text_field_7' => '',
868 'autoptimize_extra_checkbox_field_8' => '0',
869 );
870
871 return $defaults;
872 }
873
874 /**
875 * Returns default option values for autoptimizeExtra.
876 *
877 * @return array
878 */
879 public static function get_ao_imgopt_default_options()
880 {
881 $defaults = array(
882 'autoptimize_imgopt_checkbox_field_1' => '0', // imgopt off.
883 'autoptimize_imgopt_select_field_2' => '2', // quality glossy.
884 'autoptimize_imgopt_checkbox_field_3' => '0', // lazy load off.
885 'autoptimize_imgopt_checkbox_field_4' => '0', // webp off (might be removed).
886 'autoptimize_imgopt_text_field_5' => '', // lazy load exclusions empty.
887 'autoptimize_imgopt_text_field_6' => '', // optimization exclusions empty.
888 'autoptimize_imgopt_number_field_7' => '2', // lazy load from nth image (0 = lazyload all).
889 );
890 return $defaults;
891 }
892
893 /**
894 * Returns preload JS onload handler.
895 *
896 * @param string $media media attribute value the JS to use.
897 *
898 * @return string
899 */
900 public static function get_ao_css_preload_onload( $media = 'all' )
901 {
902 $preload_onload = apply_filters( 'autoptimize_filter_css_preload_onload', "this.onload=null;this.media='" . $media . "';" );
903 return $preload_onload;
904 }
905
906 public function get( $key )
907 {
908 if ( ! is_array( $this->config ) ) {
909 // Default config.
910 $config = self::get_defaults();
911
912 // Override with user settings.
913 foreach ( array_keys( $config ) as $name ) {
914 $conf = autoptimizeOptionWrapper::get_option( $name );
915 if ( false !== $conf ) {
916 // It was set before!
917 $config[ $name ] = $conf;
918 }
919 }
920
921 // Save for next call.
922 $this->config = apply_filters( 'autoptimize_filter_get_config', $config );
923 }
924
925 if ( isset( $this->config[ $key ] ) ) {
926 return $this->config[ $key ];
927 }
928
929 return false;
930 }
931
932 private function get_futtta_feeds( $url ) {
933 if ( $this->settings_screen_do_remote_http ) {
934 $rss = fetch_feed( $url );
935 $maxitems = 0;
936
937 if ( ! is_wp_error( $rss ) ) {
938 $maxitems = $rss->get_item_quantity( 7 );
939 $rss_items = $rss->get_items( 0, $maxitems );
940 }
941 ?>
942 <ul>
943 <?php if ( 0 == $maxitems ) : ?>
944 <li><?php esc_html_e( 'No items', 'autoptimize' ); ?></li>
945 <?php else : ?>
946 <?php foreach ( $rss_items as $item ) : ?>
947 <li>
948 <a href="<?php echo esc_url( $item->get_permalink() ); ?>"
949 <?php // translators: the variable contains a date. ?>
950 title="<?php printf( esc_html__( 'Posted %s', 'autoptimize' ), $item->get_date( 'j F Y | g:i a' ) ); ?>">
951 <?php echo esc_html( $item->get_title() ); ?>
952 </a>
953 </li>
954 <?php endforeach; ?>
955 <?php endif; ?>
956 </ul>
957 <?php
958 }
959 }
960
961 static function ao_admin_tabs()
962 {
963 // based on http://wordpress.stackexchange.com/a/58826 .
964 $tabs = apply_filters( 'autoptimize_filter_settingsscreen_tabs', array( 'autoptimize' => esc_html__( 'JS, CSS &amp; HTML', 'autoptimize' ) ) );
965 $tab_content = '';
966 $tabs_count = count( $tabs );
967 if ( $tabs_count > 1 ) {
968 if ( isset( $_GET['page'] ) ) {
969 $current_id = $_GET['page'];
970 } else {
971 $current_id = 'autoptimize';
972 }
973 $tab_content .= '<h2 class="nav-tab-wrapper">';
974 foreach ( $tabs as $tab_id => $tab_name ) {
975 if ( $current_id == $tab_id ) {
976 $class = ' nav-tab-active';
977 } else {
978 $class = '';
979 }
980 $tab_content .= '<a class="nav-tab' . $class . '" href="?page=' . $tab_id . '">' . $tab_name . '</a>';
981 }
982 $tab_content .= '</h2>';
983 } else {
984 $tab_content = '<hr/>';
985 }
986
987 return $tab_content;
988 }
989
990 /**
991 * Returns true if in admin (and not in admin-ajax.php!)
992 *
993 * @return bool
994 */
995 public static function is_admin_and_not_ajax()
996 {
997 return ( is_admin() && ! self::doing_ajax() );
998 }
999
1000 /**
1001 * Returns true if doing ajax.
1002 *
1003 * @return bool
1004 */
1005 protected static function doing_ajax()
1006 {
1007 if ( function_exists( 'wp_doing_ajax' ) ) {
1008 return wp_doing_ajax();
1009 }
1010 return ( defined( 'DOING_AJAX' ) && DOING_AJAX );
1011 }
1012
1013 /**
1014 * Returns true menu or tab is to be shown.
1015 *
1016 * @return bool
1017 */
1018 public static function should_show_menu_tabs() {
1019 if ( ! is_multisite() || is_network_admin() || 'on' === autoptimizeOptionWrapper::get_option( 'autoptimize_enable_site_config' ) || false === autoptimizeOptionWrapper::is_ao_active_for_network() ) {
1020 return true;
1021 } else {
1022 return false;
1023 }
1024 }
1025
1026 /**
1027 * Returns the post meta AO settings for reuse in different optimizers.
1028 *
1029 * @param string $optim What optimization we need meta setting for.
1030 *
1031 * @return bool
1032 */
1033 public static function get_post_meta_ao_settings( $optim ) {
1034 if ( ! autoptimizeConfig::is_ao_meta_settings_active() ) {
1035 // Per page/post settings not active, so always return true (as in; can be optimized).
1036 if ( in_array( $optim, apply_filters( 'autoptimize_filter_meta_inactive_return_false_for', array( 'ao_post_preload' ) ) ) ) {
1037 // but make sure to return false for text input.
1038 return false;
1039 }
1040 return true;
1041 }
1042
1043 static $_meta_value = null;
1044 if ( null === $_meta_value ) {
1045 global $wp_query;
1046 if ( isset( $wp_query ) ) {
1047 $_meta_value = get_post_meta( get_the_ID(), 'ao_post_optimize', true );
1048 } else {
1049 $_meta_value = false;
1050 }
1051 }
1052
1053 // If autoptimize_post_optimize !== 'on' (except for ao_post_preload, which can have other values) then always return false as all is off.
1054 // fixme: need unit tests to ensure below logic is sane!
1055 if ( empty( $_meta_value ) || ! is_array( $_meta_value ) ) {
1056 // no metabox values so all optimizations are a go.
1057 if ( in_array( $optim, apply_filters( 'autoptimize_filter_meta_optim_nonbool', array( 'ao_post_preload' ) ) ) ) {
1058 // but make sure to return false for text input.
1059 return false;
1060 }
1061 return true;
1062 } else if ( array_key_exists( 'ao_post_optimize', $_meta_value ) && 'on' !== $_meta_value['ao_post_optimize'] ) {
1063 // ao entirely off for this page.
1064 return false;
1065 } else if ( in_array( $optim, apply_filters( 'autoptimize_filter_meta_optim_with_filters', array() ) ) ) {
1066 // if an $optim is registered as having a filter, apply filter and return that (default false).
1067 return apply_filters( 'autoptimize_filter_meta_filtered_optim', false, $optim, $_meta_value );
1068 } else if ( array_key_exists( $optim, $_meta_value ) && empty( $_meta_value[ $optim ] ) ) {
1069 // sub-optimization off for this page.
1070 return false;
1071 } else if ( array_key_exists( $optim, $_meta_value ) && 'on' === $_meta_value[ $optim ] ) {
1072 // sub-optimization is explictly on.
1073 return true;
1074 } else if ( array_key_exists( $optim, $_meta_value ) && in_array( $optim, array( 'ao_post_preload' ) ) && ! empty( $_meta_value[ $optim ] ) ) {
1075 // a non-bool metabox optimization (currently only preload field), return value instead of bool.
1076 return $_meta_value[ $optim ];
1077 } else if ( in_array( $optim, array( 'ao_post_preload' ) ) && ( ! array_key_exists( $optim, $_meta_value ) || empty( $_meta_value[ $optim ] ) ) ) {
1078 // a non-bool metabox optimization not found or empty, so returning false.
1079 return false;
1080 } else {
1081 // when in doubt "go" for optimization, but this should never happen?
1082 if ( defined( 'WP_DEBUG' ) && WP_DEBUG ) {
1083 error_log( 'AO metabox logic fallback; well, how did I get here? Maybe this helps: looking for ' . $optim . ' in ' . json_encode( $_meta_value ) );
1084 }
1085 return true;
1086 }
1087 }
1088
1089 /**
1090 * Are the post meta AO settings active (default: no)?
1091 *
1092 * @return bool
1093 */
1094 public static function is_ao_meta_settings_active() {
1095 static $_meta_settings_active = null;
1096
1097 if ( null === $_meta_settings_active ) {
1098 $_meta_settings_active = apply_filters( 'autoptimize_filter_enable_meta_ao_settings', autoptimizeOptionWrapper::get_option( 'autoptimize_enable_meta_ao_settings', '1' ) );
1099 }
1100
1101 return $_meta_settings_active;
1102 }
1103 }
1104