| @@ -3,12 +3,12 @@ | ||
| 3 | 3 | Plugin Name: Edit Flow |
| 4 | 4 | Plugin URI: http://editflow.org/ |
| 5 | 5 | Description: Remixing the WordPress admin for better editorial workflow options. |
| 6 | 6 | Author: Daniel Bachhuber, Scott Bressler, Mohammad Jangda, Automattic, and others |
| 7 | -Version: 0.8 | |
| 7 | +Version: 0.9.2 | |
| 8 | 8 | Author URI: http://editflow.org/ |
| 9 | 9 | |
| 10 | -Copyright 2009-2013 Mohammad Jangda, Daniel Bachhuber, et al. | |
| 10 | +Copyright 2009-2019 Mohammad Jangda, Daniel Bachhuber, Automattic, et al. | |
| 11 | 11 | |
| 12 | 12 | GNU General Public License, Free Software Foundation <http://creativecommons.org/licenses/GPL/2.0/> |
| 13 | 13 | |
| 14 | 14 | This program is free software; you can redistribute it and/or modify |
| @@ -26,10 +26,28 @@ | ||
| 26 | 26 | Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
| 27 | 27 | |
| 28 | 28 | */ |
| 29 | 29 | |
| 30 | +/** | |
| 31 | + * Print admin notice regarding having an old version of PHP. | |
| 32 | + * | |
| 33 | + * @since 0.9 | |
| 34 | + */ | |
| 35 | +function _ef_print_php_version_admin_notice() { | |
| 36 | + ?> | |
| 37 | + <div class="notice notice-error"> | |
| 38 | + <p><?php esc_html_e( 'Edit Flow requires PHP 5.6+. Please contact your host to update your PHP version.', 'edit-flow' ); ?></p> | |
| 39 | + </div> | |
| 40 | + <?php | |
| 41 | +} | |
| 42 | + | |
| 43 | +if ( version_compare( phpversion(), '5.6', '<' ) ) { | |
| 44 | + add_action( 'admin_notices', '_ef_print_php_version_admin_notice' ); | |
| 45 | + return; | |
| 46 | +} | |
| 47 | + | |
| 30 | 48 | // Define contants |
| 31 | -define( 'EDIT_FLOW_VERSION' , '0.8' ); | |
| 49 | +define( 'EDIT_FLOW_VERSION' , '0.9.2' ); | |
| 32 | 50 | define( 'EDIT_FLOW_ROOT' , dirname(__FILE__) ); |
| 33 | 51 | define( 'EDIT_FLOW_FILE_PATH' , EDIT_FLOW_ROOT . '/' . basename(__FILE__) ); |
| 34 | 52 | define( 'EDIT_FLOW_URL' , plugins_url( '/', __FILE__ ) ); |
| 35 | 53 | define( 'EDIT_FLOW_SETTINGS_PAGE' , add_query_arg( 'page', 'ef-settings', get_admin_url( null, 'admin.php' ) ) ); |
| @@ -76,11 +94,10 @@ | ||
| 76 | 94 | /** Do nothing **/ |
| 77 | 95 | } |
| 78 | 96 | |
| 79 | 97 | private function setup_globals() { |
| 80 | - | |
| 81 | 98 | $this->modules = new stdClass(); |
| 82 | - | |
| 99 | + $this->modules_count = 0; | |
| 83 | 100 | } |
| 84 | 101 | |
| 85 | 102 | /** |
| 86 | 103 | * Include the common resources to Edit Flow and dynamically load the modules |
| @@ -92,9 +109,12 @@ | ||
| 92 | 109 | require_once( ABSPATH . 'wp-admin/includes/class-wp-list-table.php' ); |
| 93 | 110 | |
| 94 | 111 | // Edit Flow base module |
| 95 | 112 | require_once( EDIT_FLOW_ROOT . '/common/php/class-module.php' ); |
| 96 | - | |
| 113 | + | |
| 114 | + // Edit Flow Block Editor Compat trait | |
| 115 | + require_once( EDIT_FLOW_ROOT . '/common/php/trait-block-editor-compatible.php' ); | |
| 116 | + | |
| 97 | 117 | // Scan the modules directory and include any modules that exist there |
| 98 | 118 | $module_dirs = scandir( EDIT_FLOW_ROOT . '/modules/' ); |
| 99 | 119 | $class_names = array(); |
| 100 | 120 | foreach( $module_dirs as $module_dir ) { |
| @@ -99,8 +119,13 @@ | ||
| 99 | 119 | $class_names = array(); |
| 100 | 120 | foreach( $module_dirs as $module_dir ) { |
| 101 | 121 | if ( file_exists( EDIT_FLOW_ROOT . "/modules/{$module_dir}/$module_dir.php" ) ) { |
| 102 | 122 | include_once( EDIT_FLOW_ROOT . "/modules/{$module_dir}/$module_dir.php" ); |
| 123 | + | |
| 124 | + // Try to load Gutenberg compat files | |
| 125 | + if ( file_exists( EDIT_FLOW_ROOT . "/modules/{$module_dir}/compat/block-editor.php" ) ) { | |
| 126 | + include_once( EDIT_FLOW_ROOT . "/modules/{$module_dir}/compat/block-editor.php" ); | |
| 127 | + } | |
| 103 | 128 | // Prepare the class name because it should be standardized |
| 104 | 129 | $tmp = explode( '-', $module_dir ); |
| 105 | 130 | $class_name = ''; |
| 106 | 131 | $slug_name = ''; |
| @@ -115,24 +140,32 @@ | ||
| 115 | 140 | |
| 116 | 141 | // Instantiate EF_Module as $helpers for back compat and so we can |
| 117 | 142 | // use it in this class |
| 118 | 143 | $this->helpers = new EF_Module(); |
| 119 | - | |
| 144 | + | |
| 120 | 145 | // Other utils |
| 121 | 146 | require_once( EDIT_FLOW_ROOT . '/common/php/util.php' ); |
| 122 | - | |
| 147 | + | |
| 123 | 148 | // Instantiate all of our classes onto the Edit Flow object |
| 124 | 149 | // but make sure they exist too |
| 125 | 150 | foreach( $class_names as $slug => $class_name ) { |
| 126 | 151 | if ( class_exists( $class_name ) ) { |
| 127 | 152 | $this->$slug = new $class_name(); |
| 153 | + $compat_class_name = "{$class_name}_Block_Editor_Compat"; | |
| 154 | + if ( class_exists( $compat_class_name ) ) { | |
| 155 | + $this->$slug->compat = new $compat_class_name( $this->$slug, $this->$slug->get_compat_hooks() ); | |
| 156 | + } | |
| 128 | 157 | } |
| 129 | 158 | } |
| 130 | - | |
| 131 | - // Supplementary plugins can hook into this, include their own modules | |
| 132 | - // and add them to the $edit_flow object | |
| 159 | + | |
| 160 | + /** | |
| 161 | + * Fires after edit_flow has loaded all Edit Flow internal modules. | |
| 162 | + * | |
| 163 | + * Plugin authors can hook into this action, include their own modules add them to the $edit_flow object | |
| 164 | + * | |
| 165 | + */ | |
| 133 | 166 | do_action( 'ef_modules_loaded' ); |
| 134 | - | |
| 167 | + | |
| 135 | 168 | } |
| 136 | 169 | |
| 137 | 170 | /** |
| 138 | 171 | * Setup the default hooks and actions |
| @@ -146,8 +179,15 @@ | ||
| 146 | 179 | add_action( 'init', array( $this, 'action_init_after' ), 1000 ); |
| 147 | 180 | |
| 148 | 181 | add_action( 'admin_init', array( $this, 'action_admin_init' ) ); |
| 149 | 182 | |
| 183 | + /** | |
| 184 | + * Fires after setup of all edit_flow actions. | |
| 185 | + * | |
| 186 | + * Plugin authors can hook into this action to manipulate the edit_flow class after initial actions have been registered. | |
| 187 | + * | |
| 188 | + * @param edit_flow $this The core edit flow class | |
| 189 | + */ | |
| 150 | 190 | do_action_ref_array( 'editflow_after_setup_actions', array( &$this ) ); |
| 151 | 191 | } |
| 152 | 192 | |
| 153 | 193 | /** |
| @@ -158,26 +198,32 @@ | ||
| 158 | 198 | |
| 159 | 199 | load_plugin_textdomain( 'edit-flow', null, dirname( plugin_basename( __FILE__ ) ) . '/languages/' ); |
| 160 | 200 | |
| 161 | 201 | $this->load_modules(); |
| 162 | - | |
| 202 | + | |
| 163 | 203 | // Load all of the module options |
| 164 | 204 | $this->load_module_options(); |
| 165 | - | |
| 205 | + | |
| 166 | 206 | // Load all of the modules that are enabled. |
| 167 | 207 | // Modules won't have an options value if they aren't enabled |
| 168 | 208 | foreach ( $this->modules as $mod_name => $mod_data ) |
| 169 | 209 | if ( isset( $mod_data->options->enabled ) && $mod_data->options->enabled == 'on' ) |
| 170 | 210 | $this->$mod_name->init(); |
| 171 | - | |
| 211 | + | |
| 212 | + /** | |
| 213 | + * Fires after edit_flow has loaded all modules and module options. | |
| 214 | + * | |
| 215 | + * Plugin authors can hook into this action to trigger functionaltiy after all Edit Flow module's have been loaded. | |
| 216 | + * | |
| 217 | + */ | |
| 172 | 218 | do_action( 'ef_init' ); |
| 173 | 219 | } |
| 174 | 220 | |
| 175 | 221 | /** |
| 176 | - * Initialize the plugin for the admin | |
| 222 | + * Initialize the plugin for the admin | |
| 177 | 223 | */ |
| 178 | 224 | function action_admin_init() { |
| 179 | - | |
| 225 | + | |
| 180 | 226 | // Upgrade if need be but don't run the upgrade if the plugin has never been used |
| 181 | 227 | $previous_version = get_option( $this->options_group . 'version' ); |
| 182 | 228 | if ( $previous_version && version_compare( $previous_version, EDIT_FLOW_VERSION, '<' ) ) { |
| 183 | 229 | foreach ( $this->modules as $mod_name => $mod_data ) { |
| @@ -187,9 +233,9 @@ | ||
| 187 | 233 | update_option( $this->options_group . 'version', EDIT_FLOW_VERSION ); |
| 188 | 234 | } else if ( !$previous_version ) { |
| 189 | 235 | update_option( $this->options_group . 'version', EDIT_FLOW_VERSION ); |
| 190 | 236 | } |
| 191 | - | |
| 237 | + | |
| 192 | 238 | // For each module that's been loaded, auto-load data if it's never been run before |
| 193 | 239 | foreach ( $this->modules as $mod_name => $mod_data ) { |
| 194 | 240 | // If the module has never been loaded before, run the install method if there is one |
| 195 | 241 | if ( !isset( $mod_data->options->loaded_once ) || !$mod_data->options->loaded_once ) { |
| @@ -199,20 +245,20 @@ | ||
| 199 | 245 | } |
| 200 | 246 | } |
| 201 | 247 | |
| 202 | 248 | $this->register_scripts_and_styles(); |
| 203 | - | |
| 249 | + | |
| 204 | 250 | } |
| 205 | - | |
| 251 | + | |
| 206 | 252 | /** |
| 207 | 253 | * Register a new module with Edit Flow |
| 208 | 254 | */ |
| 209 | 255 | public function register_module( $name, $args = array() ) { |
| 210 | - | |
| 256 | + | |
| 211 | 257 | // A title and name is required for every module |
| 212 | 258 | if ( !isset( $args['title'], $name ) ) |
| 213 | 259 | return false; |
| 214 | - | |
| 260 | + | |
| 215 | 261 | $defaults = array( |
| 216 | 262 | 'title' => '', |
| 217 | 263 | 'short_description' => '', |
| 218 | 264 | 'extended_description' => '', |
| @@ -245,14 +291,24 @@ | ||
| 245 | 291 | // If there's a Help Screen registered for the module, make sure we |
| 246 | 292 | // auto-load it |
| 247 | 293 | if ( !empty( $args['settings_help_tab'] ) ) |
| 248 | 294 | add_action( 'load-edit-flow_page_' . $args['settings_slug'], array( &$this->$name, 'action_settings_help_menu' ) ); |
| 249 | - | |
| 295 | + | |
| 250 | 296 | $this->modules->$name = (object) $args; |
| 297 | + | |
| 298 | + $this->modules_count++; | |
| 299 | + | |
| 300 | + /** | |
| 301 | + * Fires after edit_flow has registered a module. | |
| 302 | + * | |
| 303 | + * Plugin authors can hook into this action to trigger functionaltiy after a module has been loaded. | |
| 304 | + * | |
| 305 | + * @param string $name The name of the registered module | |
| 306 | + */ | |
| 251 | 307 | do_action( 'ef_module_registered', $name ); |
| 252 | 308 | return $this->modules->$name; |
| 253 | 309 | } |
| 254 | - | |
| 310 | + | |
| 255 | 311 | /** |
| 256 | 312 | * Load all of the module options from the database |
| 257 | 313 | * If a given option isn't yet set, then set it to the module's default (upgrades, etc.) |
| 258 | 314 | */ |
| @@ -267,8 +323,15 @@ | ||
| 267 | 323 | } |
| 268 | 324 | |
| 269 | 325 | $this->$mod_name->module = $this->modules->$mod_name; |
| 270 | 326 | } |
| 327 | + | |
| 328 | + /** | |
| 329 | + * Fires after edit_flow has loaded all of the module options from the database. | |
| 330 | + * | |
| 331 | + * Plugin authors can hook into this action to read and manipulate module settings. | |
| 332 | + * | |
| 333 | + */ | |
| 271 | 334 | do_action( 'ef_module_options_loaded' ); |
| 272 | 335 | } |
| 273 | 336 | |
| 274 | 337 | /** |
| @@ -279,21 +342,24 @@ | ||
| 279 | 342 | function action_init_after() { |
| 280 | 343 | foreach ( $this->modules as $mod_name => $mod_data ) { |
| 281 | 344 | |
| 282 | 345 | if ( isset( $this->modules->$mod_name->options->post_types ) ) |
| 283 | - $this->modules->$mod_name->options->post_types = $this->helpers->clean_post_type_options( $this->modules->$mod_name->options->post_types, $mod_data->post_type_support ); | |
| 284 | - | |
| 346 | + $this->modules->$mod_name->options->post_types = $this->helpers->clean_post_type_options( $this->modules->$mod_name->options->post_types, $mod_data->post_type_support ); | |
| 347 | + | |
| 285 | 348 | $this->$mod_name->module = $this->modules->$mod_name; |
| 286 | 349 | } |
| 287 | 350 | } |
| 288 | - | |
| 351 | + | |
| 289 | 352 | /** |
| 290 | 353 | * Get a module by one of its descriptive values |
| 354 | + * | |
| 355 | + * @param string $key The property to use for searching a module (ex: 'name') | |
| 356 | + * @param string|int|array $value The value to compare (using ==) | |
| 291 | 357 | */ |
| 292 | 358 | function get_module_by( $key, $value ) { |
| 293 | 359 | $module = false; |
| 294 | 360 | foreach ( $this->modules as $mod_name => $mod_data ) { |
| 295 | - | |
| 361 | + | |
| 296 | 362 | if ( $key == 'name' && $value == $mod_name ) { |
| 297 | 363 | $module = $this->modules->$mod_name; |
| 298 | 364 | } else { |
| 299 | 365 | foreach( $mod_data as $mod_data_key => $mod_data_value ) { |
| @@ -303,9 +369,9 @@ | ||
| 303 | 369 | } |
| 304 | 370 | } |
| 305 | 371 | return $module; |
| 306 | 372 | } |
| 307 | - | |
| 373 | + | |
| 308 | 374 | /** |
| 309 | 375 | * Update the $edit_flow object with new value and save to the database |
| 310 | 376 | */ |
| 311 | 377 | function update_module_option( $mod_name, $key, $value ) { |
| @@ -312,9 +378,9 @@ | ||
| 312 | 378 | $this->modules->$mod_name->options->$key = $value; |
| 313 | 379 | $this->$mod_name->module = $this->modules->$mod_name; |
| 314 | 380 | return update_option( $this->options_group . $mod_name . '_options', $this->modules->$mod_name->options ); |
| 315 | 381 | } |
| 316 | - | |
| 382 | + | |
| 317 | 383 | function update_all_module_options( $mod_name, $new_options ) { |
| 318 | 384 | if ( is_array( $new_options ) ) |
| 319 | 385 | $new_options = (object)$new_options; |
| 320 | 386 | $this->modules->$mod_name->options = $new_options; |
| @@ -323,9 +389,9 @@ | ||
| 323 | 389 | } |
| 324 | 390 | |
| 325 | 391 | /** |
| 326 | 392 | * Registers commonly used scripts + styles for easy enqueueing |
| 327 | - */ | |
| 393 | + */ | |
| 328 | 394 | function register_scripts_and_styles() { |
| 329 | 395 | wp_enqueue_style( 'ef-admin-css', EDIT_FLOW_URL . 'common/css/edit-flow-admin.css', false, EDIT_FLOW_VERSION, 'all' ); |
| 330 | 396 | |
| 331 | 397 | wp_register_script( 'jquery-listfilterizer', EDIT_FLOW_URL . 'common/js/jquery.listfilterizer.js', array( 'jquery' ), EDIT_FLOW_VERSION, true ); |
| @@ -330,15 +396,18 @@ | ||
| 330 | 396 | |
| 331 | 397 | wp_register_script( 'jquery-listfilterizer', EDIT_FLOW_URL . 'common/js/jquery.listfilterizer.js', array( 'jquery' ), EDIT_FLOW_VERSION, true ); |
| 332 | 398 | wp_register_style( 'jquery-listfilterizer', EDIT_FLOW_URL . 'common/css/jquery.listfilterizer.css', false, EDIT_FLOW_VERSION, 'all' ); |
| 333 | 399 | |
| 400 | + | |
| 401 | + wp_localize_script( 'jquery-listfilterizer', | |
| 402 | + '__i18n_jquery_filterizer', | |
| 403 | + array( | |
| 404 | + 'all' => esc_html__( 'All', 'edit-flow' ), | |
| 405 | + 'selected' => esc_html__( 'Selected', 'edit-flow' ), | |
| 406 | + ) ); | |
| 407 | + | |
| 334 | 408 | wp_register_script( 'jquery-quicksearch', EDIT_FLOW_URL . 'common/js/jquery.quicksearch.js', array( 'jquery' ), EDIT_FLOW_VERSION, true ); |
| 335 | 409 | |
| 336 | - // @compat 3.3 | |
| 337 | - // Register jQuery datepicker plugin if it doesn't already exist. Datepicker plugin was added in WordPress 3.3 | |
| 338 | - global $wp_scripts; | |
| 339 | - if ( !isset( $wp_scripts->registered['jquery-ui-datepicker'] ) ) | |
| 340 | - wp_register_script( 'jquery-ui-datepicker', EDIT_FLOW_URL . 'common/js/jquery.ui.datepicker.min.js', array( 'jquery', 'jquery-ui-core'), '1.8.16', true ); | |
| 341 | 410 | } |
| 342 | 411 | |
| 343 | 412 | } |
| 344 | 413 | |
| @@ -344,5 +413,5 @@ | ||
| 344 | 413 | |
| 345 | 414 | function EditFlow() { |
| 346 | 415 | return edit_flow::instance(); |
| 347 | 416 | } |
| 348 | -add_action( 'plugins_loaded', 'EditFlow' ); | |
| 417 | +add_action( 'plugins_loaded', 'EditFlow' ); | |