PluginProbe
Document Gallery / 3.0.0-beta
Document Gallery v3.0.0-beta
trunk 0.8 0.8.5 1.0 1.0.1 1.0.2 1.0.3 1.0.4 1.1 1.2 1.2.1 1.3 1.3.1 1.4 1.4.1 1.4.2 1.4.3 2.0 2.0.1 2.0.10 2.0.2 2.0.3 2.0.4 2.0.5 2.0.6 All 94 releases
document-gallery / document-gallery.php

document-gallery.php in Document Gallery 3.0.0-beta, at document-gallery.php

331 lines 10.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 defined('WPINC') OR exit;
3
4 /*
5 Plugin Name: Document Gallery
6 Plugin URI: http://wordpress.org/extend/plugins/document-gallery/
7 Description: Display non-images (and images) in gallery format on a page or post with the [dg] shortcode.
8 Version: 3.0.0-beta
9 Author: Dan Rossiter
10 Author URI: http://danrossiter.org/
11 License: GPLv2
12 Text Domain: document-gallery
13 */
14
15 define('DG_VERSION', '3.0.0-beta');
16
17 // define helper paths & URLs
18 define('DG_BASENAME', plugin_basename(__FILE__));
19 define('DG_URL', plugin_dir_url(__FILE__));
20 define('DG_PATH', plugin_dir_path(__FILE__));
21 define('DG_WPINC_PATH', ABSPATH . WPINC . '/');
22 define('DG_WPADMIN_PATH', ABSPATH . 'wp-admin/');
23
24 // init DG options for use throughout plugin
25 global $dg_options;
26 define('DG_OPTION_NAME', 'document_gallery');
27 $dg_options = get_option(DG_OPTION_NAME, null);
28
29 // DG general utility functions
30 include_once DG_PATH . 'inc/class-util.php';
31
32 // logging functionality
33 include_once DG_PATH . 'inc/class-logger.php';
34
35 // handle activation, updates, and uninstallation
36 include_once DG_PATH . 'inc/class-setup.php';
37 register_activation_hook(__FILE__, array('DG_Setup', 'activate'));
38 add_action('wpmu_new_blog', array('DG_Setup','activateNewBlog'));
39 register_uninstall_hook(__FILE__, array('DG_Setup', 'uninstall'));
40 DG_Setup::maybeUpdate();
41
42 // validate options if desired
43 if ($dg_options['validation']) {
44 add_action('init', array('DocumentGallery', 'addValidation'));
45 }
46
47 // I18n
48 add_action('plugins_loaded', array('DocumentGallery', 'loadTextDomain'));
49
50 // cleanup cached data when thumbed attachment deleted
51 include_once DG_PATH . 'inc/class-thumber.php';
52 add_action('delete_attachment', array('DG_Thumber', 'deleteThumbMeta'));
53
54 if (is_admin()) {
55 // admin house keeping
56 include_once DG_PATH . 'admin/class-admin.php';
57
58 // add links to plugin index
59 add_filter('plugin_action_links_' . DG_BASENAME, array('DG_Admin', 'addSettingsLink'));
60 add_filter('plugin_row_meta', array('DG_Admin', 'addDonateLink'), 10, 2);
61
62 // build options page
63 add_action('admin_menu', array('DG_Admin', 'addAdminPage'));
64
65 // add meta box for managing thumbnail generation to attachment Edit Media page
66 add_action('add_meta_boxes', array('DG_Admin', 'addMetaBox'));
67 add_action('wp_ajax_dg_upload_thumb', array('DG_Admin', 'saveMetaBox'));
68
69 if (DG_Admin::doRegisterSettings()) {
70 add_action('admin_init', array('DG_Admin', 'registerSettings'));
71 }
72 } else {
73 // styling for gallery
74 if (apply_filters('dg_use_default_gallery_style', true )) {
75 add_action('wp_enqueue_scripts', array('DocumentGallery', 'enqueueGalleryStyle'));
76 }
77 add_action('wp_print_scripts', array('DocumentGallery', 'printCustomStyle'));
78 }
79
80 // adds 'dg' shortcode
81 add_shortcode('dg', array('DocumentGallery', 'doShortcode'));
82
83 /**
84 * DocumentGallery wraps basic functionality to setup the plugin.
85 *
86 * @author drossiter
87 */
88 class DocumentGallery {
89
90 /*==========================================================================
91 * THE SHORTCODE
92 *=========================================================================*/
93
94 /**
95 * Takes values passed from attributes and returns sutable HTML to represent
96 * all valid attachments requested.
97 *
98 * @param multitype:string $atts Arguments from the user.
99 * @return string HTML for the Document Gallery.
100 */
101 public static function doShortcode($atts) {
102 include_once 'inc/class-gallery.php';
103
104 $start = microtime(true);
105 $gallery = (string)new DG_Gallery($atts);
106 DG_Logger::writeLog(DG_LogLevel::Detail, 'Generation Time: ' . sprintf('%.2f', (microtime(true) - $start)) . ' s');
107
108 return $gallery;
109 }
110
111 /**
112 * Enqueue standard DG CSS.
113 */
114 public static function enqueueGalleryStyle() {
115 wp_enqueue_style('document-gallery', DG_URL . 'assets/css/style.css', null, DG_VERSION);
116 }
117
118 /**
119 * Prints user's custom CSS.
120 */
121 public static function printCustomStyle() {
122 global $dg_options;
123
124 if (!empty($dg_options['css']['minified'])) {
125 echo "<style type='text/css'>{$dg_options['css']['minified']}</style>" . PHP_EOL;
126 }
127 }
128
129 /*==========================================================================
130 * I18n
131 *=========================================================================*/
132
133 /**
134 * Loads language files into WP core.
135 */
136 public static function loadTextDomain() {
137 load_plugin_textdomain('document-gallery', false, dirname(DG_BASENAME) . '/languages/');
138 }
139
140 /*==========================================================================
141 * HELPER FUNCTIONS
142 *=========================================================================*/
143
144 /**
145 * @param int $blog ID of the blog to be retrieved in multisite env.
146 * @return multitype:unknown Options for the blog.
147 */
148 public static function getOptions($blog = null) {
149 global $dg_options;
150 return is_null($blog)
151 ? $dg_options
152 : get_blog_option($blog, DG_OPTION_NAME, null);
153 }
154
155 /**
156 * @param multitype:unknown $options
157 * @param int $blog ID of the blog to be set in multisite env.
158 */
159 public static function setOptions($options, $blog = null) {
160 if (is_null($blog)) {
161 global $dg_options;
162 update_option(DG_OPTION_NAME, $options);
163 $dg_options = $options;
164 } else {
165 update_blog_option($blog, DG_OPTION_NAME, $options);
166 }
167 }
168
169 /**
170 * @param int $blog ID of the blog to be deleted in multisite env.
171 */
172 public static function deleteOptions($blog = null) {
173 if (is_null($blog)) {
174 delete_option(DG_OPTION_NAME);
175 } else {
176 delete_blog_option($blog, DG_OPTION_NAME);
177 }
178 }
179
180 /**
181 * Adds hook to validate DG options every time save is attempted.
182 */
183 public static function addValidation() {
184 add_filter('pre_update_option_' . DG_OPTION_NAME, array('DocumentGallery', 'validateOptionsStructure'), 10, 2);
185 }
186
187 /**
188 * Checks whether the given options match the option schema.
189 * @param multivar $new The new options to be validated.
190 * @param multivar $old The old options.
191 * @return array The options to be saved.
192 */
193 public static function validateOptionsStructure($new, $old) {
194 if (self::isValidOptionsStructure($new)) {
195 $ret = $new;
196 } else {
197 $ret = $old;
198 DG_Logger::writeLog(DG_LogLevel::Error, 'Attempted to save invalid options.' . PHP_EOL . print_r($new, true), true, true);
199 }
200
201 return $ret;
202 }
203
204 /**
205 * @param multivar|unknown $o The options structure to validate.
206 * @param multivar $schema The schema to validate against (note that only keys matter -- non-array values are ignored).
207 * @return bool Whether the given options structure matches the schema.
208 */
209 private static function isValidOptionsStructure($o, $schema = null) {
210 if (is_null($schema)) {
211 $schema = DG_Setup::getDefaultOptions(true);
212 }
213
214 // simple checks first
215 $valid = is_array($o) && (count($schema) === count($o));
216
217 if ($valid) {
218 foreach ($schema as $sk => $sv) {
219 $valid = array_key_exists($sk, $o);
220 if (is_array($sv) && !empty($sv)) {
221 $valid = $valid && self::isValidOptionsStructure($o[$sk], $sv);
222 }
223
224 if (!$valid) {
225 break;
226 }
227 }
228 }
229
230 return $valid;
231 }
232
233 /**
234 * Function takes a GMT timestamp and returns a date/time string in the
235 * current timezone and WP format.
236 * @param int $timestamp The GMT timestamp to translate.
237 * @return string The local time in the WP date/time format.
238 */
239 public static function localDateTimeFromTimestamp($timestamp) {
240 static $gmt_offet = null;
241 static $wp_date_format = null;
242 static $wp_time_format = null;
243 if (is_null($gmt_offet)) {
244 $gmt_offet = get_option('gmt_offset');
245 $wp_date_format = get_option('date_format');
246 $wp_time_format = get_option('time_format');
247 }
248
249 return '<span class="nowrap">'.date_i18n($wp_date_format, $timestamp + $gmt_offet * 3600).'</span> <span class="nowrap">'.date_i18n($wp_time_format, $timestamp + $gmt_offet * 3600).'</span>';
250 }
251
252 /**
253 * Compiles any custom CSS, including minification and escaping HTML.
254 * @param string $custom The custom CSS to compile.
255 * @return string Compiled CSS.
256 */
257 public static function compileCustomCss($custom) {
258 $css = str_replace('&gt;', '>', esc_html($custom));
259 return self::minifyCss($css);
260 }
261
262 /**
263 * Minifies CSS string.
264 * Source: http://stackoverflow.com/a/15195752/866618
265 */
266 private static function minifyCss($css) {
267 # remove comments first (simplifies the other regex)
268 $re1 = <<<EOS
269 (?sx)
270 # quotes
271 (
272 "(?:[^"\\\\]++|\\.)*+"
273 | '(?:[^'\\\\]++|\\.)*+'
274 )
275 |
276 # comments
277 /\* (?> .*? \*/ )
278 EOS;
279
280 $re2 = <<<EOS
281 (?six)
282 # quotes
283 (
284 "(?:[^"\\\\]++|\\.)*+"
285 | '(?:[^'\\\\]++|\\.)*+'
286 )
287 |
288 # ; before } (and the spaces after it while we're here)
289 \s*+ ; \s*+ ( } ) \s*+
290 |
291 # all spaces around meta chars/operators
292 \s*+ ( [*$~^|]?+= | [{};,>~+-] | !important\b ) \s*+
293 |
294 # spaces right of ( [ :
295 ( [[(:] ) \s++
296 |
297 # spaces left of ) ]
298 \s++ ( [])] )
299 |
300 # spaces left (and right) of :
301 \s++ ( : ) \s*+
302 # but not in selectors: not followed by a {
303 (?!
304 (?>
305 [^{}"']++
306 | "(?:[^"\\\\]++|\\.)*+"
307 | '(?:[^'\\\\]++|\\.)*+'
308 )*+
309 {
310 )
311 |
312 # spaces at beginning/end of string
313 ^ \s++ | \s++ \z
314 |
315 # double spaces to single
316 (\s)\s+
317 EOS;
318
319 $css = preg_replace("%$re1%", '$1', $css);
320 return preg_replace("%$re2%", '$1$2$3$4$5$6$7', $css);
321 }
322
323 /**
324 * Blocks instantiation. All functions are static.
325 */
326 private function __construct() {
327
328 }
329 }
330
331 ?>