Browse Source

Initial commit

master 1.0.0
Yoan Cutillas 5 years ago
commit
cf00ad5a72
  1. 292
      booking-activities.php
  2. 335
      class/class-bookings-list.php
  3. 114
      controller/controller-booking-system.php
  4. 427
      controller/controller-bookings.php
  5. 255
      controller/controller-settings.php
  6. 293
      controller/controller-shortcodes.php
  7. 719
      controller/controller-templates.php
  8. 609
      controller/controller-woocommerce-backend.php
  9. 521
      controller/controller-woocommerce-bookings.php
  10. 705
      controller/controller-woocommerce-frontend.php
  11. 170
      controller/controller-woocommerce-settings.php
  12. 128
      css/backend.css
  13. 183
      css/bookings.css
  14. 13
      css/frontend.css
  15. 115
      css/global.css
  16. 58
      css/landing.css
  17. 79
      css/templates.css
  18. 15
      css/woocommerce.css
  19. 423
      functions/functions-booking-system.php
  20. 513
      functions/functions-bookings.php
  21. 260
      functions/functions-global.php
  22. 373
      functions/functions-settings.php
  23. 92
      functions/functions-template.php
  24. 274
      functions/functions-templates-forms-control.php
  25. 657
      functions/functions-woocommerce.php
  26. 22
      i18n-config.json
  27. BIN
      img/add-hover.png
  28. BIN
      img/add-ons/display-pack.png
  29. BIN
      img/add-ons/order-for-customers.png
  30. BIN
      img/add-ons/points-of-sale.png
  31. BIN
      img/add-ons/prices-and-promotions.png
  32. BIN
      img/add.png
  33. BIN
      img/ajax-loader.gif
  34. BIN
      img/close.png
  35. BIN
      img/cross.png
  36. BIN
      img/delete-hover.png
  37. BIN
      img/delete.png
  38. BIN
      img/edit-hover.png
  39. BIN
      img/edit.png
  40. BIN
      img/gear.png
  41. BIN
      img/help.png
  42. BIN
      img/hide.png
  43. BIN
      img/show.png
  44. BIN
      img/tick.png
  45. BIN
      img/trash-closed.png
  46. BIN
      img/trash-open.png
  47. 88
      js/backend-functions.js
  48. 700
      js/bookings-dialogs.js
  49. 362
      js/bookings-functions.js
  50. 96
      js/bookings.js
  51. 38
      js/global-booking-system.js
  52. 342
      js/global-functions-booking-system.js
  53. 485
      js/global-functions-calendar.js
  54. 127
      js/global-functions.js
  55. 32
      js/global-var.js
  56. 154
      js/shortcodes.js
  57. 1462
      js/templates-dialogs.js
  58. 564
      js/templates-forms-control.js
  59. 760
      js/templates-functions.js
  60. 538
      js/templates.js
  61. 165
      js/woocommerce-backend.js
  62. 361
      js/woocommerce-frontend.js
  63. BIN
      languages/booking-activities-fr_FR.mo
  64. 2953
      languages/booking-activities-fr_FR.po
  65. 1940
      languages/booking-activities.pot
  66. 232
      languages/script-translation.php
  67. 5
      lib/fullcalendar/fullcalendar-locale-all.min.js
  68. 5
      lib/fullcalendar/fullcalendar.min.css
  69. 10
      lib/fullcalendar/fullcalendar.min.js
  70. 5
      lib/fullcalendar/fullcalendar.print.min.css
  71. 551
      lib/fullcalendar/moment.min.js
  72. BIN
      lib/jquery-ui/themes/booking-activities/images/ui-icons_272727_256x240.png
  73. BIN
      lib/jquery-ui/themes/booking-activities/images/ui-icons_418FB6_256x240.png
  74. BIN
      lib/jquery-ui/themes/booking-activities/images/ui-icons_565d61_256x240.png
  75. BIN
      lib/jquery-ui/themes/booking-activities/images/ui-icons_b81c23_256x240.png
  76. BIN
      lib/jquery-ui/themes/booking-activities/images/ui-icons_fff_256x240.png
  77. BIN
      lib/jquery-ui/themes/booking-activities/images/ui-icons_ffffff_256x240.png
  78. 7
      lib/jquery-ui/themes/booking-activities/jquery-ui.min.css
  79. 674
      license.txt
  80. 0
      log/debug.log
  81. 0
      log/error.log
  82. 579
      model/model-booking-system.php
  83. 368
      model/model-bookings.php
  84. 71
      model/model-global.php
  85. 107
      model/model-install.php
  86. 1257
      model/model-templates.php
  87. 358
      model/model-woocommerce.php
  88. 260
      readme.txt
  89. 182
      view/view-backend-bookings-dialogs.php
  90. 29
      view/view-bookings-dialogs.php
  91. 135
      view/view-bookings.php
  92. 196
      view/view-landing.php
  93. 55
      view/view-settings.php
  94. 480
      view/view-templates-dialogs.php
  95. 173
      view/view-templates.php

292
booking-activities.php

@ -0,0 +1,292 @@
<?php
/**
* Plugin Name: Booking Activities
* Plugin URI: http://booking-activities.fr/en
* Description: Create your activity calendars with drag and drop and book scheduled events with one click. Enable online payments of reservations with WooCommerce.
* Version: 1.0.0
* Author: Booking Activities Team
* Author URI: http://booking-activities.fr/en
* Text Domain: booking-activities
* Domain Path: /languages/
* License: GPL3
* License URI: https://www.gnu.org/licenses/gpl-3.0.html
*
* This file is part of Booking Activities.
*
* Booking Activities 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 3 of the License, or
* any later version.
*
* Booking Activities 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 Booking Activities. If not, see <http://www.gnu.org/licenses/>.
*
* @package Booking Activities
* @category Core
* @author Booking Activities Team
*
* Copyright 2017 Yoan Cutillas
*/
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
// GLOBALS AND CONSTANTS
if( ! defined( 'BOOKACTI_PLUGIN_NAME' ) || ! defined( 'BOOKACTI_PLUGIN_BASENAME' ) ) {
define( 'BOOKACTI_PLUGIN_NAME', 'booking-activities' );
define( 'BOOKACTI_PLUGIN_BASENAME', plugin_basename( __FILE__ ) );
}
// HEADER STRINGS (For translation)
__( 'Booking Activities', BOOKACTI_PLUGIN_NAME );
__( 'Create your activity calendars with drag and drop and book scheduled events with one click. Enable online payments of reservations with WooCommerce.', BOOKACTI_PLUGIN_NAME );
/* translators: Add " /lang-code " after this url and check if the url exists, else do not translate. Ex: http://booking-activities.fr/fr works, but http://booking-activities.fr/nl doesn't exist yet. */
__( 'http://booking-activities.fr/en', BOOKACTI_PLUGIN_NAME );
// INCLUDE LANGUAGES FILES
add_action( 'plugins_loaded', 'bookacti_load_textdomain' );
function bookacti_load_textdomain() { load_plugin_textdomain( BOOKACTI_PLUGIN_NAME, FALSE, basename( dirname( __FILE__ ) ) . '/languages/' ); }
// INCLUDE PHP FUNCTIONS
include_once( 'functions/functions-global.php' );
include_once( 'functions/functions-booking-system.php' );
include_once( 'functions/functions-template.php' );
include_once( 'functions/functions-templates-forms-control.php' );
include_once( 'functions/functions-bookings.php' );
include_once( 'functions/functions-settings.php' );
include_once( 'controller/controller-templates.php' );
include_once( 'controller/controller-booking-system.php' );
include_once( 'controller/controller-settings.php' );
include_once( 'controller/controller-bookings.php' );
include_once( 'controller/controller-shortcodes.php' );
// If woocommerce is active, include functions
if( bookacti_is_plugin_active( 'woocommerce/woocommerce.php' ) ) {
include_once( 'controller/controller-woocommerce-bookings.php' );
include_once( 'controller/controller-woocommerce-backend.php' );
include_once( 'controller/controller-woocommerce-frontend.php' );
include_once( 'controller/controller-woocommerce-settings.php' );
include_once( 'functions/functions-woocommerce.php' );
}
// INCLUDE DATABASE FUNCTIONS
require_once( 'model/model-global.php' );
require_once( 'model/model-install.php' );
require_once( 'model/model-templates.php' );
require_once( 'model/model-booking-system.php' );
require_once( 'model/model-bookings.php' );
require_once( 'model/model-woocommerce.php' );
// INCLUDE CLASSES
require_once( 'class/class-bookings-list.php' );
// INCLUDE SCRIPTS
add_action( 'init', 'bookacti_build_translation_array' );
function bookacti_build_translation_array() {
global $bookacti_translation_array;
require_once( 'languages/script-translation.php' );
}
add_action( 'admin_enqueue_scripts','bookacti_enqueue_global_scripts', 20 );
add_action( 'wp_enqueue_scripts', 'bookacti_enqueue_global_scripts', 20 );
function bookacti_enqueue_global_scripts() {
// INCLUDE LIBRARIES
wp_enqueue_script( 'bookacti-js-moment', plugins_url( 'lib/fullcalendar/moment.min.js', __FILE__ ), array( 'jquery' ), '1.0', true );
wp_enqueue_style ( 'bookacti-css-fullcalendar', plugins_url( 'lib/fullcalendar/fullcalendar.min.css', __FILE__ ) );
wp_enqueue_style ( 'bookacti-css-fullcalendar-print', plugins_url( 'lib/fullcalendar/fullcalendar.print.min.css', __FILE__ ),array( 'bookacti-css-fullcalendar' ), false, 'print' );
wp_enqueue_script( 'bookacti-js-fullcalendar', plugins_url( 'lib/fullcalendar/fullcalendar.min.js', __FILE__ ), array( 'jquery', 'bookacti-js-moment' ), '1.0', true );
wp_enqueue_script( 'bookacti-js-fullcalendar-locale-all', plugins_url( 'lib/fullcalendar/fullcalendar-locale-all.min.js', __FILE__ ),array( 'jquery', 'bookacti-js-fullcalendar' ), '1.0', true );
// INCLUDE STYLESHEETS
wp_enqueue_style ( 'bookacti-css-global', plugins_url( 'css/global.css', __FILE__ ) );
wp_enqueue_style ( 'bookacti-css-bookings', plugins_url( 'css/bookings.css', __FILE__ ) );
wp_enqueue_style ( 'bookacti-css-woocommerce', plugins_url( 'css/woocommerce.css', __FILE__ ) );
wp_enqueue_style ( 'jquery-ui-bookacti-theme', plugins_url( 'lib/jquery-ui/themes/booking-activities/jquery-ui.min.css', __FILE__ ), false, null );
// INCLUDE JAVASCRIPT FILES
wp_enqueue_script( 'bookacti-js-global-var', plugins_url( 'js/global-var.js', __FILE__ ), array(), '1.0', true );
wp_register_script( 'bookacti-js-global-booking-system', plugins_url( 'js/global-booking-system.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-global-functions' ), '1.0', true );
wp_register_script( 'bookacti-js-global-functions', plugins_url( 'js/global-functions.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var' ), '1.0', true );
wp_register_script( 'bookacti-js-global-functions-booking-system', plugins_url( 'js/global-functions-booking-system.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'jquery-effects-highlight' ), '1.0', true );
wp_register_script( 'bookacti-js-global-functions-calendar', plugins_url( 'js/global-functions-calendar.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-global-functions' ), '1.0', true );
wp_register_script( 'bookacti-js-bookings', plugins_url( 'js/bookings.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-global-functions' ), '1.0', true );
wp_register_script( 'bookacti-js-bookings-functions', plugins_url( 'js/bookings-functions.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-global-functions', ), '1.0', true );
wp_register_script( 'bookacti-js-bookings-dialogs', plugins_url( 'js/bookings-dialogs.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-global-functions', 'bookacti-js-moment', 'jquery-ui-dialog' ), '1.0', true );
// LOCALIZE SCRIPTS
global $bookacti_translation_array;
wp_localize_script( 'bookacti-js-global-var', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-global-booking-system', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-global-functions', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-global-functions-booking-system', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-global-functions-calendar', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-bookings', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-bookings-functions', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-bookings-dialogs', 'bookacti_localized', $bookacti_translation_array );
//ENQUEUE SCRIPTS
wp_enqueue_script ( 'bookacti-js-global-var' );
wp_enqueue_script ( 'bookacti-js-global-booking-system' );
wp_enqueue_script ( 'bookacti-js-global-functions' );
wp_enqueue_script ( 'bookacti-js-global-functions-booking-system' );
wp_enqueue_script ( 'bookacti-js-global-functions-calendar' );
wp_enqueue_script ( 'bookacti-js-bookings' );
wp_enqueue_script ( 'bookacti-js-bookings-functions' );
wp_enqueue_script ( 'bookacti-js-bookings-dialogs' );
}
add_action( 'admin_enqueue_scripts', 'bookacti_enqueue_backend_scripts', 30 );
function bookacti_enqueue_backend_scripts() {
// INCLUDE STYLESHEETS
wp_enqueue_style ( 'bookacti-css-backend', plugins_url( 'css/backend.css', __FILE__ ) );
wp_enqueue_style ( 'bookacti-css-templates',plugins_url( 'css/templates.css', __FILE__ ) );
wp_enqueue_style ( 'bookacti-css-landing', plugins_url( 'css/landing.css', __FILE__ ) );
// INCLUDE JAVASCRIPT FILES
wp_register_script( 'bookacti-js-backend-functions', plugins_url( 'js/backend-functions.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'jquery-ui-dialog', 'jquery-ui-tabs', 'jquery-ui-tooltip' ), '1.0', true );
wp_register_script( 'bookacti-js-templates', plugins_url( 'js/templates.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-global-functions', 'bookacti-js-templates-functions', 'bookacti-js-templates-dialogs' ), '1.0', true );
wp_register_script( 'bookacti-js-templates-functions', plugins_url( 'js/templates-functions.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-bookings', 'jquery-effects-highlight' ), '1.0', true );
wp_register_script( 'bookacti-js-templates-forms-control', plugins_url( 'js/templates-forms-control.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-moment' ), '1.0', true );
wp_register_script( 'bookacti-js-templates-dialogs', plugins_url( 'js/templates-dialogs.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-global-functions', 'bookacti-js-backend-functions', 'bookacti-js-templates-forms-control', 'bookacti-js-moment', 'jquery-ui-dialog', 'jquery-ui-selectmenu' ), '1.0', true );
wp_register_script( 'bookacti-js-woocommerce-backend', plugins_url( 'js/woocommerce-backend.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-moment' ), '1.0', true );
// LOCALIZE SCRIPTS
global $bookacti_translation_array;
wp_localize_script( 'bookacti-js-templates', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-templates-functions', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-templates-forms-control', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-templates-dialogs', 'bookacti_localized', $bookacti_translation_array );
//ENQUEUE SCRIPTS
wp_enqueue_script ( 'bookacti-js-backend-functions' );
wp_enqueue_script ( 'bookacti-js-templates' );
wp_enqueue_script ( 'bookacti-js-templates-functions' );
wp_enqueue_script ( 'bookacti-js-templates-forms-control' );
wp_enqueue_script ( 'bookacti-js-templates-dialogs' );
wp_enqueue_script ( 'bookacti-js-woocommerce-backend' );
}
add_action( 'wp_enqueue_scripts', 'bookacti_enqueue_frontend_scripts', 30 );
function bookacti_enqueue_frontend_scripts() {
// INCLUDE STYLESHEETS
wp_enqueue_style ( 'bookacti-css-frontend', plugins_url( 'css/frontend.css', __FILE__ ) );
// INCLUDE JAVASCRIPT FILES
wp_register_script( 'bookacti-js-woocommerce-frontend', plugins_url( 'js/woocommerce-frontend.js', __FILE__ ), array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-fullcalendar', 'bookacti-js-global-functions', 'bookacti-js-global-functions-calendar' ), '1.0', true );
wp_register_script( 'bookacti-js-shortcodes', plugins_url( 'js/shortcodes.js', __FILE__ ),array( 'jquery', 'bookacti-js-global-var', 'bookacti-js-moment' ), '1.0', true );
// LOCALIZE SCRIPTS
global $bookacti_translation_array;
wp_localize_script( 'bookacti-js-woocommerce-frontend', 'bookacti_localized', $bookacti_translation_array );
wp_localize_script( 'bookacti-js-shortcodes', 'bookacti_localized', $bookacti_translation_array );
//ENQUEUE SCRIPTS
wp_enqueue_script ( 'bookacti-js-woocommerce-frontend' );
wp_enqueue_script ( 'bookacti-js-shortcodes' );
}
// ACTIVATE
register_activation_hook( __FILE__, 'bookacti_activate' );
function bookacti_activate() {
// Allow users to manage Bookings
bookacti_set_role_and_cap();
// Create tables in database
bookacti_create_tables();
// Insert default values for plugin settings
bookacti_define_default_settings_constants();
bookacti_init_settings_values();
// Keep in memory the first installed date
if( empty( get_option( 'bookacti-install-date' ) ) ) {
update_option( 'bookacti-install-date', date( 'Y-m-d H:i:s' ) );
}
do_action( 'bookacti_activate' );
}
// DEACTIVATION
register_deactivation_hook( __FILE__, 'bookacti_deactivate' );
function bookacti_deactivate() {
do_action( 'bookacti_deactivate' );
}
// UNINSTALL
register_uninstall_hook( __FILE__, 'bookacti_uninstall' );
function bookacti_uninstall() {
//Deregister the hourly reccuring event
wp_clear_scheduled_hook( 'bookacti_hourly_event' );
// Delete plugin settings
bookacti_delete_settings();
// Delete notices acknowledgement
bookacti_reset_notices();
// Drop tables and every Booking Activities Data
bookacti_drop_tables();
// Unset roles and capabilities
bookacti_unset_role_and_cap();
do_action( 'bookacti_uninstall' );
// Clear any cached data that has been removed
wp_cache_flush();
}
// ADMIN MENU
add_action( 'admin_menu', 'bookacti_create_menu' );
function bookacti_create_menu(){
// Add a menu and submenus
$icon_url = 'dashicons-calendar-alt';
add_menu_page( __( 'Booking Activities', BOOKACTI_PLUGIN_NAME ), _x( 'Booking Activities', 'Name of the tab in the menu', BOOKACTI_PLUGIN_NAME ), 'bookacti_manage_booking_activities', 'booking-activities', null, $icon_url, '56.5' );
add_submenu_page( 'booking-activities', _x( 'Booking Activities', 'Landing page title', BOOKACTI_PLUGIN_NAME ), _x( 'Home', 'Landing page tab name', BOOKACTI_PLUGIN_NAME ),'bookacti_manage_booking_activities', 'booking-activities', 'bookacti_landing_page' );
add_submenu_page( 'booking-activities', __( 'Calendar editor', BOOKACTI_PLUGIN_NAME ), __( 'Calendar editor', BOOKACTI_PLUGIN_NAME ), 'bookacti_manage_templates', 'bookacti_calendars', 'bookacti_templates_page' );
add_submenu_page( 'booking-activities', __( 'Bookings', BOOKACTI_PLUGIN_NAME ), __( 'Bookings', BOOKACTI_PLUGIN_NAME ), 'bookacti_manage_bookings', 'bookacti_bookings', 'bookacti_bookings_page' );
add_submenu_page( 'booking-activities', __( 'Settings', BOOKACTI_PLUGIN_NAME ), __( 'Settings', BOOKACTI_PLUGIN_NAME ), 'bookacti_manage_booking_activities_settings', 'bookacti_settings', 'bookacti_settings_page' );
}
// Landing Page
function bookacti_landing_page() {
include_once( 'view/view-landing.php' );
}
// Page content of Booking top-level menu
function bookacti_templates_page() {
include_once( 'view/view-templates.php' );
}
// Page content of the first Booking submenu
function bookacti_bookings_page() {
include_once( 'view/view-bookings.php' );
}
// Page content of the settings submenu
function bookacti_settings_page() {
include_once( 'view/view-settings.php' );
}

335
class/class-bookings-list.php

@ -0,0 +1,335 @@
<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
if( ! class_exists( 'WP_List_Table' ) ) {
require_once( ABSPATH . 'wp-admin/includes/class-wp-list-table.php' );
}
if( ! class_exists( 'Bookings_List_Table' ) ) {
class Bookings_List_Table extends WP_List_Table {
public $items;
public $bookings;
public function __construct(){
global $status, $page;
parent::__construct( array(
/*translator: */
'singular' => 'booking', //singular name of the listed records
'plural' => 'bookings', //plural name of the listed records
'ajax' => true,
'screen' => 'bookacti-bookings'
) );
add_action( 'admin_head', array( &$this, 'admin_header' ) );
}
public function get_columns(){
// SET THE COLUMNS
$columns = array(
'cb' => '<input type="checkbox" />',
'customer' => __( 'Customer', BOOKACTI_PLUGIN_NAME ),
'state' => _x( 'State', 'State of a booking', BOOKACTI_PLUGIN_NAME ),
'quantity' => _x( 'Qty', 'Short for "Quantity"', BOOKACTI_PLUGIN_NAME )
);
/**
* Columns of the booking list.
*
* You must use 'bookacti_booking_list_columns_order' php filter order your custom columns.
* You must use 'bookacti_fill_booking_list_entry' jquery hook to fill your custom columns.
*
* @since 1.0.0
*
* @param array $columns
*/
$columns = apply_filters( 'bookacti_booking_list_columns', $columns );
// SORT THE COLUMNS
$columns_order = array(
10 => 'cb',
20 => 'customer',
30 => 'state',
40 => 'quantity'
);
/**
* Columns order of the booking list.
*
* Order the columns given by the filter 'bookacti_booking_list_columns'
*
* @since 1.0.0
*
* @param array $columns
*/
$columns_order = apply_filters( 'bookacti_booking_list_columns_order', $columns_order );
ksort( $columns_order );
$displayed_columns = array();
foreach( $columns_order as $column_id ) {
$displayed_columns[ $column_id ] = $columns[ $column_id ];
}
// RETURN THE COLUMNS
return $displayed_columns;
}
public function prepare_items() {
$columns = $this->get_columns();
$hidden = array();
$sortable = array();
$this->_column_headers = array( $columns, $hidden, $sortable );
$this->items = $this->get_booking_list_items();
}
public function column_default( $item, $column_name ) {
return $item[ $column_name ];
}
public function column_customer( $item ) {
$actions = bookacti_get_booking_actions_array( $item[ 'id' ] );
$actions_array = array();
if( ! empty( $actions ) ) {
foreach( $actions as $action_id => $action ) {
if( $action[ 'admin_or_front' ] === 'both' || $action[ 'admin_or_front' ] === 'admin' ) {
$actions_array[ $action_id ] = '<a '
. 'href="' . esc_url( $action[ 'link' ] ) . '" '
. 'id="bookacti-booking-action-' . esc_attr( $action_id ) . '-' . esc_attr( $item[ 'id' ] ) . '" '
. 'class="button ' . esc_attr( $action[ 'class' ] ) . ' bookacti-booking-action bookacti-tip" '
. 'data-tip="' . esc_attr( $action[ 'description' ] ) . '" '
. 'data-booking-id="' . esc_attr( $item[ 'id' ] ) . '" >'
. esc_html( $action[ 'label' ] )
. '</a> ';
}
}
}
return sprintf( '%1$s %2$s', $item[ 'customer' ], $this->row_actions( $actions_array ) );
}
public function get_booking_list_items( $event_id = 0, $event_start = 0, $event_end = 0 ) {
$booking_list_items = array();
$event_id = isset( $_POST[ 'event_id' ] ) ? intval( $_POST[ 'event_id' ] ): $event_id;
$event_id = isset( $_GET[ 'event_id' ] ) ? intval( $_GET[ 'event_id' ] ) : $event_id;
$event_start= isset( $_POST[ 'event_start' ] ) ? bookacti_sanitize_datetime( $_POST[ 'event_start' ] ) : $event_start;
$event_start= isset( $_GET[ 'event_start' ] ) ? bookacti_sanitize_datetime( $_GET[ 'event_start' ] ) : $event_start;
$event_end = isset( $_POST[ 'event_end' ] ) ? bookacti_sanitize_datetime( $_POST[ 'event_end' ] ) : $event_end;
$event_end = isset( $_GET[ 'event_end' ] ) ? bookacti_sanitize_datetime( $_GET[ 'event_end' ] ) : $event_end;
if( $event_id && $event_start && $event_end ) {
$bookings = bookacti_get_bookings_for_bookings_list( $event_id, $event_start, $event_end );
$users = bookacti_get_users_data_by_bookings( $bookings );
$this->bookings = $bookings;
foreach( $bookings[ $event_id ] as $i => $booking ) {
if( is_numeric( $booking->user_id ) ) {
$user = $users[ $booking->user_id ];
$this->bookings[ $event_id ][ $i ]->user = $user;
$customer = '<a '
. ' href="' . esc_url( get_admin_url() . 'user-edit.php?user_id=' . $booking->user_id ) . '" '
. ' target="_blank" '
. ' >'
. esc_html( $user->user_login . ' (' . $user->user_email . ')' )
. ' </a>';
} else {
$customer = esc_html( __( 'Unknown user', BOOKACTI_PLUGIN_NAME ) . ' (' . $booking->user_id . ')' );
}
$state = bookacti_format_booking_state( $booking->state );
$booking_item = apply_filters( 'bookacti_booking_list_booking_columns', array(
'customer' => $customer,
'state' => $state,
'quantity' => $booking->quantity,
'id' => $booking->id,
'order_id' => $booking->order_id,
'primary_data' => array( $state, 'x' . $booking->quantity )
), $booking, $user );
// Add info on the primary column to make them directly visible in responsive view
if( ! empty( $booking_item[ 'primary_data' ] ) ) {
$primary_column_name = $this->get_primary_column();
$primary_data = '<div class="bookacti-booking-primary-data-container">';
foreach( $booking_item[ 'primary_data' ] as $single_primary_data ) {
$primary_data .= '<span class="bookacti-booking-primary-data">' . esc_html( $single_primary_data ) . '</span>';
}
$primary_data .= '</div>';
$booking_item[ $primary_column_name ] .= $primary_data;
}
$booking_list_items[] = $booking_item;
}
}
return $booking_list_items;
}
/**
* Get the tbody element for the list table.
*
* @since 1.0.0
* @access public
*/
public function get_rows_or_placeholder() {
if ( $this->has_items() ) {
return $this->get_rows();
} else {
return '<tr class="no-items"><td class="colspanchange" colspan="' . esc_attr( $this->get_column_count() ) . '">' . esc_html__( 'No items found.', BOOKACTI_PLUGIN_NAME ) . '</td></tr>';
}
}
/**
* Generate the table rows
*
* @since 1.0.0
* @access public
*/
public function get_rows() {
$rows = '';
foreach ( $this->items as $item ) {
$rows .= $this->get_single_row( $item );
}
return $rows;
}
/**
* Returns content for a single row of the table
*
* @since 1.0.0
* @access public
*
* @param object $item The current item
*/
public function get_single_row( $item ) {
$row = '<tr>';
$row .= $this->get_single_row_columns( $item );
$row .= '</tr>';
return $row;
}
/**
* Returns the columns for a single row of the table
*
* @since 1.0.0
* @access public
*
* @param object $item The current item
*/
public function get_single_row_columns( $item ) {
list( $columns, $hidden, $sortable, $primary ) = $this->get_column_info();
$returned_columns = '';
foreach ( $columns as $column_name => $column_display_name ) {
$classes = "$column_name column-$column_name";
if ( $primary === $column_name ) {
$classes .= ' has-row-actions column-primary';
}
if ( in_array( $column_name, $hidden ) ) {
$classes .= ' hidden';
}
// Comments column uses HTML in the display name with screen reader text.
// Instead of using esc_attr(), we strip tags to get closer to a user-friendly string.
$data = 'data-colname="' . wp_strip_all_tags( $column_display_name ) . '"';
$attributes = "class='$classes' $data";
if ( 'cb' === $column_name ) {
$returned_columns .= '<th scope="row" class="check-column">';
$returned_columns .= $this->column_cb( $item );
$returned_columns .= '</th>';
} elseif ( method_exists( $this, '_column_' . $column_name ) ) {
$returned_columns .= call_user_func(
array( $this, '_column_' . $column_name ),
$item,
$classes,
$data,
$primary
);
} elseif ( method_exists( $this, 'column_' . $column_name ) ) {
$returned_columns .= "<td $attributes>";
$returned_columns .= call_user_func( array( $this, 'column_' . $column_name ), $item );
$returned_columns .= $this->handle_row_actions( $item, $column_name, $primary );
$returned_columns .= "</td>";
} else {
$returned_columns .= "<td $attributes>";
$returned_columns .= $this->column_default( $item, $column_name );
$returned_columns .= $this->handle_row_actions( $item, $column_name, $primary );
$returned_columns .= "</td>";
}
}
return $returned_columns;
}
/**
* Generate row actions div
*
* @since 3.1.0
* @access protected
*
* @param array $actions The list of actions
* @param bool $always_visible Whether the actions should be always visible
* @return string
*/
protected function row_actions( $actions, $always_visible = false ) {
$action_count = count( $actions );
$i = 0;
if ( !$action_count )
return '';
$class_visible = '';
if( $always_visible ) { $class_visible = 'visible'; }
$out = '<div class="bookacti-booking-actions row-actions ' . esc_attr( $class_visible ) . '">';
foreach ( $actions as $action => $link ) {
++$i;
( $i == $action_count ) ? $sep = '' : $sep = ' | ';
$out .= $link . $sep;
}
$out .= '</div>';
/* translators: Don't translate */
$out .= '<button type="button" class="toggle-row"><span class="screen-reader-text">' . esc_html__( 'Show more details' ) . '</span></button>';
return $out;
}
}
}
add_filter( 'list_table_primary_column', 'bookacti_bookings_list_table_primary_column', 10, 2 );
function bookacti_bookings_list_table_primary_column( $column, $screen ) {
if ( $screen === 'bookacti-bookings' ) {
$column = 'customer';
}
return $column;
}

114
controller/controller-booking-system.php

@ -0,0 +1,114 @@
<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
//Fetch events in order to display them
add_action( 'wp_ajax_bookactiFetchEvents', 'bookacti_controller_fetch_events' );
add_action( 'wp_ajax_nopriv_bookactiFetchEvents', 'bookacti_controller_fetch_events' );
function bookacti_controller_fetch_events() {
$is_admin = intval( $_POST[ 'is_admin' ] );
$templates = bookacti_ids_to_array( $_POST[ 'templates' ] );
// Check nonce
$is_nonce_valid = check_ajax_referer( 'bookacti_fetch_events', 'nonce', false );
// On admin side only, check capabilities
$is_allowed = true;
if( $is_nonce_valid && $is_admin && ! is_super_admin() ) {
$bypass_template_managers_check = apply_filters( 'bookacti_bypass_template_managers_check', false );
if( ! $bypass_template_managers_check ){
// Remove templates current user is not allowed to manage
foreach( $templates as $i => $template_id ){
if( ! bookacti_user_can_manage_template( $template_id ) ) {
unset( $templates[ $i ] );
}
}
// If none remains, disallow the action
if( empty( $templates ) ) { $is_allowed = false; }
}
}
if( $is_nonce_valid && $is_allowed ) {
$activities = bookacti_ids_to_array( $_POST[ 'activities' ] );
$user_datetime = bookacti_sanitize_datetime( $_POST[ 'user_datetime' ] );
$fetch_past_events = intval( $_POST[ 'fetch_past_events' ] );
$user_datetime_object = DateTime::createFromFormat( 'Y-m-d H:i:s', $user_datetime );
$user_datetime_object->setTimezone( new DateTimeZone( 'UTC' ) );
$events = bookacti_fetch_calendar_events( $activities, $templates, $user_datetime_object, boolval( $fetch_past_events ) );
$activities_array = bookacti_get_activities_by_template_ids( $templates, false );
wp_send_json( array( 'status' => 'success', 'events' => $events, 'activities' => $activities_array ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Retrieve HTML elements of the calendar booking system
add_action( 'wp_ajax_bookactiRetrieveCalendarElements', 'bookacti_controller_retrieve_calendar_elements' );
add_action( 'wp_ajax_nopriv_bookactiRetrieveCalendarElements', 'bookacti_controller_retrieve_calendar_elements' );
function bookacti_controller_retrieve_calendar_elements() {
// Check nonce
// No need to check capabilities since everyone can see calendars
$is_nonce_valid = check_ajax_referer( 'bookacti_retrieve_calendar_elements', 'nonce', false );
if( $is_nonce_valid ) {
$calendar_id = sanitize_title_with_dashes( $_POST[ 'calendar_id' ] );
$calendar_elements = bookacti_retrieve_calendar_elements( $calendar_id );
wp_send_json( array( 'status' => 'success', 'calendar_elements' => $calendar_elements ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Get booking system data
add_action( 'wp_ajax_bookactiGetBookingSystemData', 'bookacti_controller_get_booking_system_data' );
add_action( 'wp_ajax_nopriv_bookactiGetBookingSystemData', 'bookacti_controller_get_booking_system_data' );
function bookacti_controller_get_booking_system_data() {
$is_admin = intval( $_POST[ 'is_admin' ] );
$template_ids = bookacti_ids_to_array( $_POST[ 'template_ids' ] );
// Check nonce
$is_nonce_valid = check_ajax_referer( 'bookacti_get_booking_system_data', 'nonce', false );
// On admin side, check capabilities
$is_allowed = true;
if( $is_nonce_valid && $is_admin && ! is_super_admin() ) {
$bypass_template_managers_check = apply_filters( 'bookacti_bypass_template_managers_check', false );
if( ! $bypass_template_managers_check ){
// Remove templates current user is not allowed to manage
foreach( $template_ids as $i => $template_id ){
if( ! bookacti_user_can_manage_template( $template_id ) ) {
unset( $template_ids[ $i ] );
}
}
// If none remains, disallow the action
if( empty( $template_ids ) ) { $is_allowed = false; }
}
}
if( $is_nonce_valid && $is_allowed ) {
$settings = array();
if( count( $template_ids ) !== 1 ) {
$settings = bookacti_get_mixed_template_settings( $template_ids );
} else {
$settings = bookacti_get_templates_settings( $template_ids );
}
if( is_array( $settings ) ){
wp_send_json( array( 'status' => 'success', 'settings' => $settings ) );
} else {
wp_send_json( array( 'status' => 'failed' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}

427
controller/controller-bookings.php

@ -0,0 +1,427 @@
<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
// BOOKINGS
//Get all bookings for a given template and / or event
add_action( 'wp_ajax_bookactiGetBookings', 'bookacti_controller_get_bookings' );
function bookacti_controller_get_bookings() {
// Check nonce and capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_get_bookings', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_read_templates' );
if( $is_nonce_valid && $is_allowed ) {
$template_id = intval( $_POST[ 'template_id' ] );
$event_id = intval( $_POST[ 'event_id' ] );
$bookings = bookacti_get_bookings( $template_id, $event_id );
if( count( $bookings ) > 0 ) {
wp_send_json( array( 'status' => 'success', 'bookings' => $bookings ) );
} else if( count( $bookings ) === 0 ) {
wp_send_json( array( 'status' => 'no_bookings' ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'unknown' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
//Get the HTML bookings list for a given event
add_action( 'wp_ajax_bookactiGetBookingRows', 'bookacti_controller_get_booking_rows' );
function bookacti_controller_get_booking_rows() {
// Check nonce and capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_get_booking_rows', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_edit_bookings' );
if( $is_nonce_valid && $is_allowed ) {
$Bookings_List_Table = new Bookings_List_Table();
$Bookings_List_Table->prepare_items();
$rows = $Bookings_List_Table->get_rows_or_placeholder();
if( $rows ) {
$global_actions_html = bookacti_get_booking_global_actions_html( $Bookings_List_Table->bookings, 'admin' );
wp_send_json( array( 'status' => 'success', 'rows' => $rows, 'global_actions_html' => $global_actions_html ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'no_rows' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// BOOKINGS FILTERS
// Change selected template
add_action( 'wp_ajax_bookactiSelectTemplateFilter', 'bookacti_controller_select_template_filter' );
function bookacti_controller_select_template_filter() {
// Check nonce
$is_nonce_valid = check_ajax_referer( 'bookacti_selected_template_filter', 'nonce', false );
// Check capabilities
$is_allowed = current_user_can( 'bookacti_read_templates' );
if( $is_allowed ){
// Get selected templates and format them
$template_ids = bookacti_ids_to_array( $_POST[ 'template_ids' ] );
// Remove templates current user is not allowed to manage
foreach( $template_ids as $i => $template_id ){
if( ! bookacti_user_can_manage_template( $template_id ) ){
unset( $template_ids[$i] );
}
}
// If none remains, disallow the action
if( empty( $template_ids ) ) { $is_allowed = false; }
}
if( $is_nonce_valid && $is_allowed ) {
// Get selected activities and format them
$activity_ids = bookacti_ids_to_array( $_POST[ 'activity_ids' ] );
// Change default template to the first selected
bookacti_update_user_default_template( $template_ids[ 0 ] );
// Actvity filters change depending on the templates selection,
// this retrieve the HTML for activity filters corresponding to templates selection
$activities_html = bookacti_get_activities_html_for_booking_page( $template_ids, $activity_ids );
wp_send_json( array( 'status' => 'success', 'activities_html' => $activities_html ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// BOOKINGS SETTINGS
// Update booking filters settings
add_action( 'wp_ajax_bookactiBookingFiltersSettings', 'bookacti_controller_change_booking_filter_settings' );
function bookacti_controller_change_booking_filter_settings() {
// Check nonce
$is_nonce_valid = check_ajax_referer( 'bookacti_update_booking_filters_settings', 'nonce', false );
// Check capabilities
if( $is_nonce_valid ) {
if( current_user_can( 'bookacti_read_templates' ) && current_user_can( 'bookacti_manage_bookings' ) ){
$show_past_events = intval( $_POST[ 'show_past_events' ] );
$allow_templates_filter = intval( $_POST[ 'allow_templates_filter' ] );
$allow_activities_filter= intval( $_POST[ 'allow_activities_filter' ] );
$bookings_settings = get_option( 'bookacti_bookings_settings' );
$user_id = get_current_user_id();
if( ! is_array( $bookings_settings['show_past_events'] ) ) { $bookings_settings['show_past_events'] = array(); }
if( ! is_array( $bookings_settings['allow_templates_filter'] ) ) { $bookings_settings['allow_templates_filter'] = array(); }
if( ! is_array( $bookings_settings['allow_activities_filter'] ) ) { $bookings_settings['allow_activities_filter'] = array(); }
$bookings_settings[ 'show_past_events' ][ $user_id ] = $show_past_events;
$bookings_settings[ 'allow_templates_filter' ][ $user_id ] = $allow_templates_filter;
$bookings_settings[ 'allow_activities_filter' ][ $user_id ] = $allow_activities_filter;
update_option( 'bookacti_bookings_settings', $bookings_settings );
wp_send_json( array( 'status' => 'success' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Update booking list settings
add_action( 'wp_ajax_bookactiBookingListSettings', 'bookacti_controller_change_booking_list_settings' );
function bookacti_controller_change_booking_list_settings() {
// Check nonce
$is_nonce_valid = check_ajax_referer( 'bookacti_update_booking_list_settings', 'nonce', false );
// Check capabilities
if( $is_nonce_valid ) {
if( current_user_can( 'bookacti_edit_bookings' ) && current_user_can( 'bookacti_manage_bookings' ) ){
$show_inactive_bookings = intval( $_POST[ 'show_inactive_bookings' ] );
$show_temporary_bookings = intval( $_POST[ 'show_temporary_bookings' ] );
$bookings_settings = get_option( 'bookacti_bookings_settings' );
$user_id = get_current_user_id();
if( ! is_array( $bookings_settings['show_inactive_bookings'] ) ) { $bookings_settings['show_inactive_bookings'] = array(); }
if( ! is_array( $bookings_settings['show_temporary_bookings'] ) ) { $bookings_settings['show_temporary_bookings'] = array(); }
$bookings_settings[ 'show_inactive_bookings' ][ $user_id ] = $show_inactive_bookings;
$bookings_settings[ 'show_temporary_bookings' ][ $user_id ] = $show_temporary_bookings;
update_option( 'bookacti_bookings_settings', $bookings_settings );
wp_send_json( array( 'status' => 'success' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// BOOKING ACTIONS
//Cancel a booking
add_action( 'wp_ajax_bookactiCancelBooking', 'bookacti_controller_cancel_booking' );
add_action( 'wp_ajax_nopriv_bookactiCancelBooking', 'bookacti_controller_cancel_booking' );
function bookacti_controller_cancel_booking() {
$booking_id = intval( $_POST[ 'booking_id' ] );
// Check nonce, capabilities and other params
$is_nonce_valid = check_ajax_referer( 'bookacti_cancel_booking', 'nonce', false );
$is_allowed = bookacti_user_can_manage_booking( $booking_id );
$can_be_cancelled = bookacti_booking_can_be_cancelled( $booking_id );
if( $is_nonce_valid && $is_allowed && $can_be_cancelled ) {
$cancelled = bookacti_cancel_booking( $booking_id );
if( $cancelled ) {
// Is bookings page ?
$is_bookings_page = false;
if( isset( $_POST[ 'is_bookings_page' ] ) ) {
$is_bookings_page = intval( $_POST[ 'is_bookings_page' ] ) === 1 ? true : false;
}
do_action( 'bookacti_booking_state_changed', $booking_id, 'cancelled', array( 'is_admin' => $is_bookings_page ) );
$admin_or_front = $is_bookings_page ? 'both' : 'front';
$allow_refund = bookacti_booking_can_be_refunded( $booking_id );
$actions_html = bookacti_get_booking_actions_html( $booking_id, $admin_or_front );
wp_send_json( array( 'status' => 'success', 'allow_refund' => $allow_refund, 'new_actions_html' => $actions_html ) );
} else {
wp_send_json( array( 'status' => 'failed' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Get possible actions to refund a booking
add_action( 'wp_ajax_bookactiGetRefundActionsHTML', 'bookacti_controller_get_refund_actions_html' );
add_action( 'wp_ajax_nopriv_bookactiGetRefundActionsHTML', 'bookacti_controller_get_refund_actions_html' );
function bookacti_controller_get_refund_actions_html() {
$booking_id = intval( $_POST[ 'booking_id' ] );
// Check nonce, capabilities and other params
$is_nonce_valid = check_ajax_referer( 'bookacti_get_refund_actions_html', 'nonce', false );
$is_allowed = bookacti_user_can_manage_booking( $booking_id );
$can_be_refund = bookacti_booking_can_be_refunded( $booking_id );
if( $is_nonce_valid && $is_allowed && $can_be_refund ) {
$refund_actions_array = bookacti_get_refund_actions_by_booking_id( $booking_id );
$refund_actions_html = bookacti_get_refund_dialog_html_by_booking_id( $booking_id );
if( ! empty( $refund_actions_html ) ) {
wp_send_json( array( 'status' => 'success', 'actions_html' => $refund_actions_html, 'actions_array' => $refund_actions_array ) );
} else {
wp_send_json( array( 'status' => 'failed' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Refund a booking
add_action( 'wp_ajax_bookactiRefundBooking', 'bookacti_controller_refund_booking' );
add_action( 'wp_ajax_nopriv_bookactiRefundBooking', 'bookacti_controller_refund_booking' );
function bookacti_controller_refund_booking() {
$booking_id = intval( $_POST[ 'booking_id' ] );
$sanitized_action = sanitize_title_with_dashes( $_POST[ 'refund_action' ] );
$refund_action = array_key_exists( $sanitized_action, bookacti_get_refund_actions_by_booking_id( $booking_id ) ) ? $sanitized_action : 'email';
// Check nonce, capabilities and other params
$is_nonce_valid = check_ajax_referer( 'bookacti_refund_booking', 'nonce', false );
$is_allowed = bookacti_user_can_manage_booking( $booking_id );
$can_be_refund = bookacti_booking_can_be_refunded( $booking_id, $refund_action );
if( $is_nonce_valid && $is_allowed && $can_be_refund ) {
$refund_message = sanitize_text_field( $_POST[ 'refund_message' ] );
if( $refund_action === 'email' ) {
$refunded = bookacti_send_email_refund_request( $booking_id, $refund_message );
if( $refunded ) {
$refunded = array( 'status' => 'success', 'new_state' => 'refund_requested' );
}
} else {
$refunded = apply_filters( 'bookacti_refund_booking', array( 'status' => 'failed' ), $booking_id, $refund_action, $refund_message );
}
if( $refunded[ 'status' ] === 'success' ) {
$new_state = $refunded[ 'new_state' ] ? $refunded[ 'new_state' ] : 'refunded';
$updated = bookacti_update_booking_state( $booking_id, $new_state );
// Hook status changes
if( $updated ) {
do_action( 'bookacti_booking_state_changed', $booking_id, $new_state, array( 'refund_action' => $refund_action ) );
}
// Get new booking actions
$actions_html = bookacti_get_booking_actions_html( $booking_id, 'admin' );
$refunded[ 'new_actions_html' ] = $actions_html;
}
wp_send_json( $refunded );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Change booking state
add_action( 'wp_ajax_bookactiChangeBookingState', 'bookacti_controller_change_booking_state' );
function bookacti_controller_change_booking_state() {
$booking_id = intval( $_POST[ 'booking_id' ] );
$sanitized_state = sanitize_title_with_dashes( $_POST[ 'new_state' ] );
$new_state = array_key_exists( $sanitized_state, bookacti_get_booking_state_labels() ) ? $sanitized_state : false;
// Check nonce, capabilities and other params
$is_nonce_valid = check_ajax_referer( 'bookacti_change_booking_state', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_edit_bookings' );
$state_can_be_changed = bookacti_booking_state_can_be_changed_to( $booking_id, $new_state );
if( $is_nonce_valid && $is_allowed && $state_can_be_changed && $new_state ) {
$was_active = bookacti_is_booking_active( $booking_id ) ? 1 : 0;
$active = in_array( $new_state, bookacti_get_active_booking_states() ) ? 1 : 0;
if( ! $was_active && $active ) {
$booking = bookacti_get_booking_by_id( $booking_id );
$validated = bookacti_validate_booking_form( $booking->event_id, $booking->event_start, $booking->event_end, $booking->quantity );
} else {
$validated['status'] = 'success';
}
if( $validated['status'] === 'success' ) {
$updated= bookacti_update_booking_state( $booking_id, $new_state );
if( $updated ) {
$is_bookings_page = intval( $_POST[ 'is_bookings_page' ] ) === 1 ? true : false;
do_action( 'bookacti_booking_state_changed', $booking_id, $new_state, array( 'is_admin' => $is_bookings_page, 'active' => $active ) );
$actions_html = bookacti_get_booking_actions_html( $booking_id, 'admin' );
$formatted_state= bookacti_format_booking_state( $new_state );
$active_changed = $active === $was_active ? false : true;
wp_send_json( array( 'status' => 'success', 'new_actions_html' => $actions_html, 'formatted_state' => $formatted_state, 'active_changed' => $active_changed ) );
} else {
wp_send_json( array( 'status' => 'failed' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => $validated['status'], 'message' => esc_html( $validated['message'] ) ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Get booking system info by booking ID
add_action( 'wp_ajax_bookactiGetBookingData', 'bookacti_controller_get_booking_data' );
add_action( 'wp_ajax_nopriv_bookactiGetBookingData', 'bookacti_controller_get_booking_data' );
function bookacti_controller_get_booking_data() {
// Check nonce, no need to check capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_get_booking_data', 'nonce', false );
if( $is_nonce_valid ) {
$booking_id = intval( $_POST[ 'booking_id' ] );
$booking_data = bookacti_get_booking_data( $booking_id );
if( is_array( $booking_data ) && ! empty( $booking_data ) ) {
$booking_data[ 'status' ] = 'success';
wp_send_json( $booking_data );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'empty_data' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Reschedule a booking
add_action( 'wp_ajax_bookactiRescheduleBooking', 'bookacti_controller_reschedule_booking' );
add_action( 'wp_ajax_nopriv_bookactiRescheduleBooking', 'bookacti_controller_reschedule_booking' );
function bookacti_controller_reschedule_booking() {
$booking_id = intval( $_POST[ 'booking_id' ] );
$event_id = intval( $_POST[ 'event_id' ] );
$event_start = bookacti_sanitize_datetime( $_POST[ 'event_start' ] );
$event_end = bookacti_sanitize_datetime( $_POST[ 'event_end' ] );
// Check nonce, capabilities and other params
$is_nonce_valid = check_ajax_referer( 'bookacti_reschedule_booking', 'nonce', false );
$is_allowed = bookacti_user_can_manage_booking( $booking_id );
$can_be_rescheduled = bookacti_booking_can_be_rescheduled( $booking_id, $event_id, $event_start, $event_end );
if( $is_nonce_valid && $is_allowed && $can_be_rescheduled ) {
// Validate availability
$booking = bookacti_get_booking_by_id( $booking_id );
$validated = bookacti_validate_booking_form( $event_id, $event_start, $event_end, $booking->quantity );
if( $validated['status'] === 'success' ) {
$rescheduled = bookacti_reschedule_booking( $booking_id, $event_id, $event_start, $event_end );
if( $rescheduled ) {
do_action( 'bookacti_booking_rescheduled', $booking_id, $event_start, $event_end );
$event_start_formatted = strftime( __( '%A, %B %d, %Y %I:%M %p', BOOKACTI_PLUGIN_NAME ), strtotime( $event_start ) );
$event_end_formatted = strftime( __( '%A, %B %d, %Y %I:%M %p', BOOKACTI_PLUGIN_NAME ), strtotime( $event_end ) );
$is_bookings_page = intval( $_POST[ 'is_bookings_page' ] );
$admin_or_front = $is_bookings_page ? 'both' : 'front';
$actions_html = bookacti_get_booking_actions_html( $booking_id, $admin_or_front );
wp_send_json( array( 'status' => 'success', 'event_start_formatted' => $event_start_formatted, 'event_end_formatted' => $event_end_formatted, 'actions_html' => $actions_html ) );
} else if( $rescheduled === 0 ) {
$message = __( 'You must select a different schedule than the current one.', BOOKACTI_PLUGIN_NAME );
wp_send_json( array( 'status' => 'no_changes', 'error' => 'no_changes', 'message' => $message ) );
} else {
wp_send_json( array( 'status' => 'failed' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => $validated['status'], 'message' => esc_html( $validated[ 'message' ] ) ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed', 'message' => esc_html__( 'You are not allowed to do this.', BOOKACTI_PLUGIN_NAME ) ) );
}
}

255
controller/controller-settings.php

@ -0,0 +1,255 @@
<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
// INIT BA SETTINGS
add_action( 'admin_init', 'bookacti_init_settings' );
function bookacti_init_settings() {
/* General settings Section */
add_settings_section(
'bookacti_settings_section_general',
__( 'General settings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_section_general_callback',
'bookacti_general_settings'
);
add_settings_field(
'booking_method',
__( 'Booking method', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_booking_method_callback',
'bookacti_general_settings',
'bookacti_settings_section_general'
);
add_settings_field(
'started_events_bookable',
__( 'Are started events bookable?', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_started_events_bookable_callback',
'bookacti_general_settings',
'bookacti_settings_section_general'
);
/* Template settings Section */
add_settings_section(
'bookacti_settings_section_template',
__( 'Calendars Settings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_section_template_callback',
'bookacti_template_settings'
);
add_settings_field(
'default_template_per_user',
__( 'Default calendar per user', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_default_template_callback',
'bookacti_template_settings',
'bookacti_settings_section_template'
);
/* Bookings settings Section */
add_settings_section(
'bookacti_settings_section_bookings',
__( 'Bookings Settings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_section_bookings_callback',
'bookacti_bookings_settings'
);
add_settings_field(
'show_past_events',
__( 'Show past events', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_show_past_events_callback',
'bookacti_bookings_settings',
'bookacti_settings_section_bookings'
);
add_settings_field(
'allow_templates_filter',
__( 'Allow calendars filter', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_templates_filter_callback',
'bookacti_bookings_settings',
'bookacti_settings_section_bookings'
);
add_settings_field(
'allow_activities_filter',
__( 'Allow activities filter', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_activities_filter_callback',
'bookacti_bookings_settings',
'bookacti_settings_section_bookings'
);
add_settings_field(
'show_inactive_bookings',
__( 'Show inactive bookings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_show_inactive_bookings_callback',
'bookacti_bookings_settings',
'bookacti_settings_section_bookings'
);
/* Cancellation settings Section */
add_settings_section(
'bookacti_settings_section_cancellation',
__( 'Cancellation settings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_section_cancellation_callback',
'bookacti_cancellation_settings'
);
add_settings_field(
'allow_customers_to_cancel',
__( 'Allow customers to cancel their bookings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_activate_cancel_callback',
'bookacti_cancellation_settings',
'bookacti_settings_section_cancellation'
);
add_settings_field(
'allow_customers_to_reschedule',
__( 'Allow customers to reschedule their bookings', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_activate_reschedule_callback',
'bookacti_cancellation_settings',
'bookacti_settings_section_cancellation'
);
add_settings_field(
'cancellation_min_delay_before_event',
__( 'Min delay before event', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_cancellation_delay_callback',
'bookacti_cancellation_settings',
'bookacti_settings_section_cancellation'
);
add_settings_field(
'refund_actions_after_cancellation',
__( 'Possible actions customers can take to be refund', BOOKACTI_PLUGIN_NAME ),
'bookacti_settings_field_cancellation_refund_actions_callback',
'bookacti_cancellation_settings',
'bookacti_settings_section_cancellation'
);
do_action( 'bookacti_add_settings' );
register_setting('bookacti_general_settings', 'bookacti_general_settings' );
register_setting('bookacti_cancellation_settings', 'bookacti_cancellation_settings' );
}
// Add actions to Booking Activities in plugins list
add_filter( 'plugin_action_links_' . BOOKACTI_PLUGIN_BASENAME, 'bookacti_action_links_in_plugins_table', 10, 1 );
function bookacti_action_links_in_plugins_table( $links ) {
$links = array( 'settings' => '<a href="' . admin_url( 'admin.php?page=bookacti_settings' ) . '" title="' . esc_attr( __( 'Manage Booking Activities Settings', BOOKACTI_PLUGIN_NAME ) ) . '">' . __( 'Settings', BOOKACTI_PLUGIN_NAME ) . '</a>' ) + $links;
return $links;
}
// Add meta links in plugins list
add_filter( 'plugin_row_meta', 'bookacti_meta_links_in_plugins_table', 10, 2 );
function bookacti_meta_links_in_plugins_table( $links, $file ) {
if ( $file == BOOKACTI_PLUGIN_BASENAME ) {
$links[ 'docs' ] = '<a href="' . esc_url( apply_filters( 'bookacti_user_docs_url', __( 'http://booking-activities.fr/en/documentation/user-documentation/', BOOKACTI_PLUGIN_NAME ) ) ) . '" title="' . esc_attr( __( 'View Booking Activities Documentation', BOOKACTI_PLUGIN_NAME ) ) . '" target="_blank" >' . esc_html__( 'Docs', BOOKACTI_PLUGIN_NAME ) . '</a>';
$links[ 'report' ] = '<a href="' . esc_url( apply_filters( 'bookacti_report_url', 'https://github.com/bookingactivities/booking-activities/issues/' ) ) . '" title="' . esc_attr( __( 'Report a bug or request a feature', BOOKACTI_PLUGIN_NAME ) ) . '" target="_blank" >' . esc_html__( 'Report & Request', BOOKACTI_PLUGIN_NAME ) . '</a>';
$links[ 'contact' ] = '<a href="' . esc_url( apply_filters( 'bookacti_contact_url', __( 'http://booking-activities.fr/en/#contact', BOOKACTI_PLUGIN_NAME ) ) ) . '" title="' . esc_attr( __( 'Contact us directly', BOOKACTI_PLUGIN_NAME ) ) . '" target="_blank" >' . esc_html__( 'Contact us', BOOKACTI_PLUGIN_NAME ) . '</a>';
}
return $links;
}
// INIT BA NOTICES
// FIRST20 DISCOUNT NOTICE
add_action( 'admin_notices', 'bookacti_first20_notice' );
function bookacti_first20_notice() {
if( ! empty( get_option( 'bookacti-first20-notice-dismissed' ) ) || ! current_user_can( 'bookacti_manage_booking_activities' ) ) {
return;
}
$switch_message = false;
if( ! empty( $_GET ) && isset( $_GET[ 'page' ] ) ) {
if( sanitize_title_with_dashes( $_GET[ 'page' ] ) === 'booking-activities' ) {
$switch_message = true;
if( empty( get_option( 'bookacti-first20-notice-viewed' ) ) ) {
update_option( 'bookacti-first20-notice-viewed', 1 );
}
if( isset( $_GET[ 'dismiss_first20_notice' ] ) && wp_verify_nonce( $_GET[ 'nonce' ], 'bookacti_dismiss_first20_notice' ) && current_user_can( 'bookacti_manage_booking_activities' ) ) {
update_option( 'bookacti-first20-notice-dismissed', 1 );
return;
}
} else {
if( ! empty( get_option( 'bookacti-first20-notice-viewed' ) ) ) {
return;
}
}
} else if( ! empty( get_option( 'bookacti-first20-notice-viewed' ) ) ) {
return;
}
?>
<div class='notice notice-success bookacti-first20-notice is-dismissible' >
<p><?php esc_html_e( 'Welcome to Booking Activities! To thank you for using our booking plugin, we give you a 20% discount on every add-ons with the code "FIRST20" on your first purchase on booking-activities.fr.', BOOKACTI_PLUGIN_NAME ); ?></p>
<p>
<?php if( ! $switch_message ) { ?>
<a class='button' href='<?php echo esc_url( admin_url( 'admin.php?page=booking-activities' ) ); ?>' ><?php esc_html_e( 'See add-ons and hide this message', BOOKACTI_PLUGIN_NAME ); ?></a>
<?php } else { ?>
<a class='button' href='<?php echo esc_url( wp_nonce_url( admin_url( 'admin.php?page=booking-activities&dismiss_first20_notice=1' ), 'bookacti_dismiss_first20_notice', 'nonce' ) ); ?>' ><?php esc_html_e( 'I have already benefited from this offer, hide this message', BOOKACTI_PLUGIN_NAME ); ?></a>
<?php } ?>
</p>
</div>
<?php
}
// ASK TO RATE THE PLUGIN 5 STARS
if( empty( get_option( 'bookacti-5stars-rating-notice-dismissed' ) ) ) {
if( current_user_can( 'bookacti_manage_booking_activities' ) ) {
$install_date = get_option( 'bookacti-install-date' );
if( ! empty( $install_date ) ) {
$install_datetime = DateTime::createFromFormat( 'Y-m-d H:i:s', $install_date );
$current_datetime = new DateTime();
$nb_days = floor( $install_datetime->diff( $current_datetime )->days );
if( $nb_days >= 7 ) {
add_action( 'admin_notices', 'bookacti_5stars_rating_notice' );
}
}
}
}
function bookacti_5stars_rating_notice() {
?>
<div class='notice notice-info bookacti-5stars-rating-notice is-dismissible' >
<p><?php esc_html_e( 'You have been using Booking Activities for one week now. We are glad you like it! Please let people know by rating us five stars on wordpress.org, this is really important for us as we provide Booking Activities for free, and it will only take you five minutes.', BOOKACTI_PLUGIN_NAME ); ?></p>
<p>
<a class='button' href='<?php echo esc_url( 'https://wordpress.org/support/plugin/booking-activities/reviews/' ); ?>' target='_blank' ><?php esc_html_e( "Ok, I'll rate you five stars!", BOOKACTI_PLUGIN_NAME ); ?></a>
<span class='button' id='bookacti-dismiss-5stars-rating' ><?php esc_html_e( "I already rated you, hide this message", BOOKACTI_PLUGIN_NAME ); ?></span>
</p>
</div>
<?php
}
// REMOVE NOTICES
// Remove Rate-us-5-stars notice
add_action( 'wp_ajax_bookactiDismiss5StarsRatingNotice', 'bookacti_dismiss_5stars_rating_notice' );
function bookacti_dismiss_5stars_rating_notice() {
// Check nonce, no need to check capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_dismiss_5stars_rating_notice', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_manage_booking_activities' );
if( $is_nonce_valid && $is_allowed ) {
$updated = update_option( 'bookacti-5stars-rating-notice-dismissed', 1 );
if( $updated ) {
wp_send_json( array( 'status' => 'success' ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_updated' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}

293
controller/controller-shortcodes.php

@ -0,0 +1,293 @@
<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
add_action( 'init', 'bookacti_shortcodes_init');
function bookacti_shortcodes_init() {
add_shortcode( 'bookingactivities_calendar', 'bookacti_shortcode_calendar' );
add_shortcode( 'bookingactivities_form', 'bookacti_shortcode_booking_form' );
add_shortcode( 'bookingactivities_list', 'bookacti_shortcode_bookings_list' );
}
// Show the calendar of activities / templates
// EX: [bookacti_form calendars='2' // Actual comma separated calendars ids list
// activities='1,2,10' // Actual comma separated activities ids list
// id='my-cal' // Any id you want
// classes='full-width' // Any class you want
// method='waterfall' ] // Display method
function bookacti_shortcode_calendar( $atts = [], $content = null, $tag = '' ) {
// normalize attribute keys, lowercase
$atts = array_change_key_case( (array) $atts, CASE_LOWER );
// override default attributes with user attributes
$defaults = apply_filters( 'bookacti_shortcode_' . $tag . '_default_parameters', array(
'id' => '',
'classes' => '',
'calendars' => '',
'activities' => '',
'method' => 'calendar'
) );
$atts = shortcode_atts( $defaults, $atts, $tag );
$atts = bookacti_format_booking_system_attributes( $atts );
apply_filters( 'bookacti_shortcode_atts_' . $tag, $atts, $content );
$prevent_execution = apply_filters( 'bookacti_shortcode_' . $tag . '_prevent_execution', false, $atts, $content );
$output = '';
if( ! $prevent_execution ) {
$output .= '<div class="bookacti-booking-system-alone" >'
. bookacti_display_booking_system( $atts[ 'calendars' ], $atts[ 'activities' ], $atts[ 'method' ], $atts[ 'id' ], $atts[ 'classes' ], false )
. '</div>';
}
return apply_filters( 'bookacti_shortcode_' . $tag . '_return', $output, $atts, $content );
}
// Show a booking form
// EX: [bookacti_form calendars='2' // Actual comma separated calendars ids list
// activities='1,2,10' // Actual comma separated activities ids list
// id='my-cal' // Any id you want
// classes='full-width' // Any class you want
// method='waterfall' // Display method
// url='http://page-to-go-after-successful-booking-submission'] // URL to be redirected after submission
function bookacti_shortcode_booking_form( $atts = [], $content = null, $tag = '' ) {
// normalize attribute keys, lowercase
$atts = array_change_key_case( (array) $atts, CASE_LOWER );
// override default attributes with user attributes
$defaults = apply_filters( 'bookacti_shortcode_' . $tag . '_default_parameters', array(
'id' => '',
'classes' => '',
'calendars' => '',
'activities' => '',
'method' => 'calendar',
'url' => '',
'button' => __( 'Book', BOOKACTI_PLUGIN_NAME )
) );
$atts = shortcode_atts( $defaults, $atts, $tag );
$atts = bookacti_format_booking_system_attributes( $atts );
apply_filters( 'bookacti_shortcode_atts_' . $tag, $atts, $content );
$prevent_execution = apply_filters( 'bookacti_shortcode_' . $tag . '_prevent_execution', false, $atts, $content );
$output = '';
if( ! $prevent_execution ) {
$output .= "
<form action='" . $atts[ 'url' ] . "'
class='bookacti-booking-system-form'
id='bookacti-booking-system-form-" . $atts[ 'id' ] . "' >
<input type='hidden' name='action' value='bookactiSubmitBookingForm' />
<input type='hidden' name='bookacti_booking_system_id' value='" . $atts[ 'id' ] . "' />"
. wp_nonce_field( 'bookacti_booking_form', 'nonce_booking_form', true, false )
. bookacti_display_booking_system( $atts[ 'calendars' ], $atts[ 'activities' ], $atts[ 'method' ], $atts[ 'id' ], $atts[ 'classes' ], false ) .
"<div class='bookacti-booking-system-field-container' >
<label for='bookacti-quantity-booking-form-" . $atts[ 'id' ] . "' class='bookacti-booking-system-label' >"
. __( 'Quantity', BOOKACTI_PLUGIN_NAME ) .
"</label>
<input name='bookacti_quantity'
id='bookacti-quantity-booking-form-" . $atts[ 'id' ] . "'
class='bookacti-booking-system-field bookacti-quantity'
type='number'
min='1'
value='1' />
</div>"
. apply_filters( 'bookacti_booking_form_fields', '', $atts, $content ) .
"<div class='bookacti-booking-system-field-container bookacti-booking-system-field-submit-container' >
<input type='submit'
class='button'
value='" . $atts[ 'button' ] . "' />
</div>
</form>";
}
return apply_filters( 'bookacti_shortcode_' . $tag . '_return', $output, $atts, $content );
}
// Show a bookings list
// EX: [bookacti_list]
function bookacti_shortcode_bookings_list( $atts = [], $content = null, $tag = '' ) {
// normalize attribute keys, lowercase
$atts = array_change_key_case( (array) $atts, CASE_LOWER );
// override default attributes with user attributes
$defaults = apply_filters( 'bookacti_shortcode_' . $tag . '_default_parameters', array(
'user' => get_current_user_id()
) );
$atts = shortcode_atts( $defaults, $atts, $tag );
$prevent_execution = apply_filters( 'bookacti_shortcode_' . $tag . '_prevent_execution', false, $atts, $content );
$output = '';
if( ! $prevent_execution ) {
$user_id = intval( $atts[ 'user' ] );
if( $user_id ) {
$columns = apply_filters( 'bookacti_user_bookings_list_columns_titles', array(
10 => array( 'id' => 'id', 'title' => esc_html__( 'ID', BOOKACTI_PLUGIN_NAME ) ),
20 => array( 'id' => 'activity', 'title' => esc_html__( 'Activity', BOOKACTI_PLUGIN_NAME ) ),
30 => array( 'id' => 'dates', 'title' => esc_html__( 'Dates', BOOKACTI_PLUGIN_NAME ) ),
40 => array( 'id' => 'quantity', 'title' => esc_html__( 'Quantity', BOOKACTI_PLUGIN_NAME ) ),
50 => array( 'id' => 'state', 'title' => esc_html_x( 'State', 'State of a booking', BOOKACTI_PLUGIN_NAME ) ),
100 => array( 'id' => 'actions', 'title' => esc_html__( 'Actions', BOOKACTI_PLUGIN_NAME ) )
), $user_id );
ksort( $columns );
// TABLE HEADER
$head_columns = '';
foreach( $columns as $column ) {
$head_columns .= "<th><div class='bookacti-booking-" . $column[ 'id' ] . "-title' >" . $column[ 'title' ] . "</div></th>";
}
// TABLE CONTENT
$bookings = bookacti_get_bookings_by_user_id( $user_id );
$body_columns = '';
if( ! empty( $bookings ) ) {
foreach( $bookings as $booking ) {
$event = bookacti_get_event_by_id( $booking->event_id );
$columns_value = apply_filters( 'bookacti_user_bookings_list_columns_value', array(
'id' => $booking->id,
'activity' => apply_filters( 'bookacti_translate_text', stripslashes( $event->title ) ),
'dates' => bookacti_get_booking_dates_html( $booking ),
'quantity' => $booking->quantity,
'state' => bookacti_format_booking_state( $booking->state ),
'actions' => bookacti_get_booking_actions_html( $booking->id, 'front' )
), $booking, $user_id );
$body_columns .= "<tr>";
foreach( $columns as $column ) {
// Format output values
switch ( $column[ 'id' ] ) {
case 'id':
$value = isset( $columns_value[ 'id' ] ) ? intval( $columns_value[ 'id' ] ) : '';
break;
case 'activity':
$value = isset( $columns_value[ 'activity' ] ) ? esc_html( $columns_value[ 'activity' ] ) : '';
break;
case 'quantity':
$value = isset( $columns_value[ 'quantity' ] ) ? intval( $columns_value[ 'quantity' ] ) : '';
break;
case 'dates':
case 'state':
case 'actions':
default:
$value = isset( $columns_value[ $column[ 'id' ] ] ) ? $columns_value[ $column[ 'id' ] ] : '';
}
$class_empty = empty( $value ) ? 'bookacti-empty-column' : '';
$body_columns .= "<td data-title='" . esc_attr( $column[ 'title' ] ) . "' class='" . $class_empty . "' ><div class='bookacti-booking-" . $column[ 'id' ] . "' >" . $value . "</div></td>";
}
$body_columns .= "</tr>";
}
} else {
$body_columns.= "<tr>"
. "<td colspan='" . esc_attr( count( $columns ) ) . "'>" . esc_html__( 'You don\'t have any bookings.', BOOKACTI_PLUGIN_NAME ) . "</td>"
. "</tr>";
}
// TABLE OUTPUT
$output .= "
<div id='bookacti-user-bookings-list-" . $user_id . "' class='bookacti-user-bookings-list'>
<table>
<thead>
<tr>"
. $head_columns .
"</tr>
</thead>
<tbody>"
. $body_columns .
"</tbody>
</table>
</div>";
// Include bookings dialogs if they are not already
include_once( WP_PLUGIN_DIR . '/' . BOOKACTI_PLUGIN_NAME . '/view/view-bookings-dialogs.php' );
}
}
return apply_filters( 'bookacti_shortcode_' . $tag . '_return', $output, $atts, $content );
}
// Check if booking form is correct and then book the event, or send the error message
add_action( 'wp_ajax_bookactiSubmitBookingForm', 'bookacti_controller_validate_booking_form' );
add_action( 'wp_ajax_nopriv_bookactiSubmitBookingForm', 'bookacti_controller_validate_booking_form' );
function bookacti_controller_validate_booking_form() {
// Check nonce and capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_booking_form', 'nonce_booking_form', false );
$is_allowed = is_user_logged_in();
if( $is_nonce_valid && $is_allowed ) {
//Gether the form variables
$booking_form_values = apply_filters( 'bookacti_booking_form_values', array(
'user_id' => intval( get_current_user_id() ),
'booking_system_id' => sanitize_title_with_dashes( $_POST[ 'bookacti_booking_system_id' ] ),
'event_id' => intval( $_POST[ 'bookacti_event_id' ] ),
'event_start' => bookacti_sanitize_datetime( $_POST[ 'bookacti_event_start' ] ),
'event_end' => bookacti_sanitize_datetime( $_POST[ 'bookacti_event_end' ] ),
'quantity' => intval( $_POST[ 'bookacti_quantity' ] ),
'default_state' => 'pending' ) );
//Check if the form is ok and if so Book temporarily the event
$response = bookacti_validate_booking_form( $booking_form_values[ 'event_id' ], $booking_form_values[ 'event_start' ], $booking_form_values[ 'event_end' ], $booking_form_values[ 'quantity' ] );
if( $booking_form_values[ 'user_id' ] != get_current_user_id() && ! current_user_can( 'bookacti_edit_bookings' ) ) {
$response[ 'status' ] = 'failed';
$response[ 'message' ] = __( 'You can\'t make a booking for someone else.', BOOKACTI_PLUGIN_NAME );
}
if( $response[ 'status' ] === 'success' ) {
$booking = bookacti_insert_booking( $booking_form_values[ 'user_id' ],
$booking_form_values[ 'event_id' ],
$booking_form_values[ 'event_start' ],
$booking_form_values[ 'event_end' ],
$booking_form_values[ 'quantity' ],
$booking_form_values[ 'default_state' ] );
if( ! is_null( $booking[ 'id' ] ) ) {
do_action( 'bookacti_booking_form_validated', $booking[ 'id' ], $booking_form_values );
$message = __( 'Your event has been booked successfully!', BOOKACTI_PLUGIN_NAME );
wp_send_json( array( 'status' => 'success', 'message' => esc_html( $message ), 'booking_id' => $booking[ 'id' ] ) );
} else {
$message = __( 'An error occurred, please try again.', BOOKACTI_PLUGIN_NAME );
}
} else {
$message = $response[ 'message' ];
}
} else {
$message = __( 'You are not allowed to do this.', BOOKACTI_PLUGIN_NAME );
if( ! $is_allowed ) {
$message = __( 'You are not logged in. Please create an account and log in first.', BOOKACTI_PLUGIN_NAME );
}
$response = array( 'status' => 'failed', 'error' => 'not_allowed', 'message' => $message );
}
$return_array = apply_filters( 'bookacti_booking_form_error', array( 'status' => 'failed', 'message' => $message ), $response );
wp_send_json( array( 'status' => $return_array[ 'status' ], 'message' => esc_html( $return_array[ 'message' ] ) ) );
}

719
controller/controller-templates.php

@ -0,0 +1,719 @@
<?php
// Exit if accessed directly
if ( ! defined( 'ABSPATH' ) ) { exit; }
// EVENTS
// Fetch events in order to display them
add_action( 'wp_ajax_bookactiFetchTemplateEvents', 'bookacti_controller_fetch_template_events' );
function bookacti_controller_fetch_template_events() {
$template_id = intval( $_POST['template_id'] );
// Check nonce and capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_fetch_template_events', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_read_templates' ) && bookacti_user_can_manage_template( $template_id );
if( $is_nonce_valid && $is_allowed && $template_id ) {
$event_id = intval( $_POST['event_id'] );
$events = bookacti_fetch_events( $template_id, $event_id );
wp_send_json( array( 'status' => 'success', 'events' => $events ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
}
// Retrieve some event data
add_action( 'wp_ajax_bookactiGetEventData', 'bookacti_controller_get_event_data' );
function bookacti_controller_get_event_data() {
$event_id = intval( $_POST['event_id'] );
$template_id = bookacti_get_event_template_id( $event_id );
// Check nonce and capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_get_event_data', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_read_templates' ) && bookacti_user_can_manage_template( $template_id );
if( $is_nonce_valid && $is_allowed ) {
$data = bookacti_get_event_data( $event_id );
if( is_array( $data ) && ! empty( $data ) ){
// Check template permission
if( bookacti_user_can_manage_template( $data[ 'template_id' ] ) ) {
$data[ 'status' ] = 'success';
wp_send_json( $data );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'no_data', 'data' => $data ) );
}
}
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}
// Add new event on calendar
add_action( 'wp_ajax_bookactiInsertEvent', 'bookacti_controller_insert_event' );
function bookacti_controller_insert_event() {
$template_id = intval( $_POST['template_id'] );
// Check nonce and capabilities
$is_nonce_valid = check_ajax_referer( 'bookacti_insert_event', 'nonce', false );
$is_allowed = current_user_can( 'bookacti_edit_templates' ) && bookacti_user_can_manage_template( $template_id );
if( $is_nonce_valid && $is_allowed ) {
$activity_id = intval( $_POST['activity_id'] );
$event_title = sanitize_text_field( $_POST['event_title'] );
$event_start = bookacti_sanitize_datetime( $_POST['event_start'] );
$event_end = bookacti_sanitize_datetime( $_POST['event_end'] );
$event_availability = intval( $_POST['event_availability'] );
$lastid = bookacti_insert_event( $template_id, $activity_id, $event_title, $event_start, $event_end, $event_availability );
if( $lastid ) {
wp_send_json( array( 'status' => 'success', 'eventid' => $lastid ) );
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_inserted' ) );
}
} else {
wp_send_json( array( 'status' => 'failed', 'error' => 'not_allowed' ) );
}