Plugin Directory

Changeset 2973972


Ignore:
Timestamp:
10/02/2023 06:25:57 PM (2 years ago)
Author:
arstudios
Message:

Release 1.7.0.

Location:
constellation-client-portal
Files:
156 added
6 deleted
7 edited

Legend:

Unmodified
Added
Removed
  • constellation-client-portal/trunk/README.txt

    r2961762 r2973972  
    55Requires at least: 5.0.0
    66Tested up to: 6.3
    7 Stable tag: 1.6.0
     7Stable tag: 1.7.0
    88Requires PHP: 7.4
    99License: GPLv3 or later
     
    3232* Automatically send email notifications to clients when a new File or Invoice post is created.
    3333* Automatically send reminder email notifications on a schedule.
     34* Easily generate, save, and edit file and invoice shortcodes within the plugin settings.
    3435* Add due dates and past due notices to invoices and files.
    3536* Further restrict file and invoice access within a company by user and role.
     
    686913. Admin Settings - Client Page Edit
    697014. Admin Settings - Pro Invoice Bulk Create
    70 
    71 == Shortcodes ==
     7115. Admin Settings - Pro List/Shortcode Settings
     7216. Admin Settings - Pro List/Shortcode Edit Settings
     73
     74== Shortcodes (Core) ==
     75
     76The shortcode parameters, below, are for use with the core version of the plugin.  The pro version allows for file and invoice shortcodes to be easily generated, saved, and edited within the plugin settings.
    7277
    7378= Unpaid Invoice List =
     
    9196* **align_thumbnail** this allows the thumbnail image alignment to be set if the “show_thumbnail” attribute is set to “true”. Accepted Values: “center”, “left”, “right”, “float-left”, or “float-right”. Default: null.
    9297* **show_post_date** this allows for the WordPress post date to be displayed with each item in a list. Accepted Values: “true” or “false”. Default: “false”.
    93 * **list_id** this can be useful for development when you have multiple lists on the same page (ex. this could be helpful when creatig paginated lists on the same page). Accepted Values: any whole positive number that is unique on the page. Default: null
    9498* **categories** Accepted Values: this can be entered as an Invoice Category Slug or ID, or a combination of those. Separate multiple values with a comma (ex. “21, category-a”). Default: null.
    9599* **link_title** Accepted Values: “nolink”.  Adding this parameter and setting the value to "nolink" will remove the href from post titles in the list and make them unclickable. Default: null.
    96 * **id** Accepted Values: any valid HTML ID attribute name. Default: null.
    97100* **class** Accepted Values: any valid HTML class attribute name or names (separate multiple class names with a space). Default: null.
    98 
    99 
    100 = Pro Invoice Shortcode Parameters =
    101 
    102 * **display_pay_btn** this will display a pay button if the “invoice_status” attribute is set to “unpaid” and a WooCommerce product id has been entered in the invoice. Accepted Values: “true” or “false”. Default: “false”.
    103 * **due_date** this will display the due date if a due date has been entered in the invoice. Accepted Values: “true” or “false”. Default: “false”.
    104 * **past_due_notice** this will display a “Past Due” label for each item that has a status of “unpaid” and the current date is after the “due_date”. Accepted Values: “true” or “false”. Default: “false”.
    105 * **exclude_user** this allows you to prevent specific users, within an assigned company, from viewing items in the list. Accepted Values: the WordPress user ID(s). Separate multiple values with a comma (ex. “21, 45”). Default: null.
    106 * **exclude_role** this allows you to prevent specific roles, within an assigned company, from viewing items in the list. Accepted Values: the WordPress role name. Separate multiple values with a comma (ex. “Subscriber, Editor”). Default: null.
    107101
    108102
     
    123117* **align_thumbnail** this allows the thumbnail image alignment to be set if the “show_thumbnail” attribute is set to “true”. Accepted Values: “center”, “left”, “right”, “float-left”, or “float-right”. Default: null.
    124118* **show_post_date** this allows for the WordPress post date to be displayed with each item in a list. Accepted Values: “true” or “false”. Default: “false”.
    125 * **list_id** this can be useful for development when you have multiple lists on the same page (ex. this could be helpful when creatig paginated lists on the same page). Accepted Values: any whole positive number that is unique on the page. Default: null.
    126119* **link_title** Accepted Values: “nolink”.  Adding this parameter and setting the value to "nolink" will remove the href from post titles in the list and make them unclickable. Default: null.
    127 * **id** Accepted Values: any valid HTML ID attribute name. Default: null.
    128120* **class** Accepted Values: any valid HTML class attribute name or names (separate multiple class names with a space). Default: null.
    129121
    130 = Pro File Shortcode Parameters =
    131 
    132 * **due_date** this will display the due date if a due date has been entered in the file. Accepted Values: “true” or “false”. Default: “false”.
    133 * **past_due_notice** this will display a “Past Due” label a due date has been entered, and the current date is after the “due_date”. Accepted Values: “true” or “false”. Default: “false”.
    134 * **exclude_user** this allows you to prevent specific users, within an assigned company, from viewing items in the list. Accepted Values: the WordPress user ID(s). Separate multiple values with a comma (ex. “21, 45”). Default: null.
    135 * **exclude_role** this allows you to prevent specific roles, within an assigned company, from viewing items in the list. Accepted Values: the WordPress role name. Separate multiple values with a comma (ex. “Subscriber, Editor”). Default: null.
    136122
    137123= Company Menu (Pro) =
     
    207193
    208194== Changelog ==
     195
     196= 1.7.0 (Pro) - 2023-10-2 =
     197* Update: Updated the invoice pay all functionality to leave the button disabled on AJAX success (through redirection to the cart).
     198* Update: Deprecated accp-file-list-shortcode-atts.php.
     199* Update: Deprecated accp-file-list-shortcode-vars.php.
     200* Update: Deprecated accp-invoice-list-shortcode-atts.php.
     201* Update: Deprecated ars-constellation-invoice-list-shortcode-vars.php.
     202* Update: Deprecated accp-file-list-due-date-past-due.php.
     203* Update: Deprecated accp-file-list-loop-vars.php.
     204* Update: Deprecated accp-file-list-pay-button.php.
     205* Update: Deprecated accp-invoice-list-due-date-past-due.php.
     206* Update: Deprecated accp-invoice-list-loop-vars.php.
     207* Update: Deprecated accp-invoice-list-pay-all-button.php.
     208* Update: Deprecated accp-invoice-list-pay-button.php.
     209* Update: Deprecated the accp-invoice-list-shortcode-includes dir.
     210* Update: Deprecated the accp-file-list-shortcode-includes dir.
     211* Update: Deprecated the premium admin dir is this will not be used.
     212* Feature: Added functionality to allow shortcodes to be genarated and saved as settings for easier implementation and editing.
     213* Update: Overhauled the pro file and invoice list shortcode framework for better maintainability and scalability, and for forthcoming features.
     214
     215= 1.7.0 (Core) - 2023-10-2 =
     216* Improvement: Updated the sanitize strings in array function to account for incorrect and null values.
     217* Update: Overhauled the core file and invoice list shortcode framework for better maintainability and scalability.
     218* Update: Deprecated the “list_id” shortcode param.  This now uses the auto-generated “data-list-id" value.  This is also not needed in the new pro saved shortcode framework.
     219* Update: Updated select2 to select2.full.
     220* Update: Updated Font Awesome to enqueue from a local plugin dir instead of via the CDN.  Also updated the Font Awesome version.
     221* Update: Updated the add settings sub page function to exit early for non-admin users to prevent notices on WP Admin for non-admin users.
    209222
    210223= 1.6.0 (Pro) - 2023-9-1 =
  • constellation-client-portal/trunk/admin/class-ars-constellation-client-portal-admin.php

    r2961762 r2973972  
    7272         * Enqueue Admin Styles
    7373         */
    74 
    7574        wp_enqueue_style( $this->plugin_name, plugin_dir_url( __FILE__ ) . 'css/ars-constellation-client-portal-admin.css', array(), $this->version, 'all' );       
    7675        wp_enqueue_style( $this->plugin_name.'-jquery-ui', plugin_dir_url( __FILE__ ) . 'css/jquery-ui/1.11.1/themes/cupertino/jquery-ui.css', array(), $this->version, 'all' );       
    7776               
    78         wp_enqueue_style( $this->plugin_name.'-selec2-css', plugin_dir_url( __FILE__ ) . 'css/select2.min.css', array(), $this->version, 'all' );       
    79        
    80         // Font Awesome
    81         if (!wp_style_is( 'fontawesome', 'enqueued' )) {
    82             wp_register_style( 'fontawesome', '//maxcdn.bootstrapcdn.com/font-awesome/4.6.1/css/font-awesome.min.css', false, '4.6.1' );
    83             wp_enqueue_style( 'fontawesome' );
    84         }
     77        wp_enqueue_style( $this->plugin_name.'-selec2-css', plugin_dir_url( __FILE__ ) . 'css/select2.min.css', array(), $this->version, 'all' );               
     78       
     79        /**
     80         * Conditionally enqueue Font Awesome CSS.
     81         */
     82        if( !wp_style_is('font-awesome', 'registered') ){
     83           
     84            wp_enqueue_style( 'accp-font-awesome-css', dirname( plugin_dir_url( __FILE__ ) ) . '/assets/css/font-awesome/css/all.min.css', array(), $this->version, 'all' );
     85
     86        }
     87
    8588    }
    8689
     
    9699        wp_enqueue_script( 'jquery-ui-datepicker' );
    97100
    98         wp_enqueue_script( $this->plugin_name . '-select2-js', plugin_dir_url( __FILE__ ) . 'js/select2.min.js', array( 'jquery' ), $this->version, false );       
     101        wp_enqueue_script( $this->plugin_name . '-select2-js', plugin_dir_url( __FILE__ ) . 'js/select2.full.min.js', array( 'jquery' ), $this->version, false );       
    99102       
    100103    }
     
    21362139
    21372140        wp_die();
     2141       
    21382142    }
    21392143   
  • constellation-client-portal/trunk/admin/class-ars-constellation-client-portal-settings.php

    r2961762 r2973972  
    7070    function add_accp_settings_pages_to_wp_admin(){
    7171
     72        if( !is_admin() || !is_user_logged_in() || !current_user_can('manage_options') )
     73            return;
     74
    7275        $defined_settings_pages = $this->get_defined_settings_pages();
     76
     77        if( !$defined_settings_pages || empty($defined_settings_pages) )
     78            return;
    7379
    7480        foreach( $defined_settings_pages as $slug => $settings_page ){         
     
    126132        $html .= '<div class="accp-admin-main-content-header">';       
    127133
    128         $html .=    '<h1>'.esc_html( $this->get_settings_page_title_from_url() ).'</h1>';
     134        $html .=    '<h1>'.esc_html( $this->get_settings_page_title() ).'</h1>';
    129135
    130136        $html .= '</div>';
     
    244250     * @return string $page_title - The title of the settings page.
    245251     */
    246     function get_settings_page_title_from_url(){
     252    function get_settings_page_title(){
    247253
    248254        /**
     
    253259        if( $title && !empty($title) )
    254260            return $title;
     261
     262        $is_pro = $this->utilities->is_pro_plugin($this->plugin_name);
    255263
    256264        if( $title == 'Settings' ){
     
    259267            $page_title = 'Settings';       
    260268        }
     269
    261270
    262271        /**
     
    466475
    467476
     477    function get_list_settings_page_content(){
     478
     479        if( !is_admin() || !is_user_logged_in() || !current_user_can('manage_options') )
     480            return;
     481
     482        $allowed_html = $this->get_customized_allowed_html_for_wp_kses();
     483        $is_pro = $this->utilities->is_pro_plugin($this->plugin_name);
     484        $html = '';             
     485       
     486        /**
     487         * Section html filter.
     488         */
     489        if( true === $is_pro ){
     490
     491            $html = apply_filters('accp_list_settings_page_section_html', $html);
     492
     493        }
     494
     495        if( !empty($html) ){                       
     496
     497            echo wp_kses( $this->generate_settings_page_html($html, false, false, false, false), $allowed_html );
     498
     499        }
     500
     501    }
     502
     503
    468504    function get_documentation_settings_page_content(){
    469505
     
    847883            $page_list['accp-company-settings'] = 'Companies';
    848884            $page_list['accp-email-settings'] = 'Email';
     885            $page_list['accp-list-settings'] = 'Lists';
    849886
    850887        }
     
    10931130            'multiple'    => array(),
    10941131            'required'    => array(),
     1132            'disabled'    => array(),
     1133            'size'        => array(),
     1134            'data-term-slug' => array(),           
    10951135        );
    10961136
  • constellation-client-portal/trunk/admin/css/ars-constellation-client-portal-admin.css

    r2961762 r2973972  
    409409}
    410410
     411#accp-shorcode-list-table-container{
     412    display: table;
     413    width: 100%;
     414    border-collapse: collapse;
     415}
     416
     417.accp-shortcode-col-heading-row,
     418.accp-saved-shortcode-item-row{
     419    display: table-row;
     420    height: 60px;
     421    border-bottom: 1px solid #eee;
     422}
     423
     424.accp-shortcode-col-heading {
     425    font-weight: bold;
     426    color: #777;
     427}
     428
     429.accp-add-shortcode-btn-container{
     430    text-align: right;
     431    margin-top: 15px;
     432}
     433
     434.accp-row-action-col-heading{
     435    visibility: hidden;
     436}
     437
     438.accp-shortcode-item-cell{
     439    display: table-cell;
     440    padding: 5px;
     441    vertical-align: middle;   
     442}
     443
     444.accp-shortcode-item-cell a{
     445    text-decoration: none;
     446}
     447
     448input.accp-copy-text-enabled {
     449    cursor: pointer;
     450    background-color: #eee;
     451    padding: 5px 7px 7px 7px;
     452    border-radius: 3px;
     453    border: none;
     454    text-align: center;
     455}
     456
     457.accp-shortcode-input-container{
     458    position: relative;
     459}
     460
     461.accp-shortcode-input-container:hover::after {
     462    display: block;
     463}
     464
     465.accp-shortcode-input-container::after {
     466    content: "\f0c5";
     467    font-family: "Font Awesome 5 Free";
     468    font-weight: 400;
     469    position: absolute;
     470    right: 5px;
     471    display: none;
     472}
     473
     474.accp-shortcode-input-container.accp-element-copied::after {
     475    content: "\f00c";
     476    font-family: "Font Awesome 5 Free";
     477    font-weight: 600;
     478    position: absolute;
     479    right: 5px;
     480    top: 0;
     481    color: #259d25; 
     482}
     483
    411484.accp-settings-tabs li:hover {
    412485    background-color: #fff;   
  • constellation-client-portal/trunk/ars-constellation-client-portal.php

    r2961762 r2973972  
    55 * Plugin URI:        https://adrianrodriguezstudios.com/constellation-client-portal/
    66 * Description:       Create private pages for each of your clients, post private files, and protect your client files from unauthorized users and search engines.  <strong>Important:</strong> All Site-level File Protection features will cease to function if the plugin is disabled or uninstalled.
    7  * Version:           1.6.0
     7 * Version:           1.7.0
    88 * Author:            ARS
    99 * Author URI:        https://adrianrodriguezstudios.com
     
    5555     */
    5656    define('ACCP_PLUGIN_NAME', 'ARS_CONSTELLATION_CLIENT_PORTAL');
    57     define('ACCP_PLUGIN_VERSION', '1.6.0'); // Change the version in the header as well.
     57    define('ACCP_PLUGIN_VERSION', '1.7.0'); // Change the version in the header as well.
    5858    define( ACCP_PLUGIN_NAME, ACCP_PLUGIN_VERSION );
    5959    define('ACCP_PLUGIN_FILE_NAME', __FILE__);
  • constellation-client-portal/trunk/includes/class-ars-constellation-client-portal.php

    r2961762 r2973972  
    127127        require_once plugin_dir_path( dirname( __FILE__ ) ) . 'admin/class-ars-constellation-client-portal-settings.php';
    128128        require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-ars-constellation-client-portal-utility-functions.php';
     129        require_once plugin_dir_path( dirname( __FILE__ ) ) . 'public/shortcodes/class-ars-constellation-client-portal-list-shortcodes.php';
    129130
    130131       
     
    201202        $plugin_authorization = new ARS_Constellation_Client_Portal_Core_Authorization( $this->get_plugin_name(), $this->get_version() );
    202203        $plugin_users = new ARS_Constellation_Client_Portal_Users( $this->get_plugin_name(), $this->get_version() );
    203         $core_settings = new ARS_Constellation_Client_Portal_Settings();
     204        $core_settings = new ARS_Constellation_Client_Portal_Settings();       
    204205
    205206        /* Core (Basic tier) hooks */
     
    495496
    496497        $plugin_public = new ARS_Constellation_Client_Portal_Public( $this->get_plugin_name(), $this->get_version() );
     498        $list_shortcodes = new ARS_Constellation_Client_Portal_List_Shortcodes;
    497499
    498500        $this->loader->add_action( 'wp_enqueue_scripts', $plugin_public, 'enqueue_styles' );
    499         $this->loader->add_action( 'wp_enqueue_scripts', $plugin_public, 'enqueue_scripts' );
    500        
     501        $this->loader->add_action( 'wp_enqueue_scripts', $plugin_public, 'enqueue_scripts' );       
    501502       
    502503        // Client File List shortcode - [accp_clientfiles]     
    503         $this->loader->add_shortcode( 'accp_clientfiles', $plugin_public, 'accp_client_files' );
     504        $this->loader->add_shortcode( 'accp_clientfiles', $list_shortcodes, 'get_client_files_shortcode' );
    504505
    505506        // Client Invoice List shortcode - [accp_clientinvoices]       
    506         $this->loader->add_shortcode( 'accp_clientinvoices', $plugin_public, 'accp_client_invoices' );
     507        $this->loader->add_shortcode( 'accp_clientinvoices', $list_shortcodes, 'get_client_invoices_shortcode' );
    507508       
    508509
     
    519520        }
    520521
    521         /* Premium tier hooks */
    522         if ( $this->plugin_name == 'ars-constellation-client-portal-premium' ){     
    523            
    524             // Include the Pro hooks
    525             $plugin_pro_public = new ARS_Constellation_Client_Portal_Pro_Public( $this->get_plugin_name(), $this->get_version() );
    526             require_once ( dirname(__DIR__)  . '/pro/public/ars-constellation-client-portal-pro-public-hooks.php'  );       
    527            
    528         }
    529 
     522       
    530523    }   
    531524
  • constellation-client-portal/trunk/public/class-ars-constellation-client-portal-public.php

    r2961762 r2973972  
    7373
    7474    }
    75 
    76 
    77     /**
    78      * Set up Client File List shortcode.
    79      *
    80      * Shortcode: [accp_clientfiles]
    81      *
    82      * @param array $atts - array of atts passed in via the shortcode.
    83      * @return string $html - the shortcode result.
    84      */
    85     function accp_client_files( $atts, $content = null ) {
    86 
    87         /**
    88          * Exit if the user is not logged in
    89          * or if this is WP Admin.
    90          */
    91         if ( !is_user_logged_in() || is_admin() )
    92             return;
    93 
    94         global $post;
    95        
    96         $post_id = get_the_ID();
    97         $user = wp_get_current_user();
    98         $user_id = get_current_user_id();       
    99         $roles_array = (array)$user->roles;
    100         $roles = array_map('strtolower', $roles_array);
    101         $list_instance = filter_var( $this->accp_generate_list_instance_id(), FILTER_SANITIZE_NUMBER_INT);
    102         $paged_param = 'paged' . $list_instance;
    103         $paged = isset( $_GET[$paged_param] ) ? (int)$_GET[$paged_param] : 1;       
    104         $authorized_company_id = $this->get_client_page_authorized_company_id_by_user_id($user_id, $post_id);
    105 
    106         /**
    107          * Exit if the $authorized_company_id is false.
    108          */
    109         if( false === $authorized_company_id || !$authorized_company_id )
    110             return;
    111 
    112         $current_date = date('Y-m-d');
    113        
    114        
    115         /**
    116          * Set up the core atts for the clientfile shortcode.
    117          */
    118         $atts_list_array = $this->accp_clientfile_core_shortcode_atts();
    119 
    120 
    121         /**
    122          * Conditionally add Pro Tier shortcode attributes.
    123          */
    124         if ( $this->plugin_name == 'ars-constellation-client-portal-pro' ){
    125             include dirname(__DIR__) . '/pro/public/accp-file-list-shortcode-atts.php';
    126         }
    127 
    128         /**
    129          * Output the shortcode attributes.
    130          */
    131         $atts = shortcode_atts($atts_list_array, $atts);       
    132 
    133 
    134         /**
    135          * List vars.
    136          */
    137 
    138         // File Status
    139         if( $atts['file_status'] != null){
    140 
    141             $file_status = strtolower($atts['file_status']);   
    142 
    143         }else{
    144 
    145             $file_status = '';
    146            
    147         }
    148 
    149         // List ID
    150         $list_id = $this->accp_list_id_var($atts);   
    151        
    152         // Category Filter
    153         $taxonomy = 'accp_file_categories';
    154         $categories = $this->accp_categories_var($atts, $taxonomy);
    155 
    156         // Posts per page
    157         $number_of_posts = $this->accp_number_of_posts_var($atts);         
    158        
    159         // Order posts by
    160         $order_by = $this->accp_order_by_var($atts);
    161        
    162         // Post order
    163         $order = $this->accp_order_var($atts);
    164        
    165         // Exerpt length       
    166         $excerpt_length = $this->accp_excerpt_length_var($atts);       
    167        
    168         // Thumbnail size       
    169         $thumbnail_size = $this->accp_thumbnail_size_var($atts);       
    170        
    171         // Thumbnail alignment     
    172         $align_thumbnail = $this->accp_align_thumbnail_var($atts) ? $this->accp_align_thumbnail_var($atts) : '';       
    173 
    174         // Link title
    175         $link_title = '';
    176 
    177         if( isset($atts['link_title']) &&
    178             !empty($atts['link_title']) &&
    179             trim( strtolower($atts['link_title']) ) === 'nolink'
    180         ){
    181 
    182             $link_title = 'nolink';
    183 
    184         }
    185 
    186         // Container ID
    187         $container_id = '';
    188 
    189         if( isset($atts['id']) && !empty($atts['id']) ){
    190 
    191             $container_id = trim($atts['id']);
    192             $container_id = str_replace(' ', '', $container_id);
    193 
    194         }
    195 
    196         // Container Classes
    197         $container_classes = '';
    198 
    199         if( isset($atts['class']) && !empty($atts['class']) ){
    200 
    201             $container_classes = trim($atts['class']);
    202 
    203         }
    204 
    205         /**
    206          * Set up Pro Tier vars
    207          */
    208         if ( $this->plugin_name == 'ars-constellation-client-portal-pro' || $this->plugin_name == 'ars-constellation-client-portal-premium' ){
    209             include dirname(__DIR__) . '/pro/public/accp-file-list-shortcode-vars.php';
    210         }
    211        
    212        
    213         /**
    214          * Hook - Allow content to be added before
    215          * the file list.
    216          *
    217          * @param $post_id - ID of the page that contains the client file shortcode.       
    218          */
    219         $before_loop_content = do_action('accp_before_file_list', $post_id);
    220 
    221         if($before_loop_content){
    222             echo wp_kses_post($before_loop_content);
    223         }
    224 
    225         /**
    226          * File List
    227          */
    228         ob_start();     
    229         ?>     
    230        
    231         <div <?php echo !empty($container_id) ? 'id="'. esc_attr($container_id).'"' : ''; ?> class="accp_documents_filelist <?php echo !empty($container_classes) ? esc_attr($container_classes) : ''; ?>" <?php echo ( $list_id != null ? ' data-accp-rel-list="' . esc_attr($list_id) . '"' : '' ); ?> data-list-id="<?php echo esc_attr($list_instance); ?>">
    232         <?php           
    233            
    234             /**
    235              * Generate the file query.
    236              */
    237             $args = $this->accp_generate_file_query_args($categories, $number_of_posts, $paged, $order_by, $order, $authorized_company_id, $file_status);       
    238             $query = new WP_Query( $args );
    239 
    240             $html = '';     
    241            
    242             if ($query->have_posts()):         
    243 
    244                 while ( $query->have_posts() ):
    245                    
    246                     $query->the_post();             
    247 
    248                     $accp_file = get_post_meta($post->ID, 'accp_file', true);   
    249                     $file_post_id = get_the_ID();               
    250                    
    251                     /**
    252                      * Get the Company ID associated with the file.
    253                      */
    254                     $file_post_company_id = get_post_meta($file_post_id, 'accp_user', true );
    255 
    256 
    257                     /**
    258                      * Check if pro access checks need to be instantiated.
    259                      */       
    260                     if ( $this->plugin_name == 'ars-constellation-client-portal-pro' ){                 
    261                        
    262                         $authorization = new ARS_Constellation_Client_Portal_Pro_Authorization( $this->plugin_name, $this->version );
    263                         $check_authorization = $authorization->verify_page_or_post_authorization_pro($file_post_id, $user_id);                     
    264 
    265                     }else{                     
    266 
    267                         /**
    268                          * Use the default file check if this is the Core version
    269                          * to determine if access should be granted.
    270                          */
    271                         $authorization = new ARS_Constellation_Client_Portal_Core_Authorization( $this->plugin_name, $this->version );
    272                         $check_authorization = $authorization->verify_page_or_post_authorization($file_post_id, $user_id);
    273 
    274                     }               
    275                            
    276                     if( $check_authorization === true ){
    277 
    278                         /**
    279                          * Hook - Allow content to be added before
    280                          * the file list item.
    281                          *
    282                          * @param $item_id - The ID of the file post in the loop.
    283                          */
    284                         $item_id = $file_post_id;
    285                         $before_item_content = do_action('accp_before_file_list_item', $item_id);
    286 
    287                         if($before_item_content){
    288                             echo wp_kses_post($before_item_content);
    289                         }                               
    290                         ?>
    291 
    292                         <div class="accp-item-container clearfix">
    293 
    294                             <?php
    295                             /**
    296                              * Hook - Allow content to be added to
    297                              * the top of the file list item.
    298                              *
    299                              * @param $item_id - ID of the file post in the loop.
    300                              */
    301                             $item_id = $file_post_id;
    302                             $top_item_content = do_action('accp_file_list_item_top_inside', $item_id);
    303 
    304                             if($top_item_content){
    305                                 echo wp_kses_post($top_item_content);
    306                             }                           
    307 
    308                             if($link_title !== 'nolink'):
    309                             ?>
    310                                
    311                                 <span class="accp-file-list-item-title"><a href="<?php the_permalink(); ?>"><?php the_title(); ?></a></span>
    312 
    313                             <?php
    314                             else:
    315                             ?>
    316 
    317                                 <span class="accp-file-list-item-title"><?php the_title(); ?></span>
    318 
    319                             <?php
    320                             endif;
    321                             ?>             
    322                            
    323                             <div class="accp-list-item-meta">     
    324                            
    325                                 <?php // Post Date ?>
    326 
    327                                 <?php           
    328                                 if( $atts['show_post_date'] == true && $atts['show_post_date'] !== null){
    329                                        
    330                                     ?>
    331                                     <div class="accp-file-post-date">
    332                                         <?php echo esc_html(get_the_date()); ?>
    333                                     </div>
    334                                     <?php
    335                                    
    336                                 }
    337                                 ?>
    338 
    339                                 <?php // Pro - Due Date and Past Due Elements ?>
    340                                
    341                                 <?php
    342                                 if ( $this->plugin_name == 'ars-constellation-client-portal-pro' || $this->plugin_name == 'ars-constellation-client-portal-premium' ){
    343                                     include dirname(__DIR__) . '/pro/public/accp-file-list-shortcode-includes/accp-file-list-due-date-past-due.php';
    344                                 }
    345                                 ?>
    346 
    347                             </div>
    348                                
    349                             <? // Thumbnail ?>
    350 
    351                             <div class="file-loop-thumbnail file-thumb-align<?php echo esc_attr($align_thumbnail); ?>">             
    352                             <?php                               
    353                                
    354                                 if( $atts['show_thumbnail'] == true){   
    355 
    356                                     if ($thumbnail_size != null){
    357 
    358                                         echo wp_kses_post( get_the_post_thumbnail($post->ID, $thumbnail_size) );
    359 
    360                                     }else{
    361 
    362                                         echo wp_kses_post( get_the_post_thumbnail() );
    363 
    364                                     }
    365                                        
    366                                 }
    367                                 ?>
    368                            
    369                             </div>
    370                            
    371                             <?php // Excerpt ?>
    372                            
    373                             <?php
    374                             $excerpt_html = $this->accp_file_and_invoice_excerpt_html($file_post_id, $atts, $excerpt_length);
    375 
    376                             echo wp_kses_post($excerpt_html);                       
    377 
    378                             // Prepare list of term slugs - TODO: allow for categories to be displayed in the loop.
    379                             $get_post_terms = get_the_terms($post->ID, 'accp_file_categories');
    380 
    381                             if( $get_post_terms ){
    382 
    383                                 foreach ( $get_post_terms as $term) {
    384 
    385                                     $term_list_array[] = $term->slug;
    386 
    387                                 }
    388 
    389                             }                   
    390                             ?>
    391 
    392                             <div class="accp-view-dl-link-container">                   
    393 
    394                                 <?php                               
    395                                 $file_dl_nonce = wp_create_nonce('file_download');
    396                                 $url_params = get_site_url() . '/?accp-dl-id=' . $file_post_id;                             
    397                                 ?>                         
    398 
    399                                 <?php if( $accp_file && $accp_file['url'] ): ?>
    400 
    401                                     <a href="<?php echo esc_url($accp_file['url']);?>" class="view-print accp-file-view-print" target="_blank">View and Print</a> <span class="accp-view-download-separator">|</span>
    402                                    
    403                                     <a href="<?php echo esc_url($url_params);?>" class="download accp-file-download" data-file-id="<?php echo esc_attr($file_post_id); ?>" data-nonce="<?php echo esc_attr($file_dl_nonce); ?>" target="_blank" download>Download</a>
    404                                
    405                                 <?php endif; ?>
    406                                
    407                             </div>
    408 
    409 
    410                             <?php
    411                             /**
    412                              * Hook - Allow content to be added to
    413                              * the bottom of the file list item.
    414                              *
    415                              * @param $item_id - ID of the file post in the loop.
    416                              */
    417                             $item_id = $file_post_id;
    418                             $bottom_item_content = do_action('accp_file_list_item_bottom_inside', $item_id);
    419 
    420                             if($bottom_item_content){
    421                                 echo wp_kses_post($bottom_item_content);
    422                             }                           
    423                             ?>
    424 
    425                         </div>           
    426                         <?php
    427                        
    428                         /**
    429                          * Hook - Allow content to be added after
    430                          * the file list item.
    431                          *
    432                          * @param $item_id - ID of the file post in the loop.
    433                          */
    434                         $item_id = $file_post_id;
    435                         $after_item_content = do_action('accp_after_file_list_item', $item_id);
    436 
    437                         if($after_item_content){
    438                             echo wp_kses_post($after_item_content);
    439                         }
    440                                
    441                     }   
    442                    
    443                 endwhile;
    444                
    445                 wp_reset_postdata();
    446 
    447             endif;
    448 
    449             /**
    450              * Hook - Allow content to be added after
    451              * the file list.
    452              *
    453              * @param $post_id - ID of the page that contains the client file shortcode.           
    454              */
    455             $after_loop_content = do_action('accp_after_file_list', $post_id);
    456 
    457             if($after_loop_content){
    458                 echo wp_kses_post($after_loop_content);
    459             }           
    460            
    461            
    462             /**
    463              * Page Nav
    464              */
    465             $page_args = array(
    466                 'format'  => '?'.$paged_param.'=%#%',
    467                 'current' => $paged,
    468                 'total'   => $query->max_num_pages,                 
    469             );
    470 
    471             if ( paginate_links( $page_args) ){
    472 
    473                 ?>         
    474                 <div class="accp-page-nav-container" <?php echo ( $list_id != null ? 'data-accp-rel-list="' . esc_attr($list_id) . '"' : '' ); ?>>
    475                
    476                     <?php                   
    477                     echo wp_kses_post(paginate_links( $page_args ));
    478                     ?>
    479                
    480                 </div>         
    481                 <?php
    482            
    483             }
    484 
    485             /**
    486              * Hook - Allow content to be added after
    487              * the file list pagination element.
    488              *
    489              * This is added whether the the pagination element exists or not.
    490              *
    491              * @param $post_id - ID of the page that contains the client file shortcode.           
    492              */
    493             $after_loop_pagination = do_action('accp_after_file_list_pagination', $post_id);
    494 
    495             if($after_loop_pagination){
    496                 echo wp_kses_post($after_loop_pagination);
    497             }   
    498 
    499             $html .= ob_get_clean();
    500        
    501         $html .= '</div>';
    502 
    503         return $html;
    504     }
    505 
    506 
    507     /**
    508      * Generate file query args.
    509      *
    510      * @param array $categories - array of category ID's.
    511      * @param int $number_of_posts - number of posts to show in the shortcode loop.
    512      * @param int $paged - the query args paged value.
    513      * @param string $order_by - the query args order_by value.
    514      * @param string $order - the query args order value.
    515      * @param int $authorized_company_id - post ID for the authorized company.
    516      * @param string $file_status - file status value.
    517      * @return array $args - array of args for the file query. 
    518      */
    519     function accp_generate_file_query_args($categories, $number_of_posts, $paged, $order_by, $order, $authorized_company_id, $file_status){
    520 
    521         /**
    522          * Add a tax_query if the 'categories' att is not empty.
    523          */
    524         $tax_query = array();
    525            
    526         if(!empty($categories)){           
    527 
    528             $tax_query[] = array(
    529                 'taxonomy' => 'accp_file_categories',
    530                 'field' => 'id',
    531                 'terms' => $categories,             
    532             );
    533            
    534         }
    535 
    536         $meta_query = array();
    537        
    538         /**
    539          * Add the file status to the meta_query
    540          * if it's not empty.
    541          */
    542         if(!empty($file_status)){       
    543 
    544             $meta_query['relation'] = 'AND';
    545 
    546             $meta_query[] = array(         
    547                 'key' => 'file_status',
    548                 'value' => $file_status         
    549             );
    550 
    551         }
    552 
    553         $meta_query[] = array(         
    554             'key' => 'accp_user',
    555             'value' => $authorized_company_id             
    556         );
    557        
    558         $args = array(
    559             'post_type' => 'accp_clientfile',
    560             'posts_per_page' => $number_of_posts,       
    561             'paged' => $paged, 
    562             'orderby' => $order_by,           
    563             'order' => $order,
    564             'meta_query' => $meta_query,
    565             'tax_query' => $tax_query,             
    566         );     
    567 
    568         return $args;
    569 
    570     }
    571 
    572     /**
    573      * Set up the core atts for the clientfile shortcode.
    574      *
    575      * @return array $atts_list_array - array of defined shortcode atts.
    576      */
    577     function accp_clientfile_core_shortcode_atts(){
    578 
    579         $atts_list_array  = array(
    580             'id' => '', // Optional ID for the accp_documents_filelist list div.  Defaults to null.
    581             'class' => '', // Optional additional class(es) for the accp_documents_filelist list div.  Defaults to null.
    582             'categories' => '', // Category atts can be entered as the Slug or ID in the shortcode
    583             'file_status' => '', // File status to show - file status slug or null. Defaults to null.
    584             'display_number' => '', // This is the number of posts per page
    585             'order_by' => '', // This allows ordering by post title - default is post date - options "title" or "date"
    586             'order' => '', // This can be set as ASC or DESC - default is DESC     
    587             'show_excerpt' => '', // Displays truncated text from the post content field
    588             'show_thumbnail' => '', // Displays the posts featured image in the loop
    589             'excerpt_length' => '', // Accepts the number of words for the excerpt
    590             'thumbnail_size' => '', // Enter the thumbnail slug defined in the theme
    591             'align_thumbnail' => '', // center, left, right, float-left, float-right
    592             'show_post_date' => '', // Display the post date - default is false     
    593             'list_id' => '', // Integer - Useful when there are multiple shortcode lists on the same page - default is null
    594             'link_title' => '' // nolink or empty.  Used to disable post link titles - default is null.
    595         );
    596 
    597         return $atts_list_array;
    598 
    599     }
    600 
    601     /* End client file list shortcode */
    602 
    603 
    604     /**
    605      * Set up Client Invoice List shortcode.
    606      *
    607      * Shortcode: [accp_clientinvoices]
    608      *
    609      * @param array $atts - array of atts passed in via the shortcode.
    610      * @return string $html - the shortcode result.
    611      */
    612     function accp_client_invoices( $atts, $content = null ) {
    613 
    614         /**
    615          * Exit if the user is not logged in
    616          * or if this is WP Admin.
    617          */
    618         if ( !is_user_logged_in() || is_admin() )
    619             return;
    620 
    621         global $post;       
    622        
    623         $post_id = get_the_ID();
    624         $user = wp_get_current_user();
    625         $user_id = get_current_user_id();       
    626         $roles_array = ( array ) $user->roles;
    627         $roles = array_map('strtolower', $roles_array);
    628         $list_instance = filter_var( $this->accp_generate_list_instance_id(), FILTER_SANITIZE_NUMBER_INT);
    629         $paged_param = 'paged' . $list_instance;
    630         $paged = isset( $_GET[$paged_param] ) ? (int)$_GET[$paged_param] : 1;
    631 
    632         $authorized_company_id = $this->get_client_page_authorized_company_id_by_user_id($user_id, $post_id);
    633 
    634         /**
    635          * Exit if the $authorized_company_id is false.
    636          */
    637         if( false === $authorized_company_id || !$authorized_company_id )
    638             return;
    639 
    640         $current_date = date('Y-m-d');
    641        
    642        
    643         /**
    644          * Set up the Basic Tier File List shortcode attributes.
    645          */
    646         $atts_list_array  = $this->accp_clientinvoice_core_shortcode_atts();
    647 
    648 
    649         /**
    650          * Conditionally add Pro Tier shortcode attributes.
    651          */
    652         if ( $this->plugin_name == 'ars-constellation-client-portal-pro' ){
    653             include dirname(__DIR__) . '/pro/public/accp-invoice-list-shortcode-atts.php';
    654         }
    655 
    656 
    657         /**
    658          * Output the shortcode attributes
    659          */
    660         $atts = shortcode_atts($atts_list_array, $atts);       
    661    
    662 
    663         /**
    664          * List vars.
    665          */
    666 
    667         // Invoice Status
    668         if( $atts['invoice_status'] != null){
    669 
    670             $invoice_status = strtolower($atts['invoice_status']); 
    671 
    672         }else{
    673 
    674             $invoice_status = 'unpaid';
    675 
    676         } 
    677 
    678         // List ID
    679         $list_id = $this->accp_list_id_var($atts);
    680        
    681         // Category Filter
    682         $taxonomy = 'accp_invoice_categories';
    683         $categories = $this->accp_categories_var($atts, $taxonomy);             
    684 
    685         // Posts per page
    686         $number_of_posts = $this->accp_number_of_posts_var($atts);     
    687        
    688         // Order posts by
    689         $order_by = $this->accp_order_by_var($atts);
    690        
    691         // Post order
    692         $order = $this->accp_order_var($atts);
    693        
    694         // Exerpt length
    695         $excerpt_length = $this->accp_excerpt_length_var($atts);
    696        
    697         // Thumbnail size
    698         $thumbnail_size = $this->accp_thumbnail_size_var($atts);
    699        
    700         // Thumbnail alignment
    701         $align_thumbnail = $this->accp_align_thumbnail_var($atts) ? $this->accp_align_thumbnail_var($atts) : '';   
    702 
    703         // Link title
    704         $link_title = '';
    705 
    706         if( isset($atts['link_title']) &&
    707             !empty($atts['link_title']) &&
    708             trim( strtolower($atts['link_title']) ) === 'nolink'
    709         ){
    710 
    711             $link_title = 'nolink';
    712 
    713         }
    714 
    715         // Container ID
    716         $container_id = '';
    717 
    718         if( isset($atts['id']) && !empty($atts['id']) ){
    719 
    720             $container_id = trim($atts['id']);
    721             $container_id = str_replace(' ', '', $container_id);
    722 
    723         }
    724 
    725         // Container Classes
    726         $container_classes = '';
    727 
    728         if( isset($atts['class']) && !empty($atts['class']) ){
    729 
    730             $container_classes = trim($atts['class']);
    731 
    732         }
    733 
    734         /**
    735          * Set up Pro Tier vars
    736          */
    737         if ( $this->plugin_name == 'ars-constellation-client-portal-pro' || $this->plugin_name == 'ars-constellation-client-portal-premium' ){
    738             include dirname(__DIR__) . '/pro/public/ars-constellation-invoice-list-shortcode-vars.php';
    739         }
    740        
    741        
    742         /**
    743          * Hook - Allow content to be added before
    744          * the invoice list.
    745          *
    746          * @param $post_id - ID of the page that contains the client invoice shortcode.
    747          */
    748         $before_loop_content = do_action('accp_before_invoice_list', $post_id);
    749 
    750         if($before_loop_content){
    751             echo wp_kses_post($before_loop_content);
    752         }
    753 
    754         /**
    755          * Invoice List
    756          */
    757         ob_start();
    758         ?>
    759        
    760         <div <?php echo !empty($container_id) ? 'id="'. esc_attr($container_id).'"' : ''; ?> class="accp_documents_filelist <?php echo !empty($container_classes) ? esc_attr($container_classes) : ''; ?>" <?php echo ( $list_id != null ? ' data-accp-rel-list="' . esc_attr($list_id) . '"' : '' ); ?> data-list-id="<?php echo esc_attr($list_instance); ?>">
    761         <?php                       
    762 
    763             /**
    764              * Generate invoice query.
    765              */
    766             $args = $this->accp_generate_invoice_query_args($categories, $number_of_posts, $paged, $order_by, $order, $authorized_company_id, $invoice_status);
    767             $query = new WP_Query( $args );
    768             $html = '';
    769            
    770             if ($query->have_posts()):
    771                
    772                 $invoice_id_list = array();
    773                
    774                 while ( $query->have_posts()):
    775 
    776                     $query->the_post();                             
    777 
    778                     $accp_file = get_post_meta($post->ID, 'accp_file', true);   
    779                     $file_post_id = get_the_ID();
    780                     $invoice_woo_product_id = get_post_meta($file_post_id, 'accp_woo_inv_id', true);
    781 
    782                     /**
    783                      * Only add the invoice post id to the list of payable invoices
    784                      * if the post has a WooCommerce product ID saved to it.
    785                      */
    786                     if($invoice_woo_product_id){
    787                         $invoice_id_list[] = $file_post_id;
    788                     }
    789 
    790                    
    791                     /**
    792                      * Get the Company ID associated with the file.
    793                      */
    794                     $file_post_company_id = get_post_meta($file_post_id, 'accp_user', true );
    795 
    796                    
    797                     /**
    798                      * Check if pro access checks need to be instantiated.
    799                      */       
    800                     if ( $this->plugin_name == 'ars-constellation-client-portal-pro' ){                     
    801                        
    802                         $authorization = new ARS_Constellation_Client_Portal_Pro_Authorization( $this->plugin_name, $this->version );
    803                         $check_authorization = $authorization->verify_page_or_post_authorization_pro($file_post_id, $user_id);                     
    804 
    805                     }else{                     
    806 
    807                         /**
    808                          * Use the default file check if this is the Core version
    809                          * to determine if access should be granted.
    810                          */
    811                         $authorization = new ARS_Constellation_Client_Portal_Core_Authorization( $this->plugin_name, $this->version );
    812                         $check_authorization = $authorization->verify_page_or_post_authorization($file_post_id, $user_id);
    813 
    814                     }
    815                                        
    816                     if( $check_authorization === true ){
    817 
    818                         /**
    819                          * Hook - Allow content to be added before
    820                          * the invoice list item.
    821                          *
    822                          * @param $item_id - ID of the invoice post in the loop.
    823                          */
    824                         $item_id = $file_post_id;
    825                         $before_item_content = do_action('accp_before_invoice_list_item', $item_id);
    826 
    827                         if($before_item_content){
    828                             echo wp_kses_post($before_item_content);
    829                         }
    830                        
    831                         ?>                 
    832                         <div class="accp-item-container clearfix">
    833 
    834                             <?php
    835                             /**
    836                              * Hook - Allow content to be added to
    837                              * the top of the invoice list item.
    838                              *
    839                              * @param $item_id - ID of the invoice post in the loop.
    840                              */
    841                             $item_id = $file_post_id;
    842                             $top_item_content = do_action('accp_invoice_list_item_top_inside', $item_id);
    843 
    844                             if($top_item_content){
    845                                 echo wp_kses_post($top_item_content);
    846                             }
    847 
    848                             if($link_title !== 'nolink'):
    849                             ?>
    850                                
    851                                 <span class="accp-file-list-item-title"><a href="<?php the_permalink(); ?>"><?php the_title(); ?></a></span>
    852 
    853                             <?php
    854                             else:
    855                             ?>
    856 
    857                                 <span class="accp-file-list-item-title"><?php the_title(); ?></span>
    858 
    859                             <?php
    860                             endif;
    861                             ?>         
    862                            
    863                             <div class="accp-list-item-meta">     
    864                            
    865                             <?php // Post Date ?>
    866 
    867                             <?php           
    868                             if( $atts['show_post_date'] == true && $atts['show_post_date'] !== null){
    869                                 ?>
    870                                 <div class="accp-file-post-date">
    871                                     <?php echo esc_html(get_the_date()); ?>
    872                                 </div>
    873                                 <?php
    874                             }
    875                             ?>
    876 
    877                             <?php // Pro - Due Date and Past Due Elements ?>
    878                             <?php
    879                             if ( $this->plugin_name == 'ars-constellation-client-portal-pro' || $this->plugin_name == 'ars-constellation-client-portal-premium' ){
    880                                 include dirname(__DIR__) . '/pro/public/accp-invoice-list-shortcode-includes/accp-invoice-list-due-date-past-due.php';
    881                             }
    882                             ?>
    883 
    884                             </div>
    885                                
    886                             <? // Thumbnail ?>
    887                             <div class="file-loop-thumbnail file-thumb-align<?php echo esc_attr($align_thumbnail); ?>">                 
    888                             <?php                       
    889                            
    890                             if( $atts['show_thumbnail'] == true){   
    891 
    892                                 if ($thumbnail_size != null){
    893 
    894                                     echo wp_kses_post( get_the_post_thumbnail($post->ID, $thumbnail_size) );
    895 
    896                                 }else{
    897 
    898                                     echo wp_kses_post( get_the_post_thumbnail() );
    899 
    900                                 }
    901                                    
    902                             }
    903                             ?>
    904                            
    905                             </div>
    906                            
    907                             <?php // Excerpt ?>
    908 
    909                             <?php
    910                             $excerpt_html = $this->accp_file_and_invoice_excerpt_html($file_post_id, $atts, $excerpt_length);
    911 
    912                             echo wp_kses_post($excerpt_html);
    913                            
    914                             /**
    915                              * Display 'Invoice - Paid' if the invoice status is paid.
    916                              */
    917                             $saved_invoice_status = get_post_meta($post->ID, 'invoice_status', true);
    918 
    919                             if($saved_invoice_status === 'paid'){
    920 
    921                                 ?>
    922                                 <span class="report-status">Paid</span>
    923                                 <?php
    924                                
    925                             }
    926 
    927                             // Post Terms
    928                             $get_post_terms = get_the_terms($post->ID, 'accp_invoice_categories');             
    929 
    930                             if($get_post_terms){
    931 
    932                                 foreach ( $get_post_terms as $term) {
    933 
    934                                     $term_list_array[] = $term->slug;
    935 
    936                                 }
    937 
    938                                 if($saved_invoice_status === 'paid'){
    939                                    
    940                                     /*
    941                                     ?>
    942                                     <span class="accp-post-terms">
    943                                        
    944                                         <ul><?php echo wp_kses_post( get_the_term_list( $post->ID, 'accp_invoice_categories', '<li>', ', ', '</li>' ) ); ?></ul>
    945 
    946                                     </span>
    947                                     <?php
    948                                     */
    949 
    950                                 }
    951 
    952                             }
    953                             ?>
    954 
    955                             <div class="accp-view-dl-link-container">                   
    956 
    957                                 <?php                               
    958                                 $invoice_dl_nonce = wp_create_nonce('invoice_download');
    959                                 $url_params = get_site_url() . '/?accp-dl-id=' . $file_post_id;                             
    960                                 ?>
    961                                
    962                                 <?php if($accp_file && $accp_file['url']): ?>
    963 
    964                                     <a href="<?php echo esc_url($accp_file['url']);?>" class="view-print" target="_blank">View and Print</a> <span class="accp-view-download-separator">|</span>
    965                                    
    966                                     <a href="<?php echo esc_url($url_params);?>" class="download accp-file-download" data-file-id="<?php echo esc_attr($file_post_id); ?>" data-nonce="<?php echo esc_attr($invoice_dl_nonce); ?>" target="_blank" download>Download</a>
    967 
    968                                 <?php endif; ?>                                         
    969                                
    970                             </div>
    971 
    972                             <?php // Pro - Pay Button Element ?>
    973                             <?php
    974                             if ( $this->plugin_name == 'ars-constellation-client-portal-pro' || $this->plugin_name == 'ars-constellation-client-portal-premium' ){
    975                                    
    976                                 if($saved_invoice_status === 'unpaid'){
    977                                     include dirname(__DIR__) . '/pro/public/accp-invoice-list-shortcode-includes/accp-invoice-list-pay-button.php';
    978                                 }
    979 
    980                             }
    981                             ?>
    982                            
    983                             <?php
    984                             /**
    985                              * Hook - Allow content to be added to
    986                              * the bottom of the invoice list item.
    987                              *
    988                              * @param $item_id - ID of the invoice post in the loop.
    989                              */
    990                             $item_id = $file_post_id;
    991                             $bottom_item_content = do_action('accp_invoice_list_item_bottom_inside', $item_id);
    992 
    993                             if($bottom_item_content){
    994                                 echo wp_kses_post($bottom_item_content);
    995                             }                           
    996                             ?>
    997 
    998                         </div>                 
    999                         <?php
    1000 
    1001                         /**
    1002                          * Hook - Allow content to be added after
    1003                          * the invoice list item.
    1004                          *
    1005                          * @param $item_id - ID of the invoice post in the loop.
    1006                          */
    1007                         $item_id = $file_post_id;
    1008                         $after_item_content = do_action('accp_after_invoice_list_item', $item_id);
    1009 
    1010                         if($after_item_content){
    1011                             echo wp_kses_post($after_item_content);
    1012                         }
    1013 
    1014                     }       
    1015                    
    1016                 endwhile;
    1017 
    1018                 // Pro - Pay-All Button Element
    1019                 if ( $this->plugin_name == 'ars-constellation-client-portal-pro' || $this->plugin_name == 'ars-constellation-client-portal-premium' ){
    1020                     include dirname(__DIR__) . '/pro/public/accp-invoice-list-shortcode-includes/accp-invoice-list-pay-all-button.php';
    1021                 }               
    1022                
    1023                 wp_reset_postdata();
    1024 
    1025             endif;
    1026 
    1027 
    1028             /**
    1029              * Hook - Allow content to be added after
    1030              * the invoice list.
    1031              *
    1032              * @param $post_id - ID of the page that contains the client invoice shortcode.
    1033              */
    1034             $after_loop_content = do_action('accp_after_invoice_list', $post_id);
    1035 
    1036             if($after_loop_content){
    1037                 echo wp_kses_post($after_loop_content);
    1038             }
    1039            
    1040            
    1041             /**
    1042              * Page Nav
    1043              */
    1044             $page_args1 = array(
    1045                 'format'  => '?'.$paged_param.'=%#%',
    1046                 'current' => $paged,
    1047                 'total'   => $query->max_num_pages                 
    1048             );
    1049            
    1050             if ( paginate_links($page_args1) ){
    1051            
    1052                 ?>         
    1053                 <div class="accp-page-nav-container" <?php echo ( $list_id != null ? 'data-accp-rel-list="' . esc_attr($list_id) . '"' : '' ); ?>>         
    1054                
    1055                     <?php                               
    1056                     echo wp_kses_post(paginate_links( $page_args1 ));       
    1057                     ?>
    1058                
    1059                 </div>         
    1060                 <?php
    1061 
    1062             }
    1063            
    1064             /**
    1065              * Hook - Allow content to be added after
    1066              * the invoice list pagination element.
    1067              *
    1068              * This is added whether the the pagination element exists or not.
    1069              *
    1070              * @param $post_id - ID of the page that contains the client file shortcode.           
    1071              */
    1072             $after_loop_pagination = do_action('accp_after_invoice_list_pagination', $post_id);
    1073 
    1074             if($after_loop_pagination){
    1075                 echo wp_kses_post($after_loop_pagination);
    1076             }
    1077 
    1078             $html .= ob_get_clean();
    1079 
    1080         $html .= '</div>';
    1081 
    1082         return $html;
    1083 
    1084     }
    1085 
    1086 
    1087     /**
    1088      * Get the authorized company ID for a given user.
    1089      *
    1090      * This ID is used for generating file and invoice
    1091      * post loops for the specified company(ID).
    1092      *
    1093      * @param int $user_id - The user ID of the respective user.
    1094      * @param int $post_id - The ID of the current Client Page.
    1095      *
    1096      * @return int|bool $authorized_company_id|false - The post ID of the company that the user has
    1097      * access to.
    1098      */
    1099     function get_client_page_authorized_company_id_by_user_id($user_id, $post_id){
    1100 
    1101         if( !$user_id || !$post_id)
    1102             return false;
    1103 
    1104         /**
    1105          * Get the primary Company ID associated with the current user.
    1106          */
    1107         $user_primary_company_id = get_user_meta( $user_id, 'client_company', true );       
    1108 
    1109         /**
    1110          * Get additonal companies assigned to the user (if any).
    1111          */
    1112         $additional_assigned_companies = get_user_meta($user_id, 'client_additional_company', true);
    1113 
    1114         /**
    1115          * Check if this is a Client page set to global
    1116          * access before checking for a saved company.
    1117          *
    1118          * Only valid for Client Page post types,
    1119          * and not Client Files, Client Invoices, or
    1120          * direct file access.
    1121          */
    1122         $core_authorization = new ARS_Constellation_Client_Portal_Core_Authorization( $this->plugin_name, $this->version );
    1123         $is_global_page = $core_authorization->is_global_company_page($post_id);
    1124 
    1125         if( true === $is_global_page ){
    1126 
    1127             /**
    1128              * If this is a global page, verify that the current user
    1129              * only has a single company assigned, otherwise return false.
    1130              *
    1131              * Global pages are only suitable for users that have a single
    1132              * company assigned.
    1133              */
    1134             if( $user_primary_company_id && $additional_assigned_companies && !empty($additional_assigned_companies) )
    1135                 return false;
    1136 
    1137             if( !$user_primary_company_id && $additional_assigned_companies && count($additional_assigned_companies) > 1 )
    1138                 return false;
    1139 
    1140             /**
    1141              * Otherwise set the $authorized_company_id to the
    1142              * user primary company ID, or a single additonal company
    1143              * if the primary company is not set, and only a single
    1144              * additional company is set.
    1145              */
    1146             if($user_primary_company_id){
    1147 
    1148                 $authorized_company_id = (int)$user_primary_company_id;
    1149 
    1150                 return $authorized_company_id;
    1151 
    1152             }
    1153 
    1154             if( !empty($additional_assigned_companies) && is_array($additional_assigned_companies) && count($additional_assigned_companies) === 1 ){
    1155 
    1156                 $authorized_company_id = (int)$additional_assigned_companies[0];
    1157 
    1158                 return $authorized_company_id;
    1159 
    1160             }
    1161 
    1162         }
    1163 
    1164 
    1165         /**
    1166          * Get the Company id of the current page if
    1167          * this is not a global page.
    1168          */
    1169         $page_company_id = get_post_meta($post_id, 'accp_user', true);
    1170 
    1171         if(!$page_company_id)
    1172             return false;
    1173 
    1174         if ( $additional_assigned_companies && !empty($additional_assigned_companies) && in_array($page_company_id, $additional_assigned_companies) ){
    1175            
    1176             $additional_company_id = $page_company_id;
    1177 
    1178         }else{
    1179 
    1180             $additional_company_id = '';
    1181             $additional_assigned_companies = array();
    1182 
    1183         }
    1184 
    1185         if ( $additional_company_id && !empty($additional_company_id) ){
    1186            
    1187             $authorized_company_id = (int)$additional_company_id;
    1188 
    1189         }else{
    1190            
    1191             $authorized_company_id = $user_primary_company_id ? (int)$user_primary_company_id : false;
    1192 
    1193         }
    1194 
    1195         /**
    1196          * Admins have access to all companies, so just
    1197          * return the current Client Page ID as the authorized
    1198          * company ID if the current user is an admin.
    1199          */
    1200         if( current_user_can('manage_options') ){
    1201 
    1202             $authorized_company_id = $page_company_id;
    1203             $additional_assigned_companies = array();
    1204 
    1205             return $authorized_company_id;
    1206 
    1207         }
    1208 
    1209         return $authorized_company_id;
    1210 
    1211     }
    1212 
    1213 
    1214     /**
    1215      * Generate invoice query args.
    1216      *
    1217      * @param array $categories - array of category ID's.
    1218      * @param int $number_of_posts - number of posts to show in the shortcode loop.
    1219      * @param int $paged - the query args paged value.
    1220      * @param string $order_by - the query args order_by value.
    1221      * @param string $order - the query args order value.
    1222      * @param int $authorized_company_id - post ID for the authorized company.
    1223      * @param string $invoice_status - invoice status value.
    1224      * @return array $args - array of args for the invoice query.
    1225      */
    1226     function accp_generate_invoice_query_args($categories, $number_of_posts, $paged, $order_by, $order, $authorized_company_id, $invoice_status){
    1227    
    1228         /**
    1229          * Add a tax_query if the 'categories' att is not empty.
    1230          */
    1231         $tax_query = array();
    1232        
    1233         if(!empty($categories)){
    1234 
    1235             $tax_query[] = array(
    1236                 'taxonomy' => 'accp_invoice_categories',
    1237                 'field' => 'id',
    1238                 'terms' => $categories,             
    1239             );
    1240 
    1241         }
    1242        
    1243         $args = array(
    1244             'post_type' => 'accp_clientinvoice',
    1245             'posts_per_page' => $number_of_posts,       
    1246             'paged' => $paged, 
    1247             'orderby' => $order_by,           
    1248             'order' => $order,
    1249             'meta_query' => array(               
    1250                 'relation' => 'AND',             
    1251                 array(         
    1252                     'key' => 'accp_user',
    1253                     'value' => $authorized_company_id                         
    1254                 ),             
    1255                 array(         
    1256                     'key' => 'invoice_status',
    1257                     'value' => $invoice_status           
    1258                 )           
    1259             ),
    1260             'tax_query' => $tax_query               
    1261         );
    1262 
    1263         return $args;
    1264 
    1265     }
    1266 
    1267 
    1268     /**
    1269      * Set up the core atts for the clientinvoice shortcode.
    1270      *
    1271      * @return array $atts_list_array - array of defined shortcode atts.
    1272      */
    1273     function accp_clientinvoice_core_shortcode_atts(){
    1274 
    1275         $atts_list_array  = array(
    1276             'id' => '', // Optional ID for the accp_documents_filelist list div.  Defaults to null.
    1277             'class' => '', // Optional additional class(es) for the accp_documents_filelist list div.  Defaults to null.
    1278             'categories' => '', // Category atts can be entered as the Slug or ID in the shortcode
    1279             'invoice_status' => '', // Invoice status to show - 'paid' or 'unpaid'. Defaults to 'unpaid.'
    1280             'display_number' => '', // This is the number of posts per page
    1281             'order_by' => '', // This allows ordering by post title - default is post date - options "title" or "date"
    1282             'order' => '', // This can be set as ASC or DESC - default is DESC     
    1283             'show_excerpt' => '', // Displays truncated text from the post content field
    1284             'show_thumbnail' => '', // Displays the posts featured image in the loop
    1285             'excerpt_length' => '', // Accepts the number of words for the excerpt
    1286             'thumbnail_size' => '', // Enter the thumbnail slug defined in the theme
    1287             'align_thumbnail' => '', // center, left, right, float-left, float-right
    1288             'show_post_date' => '', // Display the post date - default is false     
    1289             'list_id' => '', // Integer - Useful when there are multiple shortcode lists on the same page - default is null
    1290             'link_title' => '' // nolink or empty.  Used to disable post link titles - default is null.
    1291         );
    1292 
    1293         return $atts_list_array;
    1294 
    1295     }
    1296 
    1297     /* End client invoice list shortcode */
    129875
    129976
     
    1414191
    1415192
    1416     /**
    1417      * Generate excerpt html for File and Invoice shortcodes.
    1418      *
    1419      * @param int $file_post_id - the post ID of the file in the loop.
    1420      * @param array $atts - array of atts passed in via the shortcode.
    1421      * @param int $excerpt_length - value to use to constrain the exerpt length.
    1422      * @return string $html - the html for the excerpt element.
    1423      */
    1424     function accp_file_and_invoice_excerpt_html($file_post_id, $atts, $excerpt_length = null){
    1425 
    1426         if(!$file_post_id || !$atts) return;
    1427 
    1428         $excerpt = get_the_excerpt($file_post_id);
    1429 
    1430         if($excerpt){       
    1431            
    1432             $html = '<div class="file-loop-description">';
    1433                
    1434                 if( $atts['show_excerpt'] == true){                             
    1435 
    1436                     if ($excerpt_length != null){
    1437 
    1438                         $html .= wp_trim_words( wp_kses_post($excerpt), $excerpt_length, $more = '...' );
    1439 
    1440                     }else{
    1441 
    1442                         $html .= wp_kses_post($excerpt);                               
    1443 
    1444                     }
    1445 
    1446                 }           
    1447 
    1448             $html .= '</div>';
    1449            
    1450             return $html;
    1451 
    1452         }
    1453 
    1454         return;
    1455 
    1456     }
    1457 
    1458     /**
    1459      * Set up the $list_id var.
    1460      *
    1461      * @param array $atts - array of atts passed in via the shortcode.
    1462      * @return int $list_id - integer.
    1463      */
    1464     function accp_list_id_var($atts){
    1465 
    1466         if(!$atts) return null;
    1467 
    1468         if( $atts['list_id'] != null){
    1469 
    1470             $list_id_input = (int)preg_replace('/[^0-9]/', '', $atts['list_id']);
    1471 
    1472             $list_id = filter_var($list_id_input, FILTER_SANITIZE_NUMBER_INT);
    1473 
    1474         }else{
    1475 
    1476             $list_id = null;
    1477         }
    1478        
    1479         return $list_id;
    1480 
    1481     }
    1482 
    1483 
    1484     /**
    1485      * Set up the $categories var.
    1486      *
    1487      * @param array $atts - array of atts passed in via the shortcode.
    1488      * @param string $taxonomy - either 'accp_file_categories' or 'accp_invoice_categories'.
    1489      * @return array $categories - array of category ID's.
    1490      */
    1491     function accp_categories_var($atts, $taxonomy){
    1492        
    1493         $categories = array();
    1494 
    1495         if( isset($atts['categories']) ){
    1496 
    1497             $categories_list = explode(',', trim($atts['categories']) );           
    1498             $categories = array();
    1499 
    1500             foreach($categories_list as $category_item){
    1501 
    1502                 $category_item = filter_var(trim($category_item), FILTER_SANITIZE_STRING);
    1503 
    1504                 // We accept either a category ID or slug, so let's try
    1505                 // to determine what has been entered.
    1506                 if (!ctype_digit($category_item)) {
    1507 
    1508                     // We assume this is a slug, get the term by the slug.
    1509                     $category = get_term_by('slug', $category_item, $taxonomy);
    1510                    
    1511                     if($category){
    1512 
    1513                         $categories[] = $category->term_id;
    1514 
    1515                     }
    1516 
    1517                 }else{
    1518 
    1519                     $category = get_term_by('ID', (int)$category_item, $taxonomy);
    1520                    
    1521                     if($category){
    1522 
    1523                         $categories[] = $category_item;
    1524 
    1525                     }else{
    1526 
    1527                         // Account for a category name/slug that is all numerical characters.
    1528                         $category = get_term_by('slug', $category_item, $taxonomy);
    1529 
    1530                         if($category){
    1531 
    1532                             $categories[] = $category->term_id;
    1533    
    1534                         }
    1535 
    1536                     }
    1537 
    1538 
    1539                 }
    1540 
    1541             }           
    1542 
    1543         }   
    1544 
    1545         return $categories;
    1546 
    1547     }
    1548 
    1549 
    1550     /**
    1551      * Set up $number_of_posts shortcode var.
    1552      *
    1553      * @param array $atts - array of atts passed in via the shortcode.
    1554      * @return int $number_of_posts - integer.
    1555      */
    1556     function accp_number_of_posts_var($atts){
    1557 
    1558         if ($atts['display_number'] != null){
    1559 
    1560             $att_input = preg_replace('/[^0-9]/', '', $atts['display_number']);
    1561             $number_of_posts = (int)$att_input;
    1562 
    1563         }else{
    1564 
    1565             $number_of_posts = 20;
    1566 
    1567         }
    1568 
    1569         return $number_of_posts;
    1570 
    1571     }
    1572 
    1573 
    1574     /**
    1575      * Set up $order_by shortcode var.
    1576      *
    1577      * @param array $atts - array of atts passed in via the shortcode.
    1578      * @return string $order_by - order_by value (ex. "date").
    1579      */
    1580     function accp_order_by_var($atts){
    1581 
    1582         if( $atts['order_by'] != null){
    1583 
    1584             $order_by = filter_var(trim($atts['order_by']), FILTER_SANITIZE_STRING);
    1585 
    1586         }else{
    1587 
    1588             $order_by = 'date';
    1589 
    1590         }
    1591 
    1592         return $order_by;
    1593 
    1594     }
    1595 
    1596     /**
    1597      * Set up $order shortcode var.
    1598      *
    1599      * @param array $atts - array of atts passed in via the shortcode.
    1600      * @return string $order - the order value (ASC or DESC).
    1601      */
    1602     function accp_order_var($atts){
    1603 
    1604         if( $atts['order'] != null){
    1605 
    1606             $order = filter_var(trim($atts['order']), FILTER_SANITIZE_STRING);
    1607 
    1608         }else{
    1609 
    1610             $order = 'DESC';
    1611 
    1612         }
    1613 
    1614         return $order;
    1615 
    1616     }
    1617 
    1618 
    1619     /**
    1620      * Set up $excerpt_length shortcode var.
    1621      *
    1622      * @param array $atts - array of atts passed in via the shortcode.
    1623      * @return int $excerpt_length - integer.
    1624      */
    1625     function accp_excerpt_length_var($atts){
    1626        
    1627         if($atts['excerpt_length'] != null){
    1628 
    1629             $att_input = preg_replace('/[^0-9]/', '', $atts['excerpt_length']);
    1630            
    1631             if(!empty($att_input) ){
    1632 
    1633                 $excerpt_length = (int)$atts['excerpt_length'];
    1634 
    1635             }else{
    1636 
    1637                 $excerpt_length = null;
    1638 
    1639             }
    1640            
    1641         }else{
    1642 
    1643             $excerpt_length = null;
    1644 
    1645         }
    1646 
    1647         return $excerpt_length;
    1648        
    1649     }
    1650 
    1651     /**
    1652      * Set up $thumbnail_size shortcode var.
    1653      *
    1654      * @param array $atts - array of atts passed in via the shortcode.
    1655      * @return string $thumbnail_size - the thumbnail slug.
    1656      */
    1657     function accp_thumbnail_size_var($atts){
    1658 
    1659         if($atts['thumbnail_size'] != null){
    1660 
    1661             $thumbnail_size = filter_var( trim($atts['thumbnail_size']), FILTER_SANITIZE_STRING);
    1662 
    1663         }else{
    1664 
    1665             $thumbnail_size = null;
    1666 
    1667         }
    1668 
    1669         return $thumbnail_size;
    1670 
    1671     }
    1672 
    1673 
    1674     /**
    1675      * Set up $align_thumbnail shortcode var.
    1676      *
    1677      * @param array $atts - array of atts passed in via the shortcode.
    1678      * @return string|false $align_thumbnail - the thumbnail CSS class suffix.
    1679      */
    1680     function accp_align_thumbnail_var($atts){
    1681 
    1682         if( !array_key_exists('align_thumbnail', $atts) )
    1683             return false;
    1684 
    1685         $att_input = trim( strtolower($atts['align_thumbnail']) );     
    1686 
    1687         switch($att_input){
    1688 
    1689             case 'left':
    1690                 $align_thumbnail = '-left';
    1691                 break;
    1692 
    1693             case 'right':
    1694                 $align_thumbnail = '-right';
    1695                 break;
    1696 
    1697             case 'center':
    1698                 $align_thumbnail = '-cetner';
    1699                 break;
    1700 
    1701             case 'float-left':
    1702                 $align_thumbnail = '-float-left';
    1703                 break;
    1704 
    1705             case 'float-right':
    1706                 $align_thumbnail = '-float-right';
    1707                 break;
    1708 
    1709             default:
    1710                 $align_thumbnail = false;
    1711 
    1712         }       
    1713 
    1714         return $align_thumbnail;
    1715 
    1716     }
    1717 
    1718 
    1719     /**
    1720      * Generate a list instance ID by posting
    1721      * and incrementing a number that can be assigned
    1722      * to lists that are added to the page via file and
    1723      * invoice shortcodes.
    1724      *
    1725      * This allows for accurate pagination functionality
    1726      * when multiple lists are added to the same page, and
    1727      * can allow for better css and/or script targetting.
    1728      *
    1729      * @return int $list_instance_id - a unique number to be used
    1730      * for a file or invoice list.
    1731      */
    1732     function accp_generate_list_instance_id(){
    1733 
    1734         /**
    1735          * If $_POST['accp_list_count'] is not set,
    1736          * this should be the first (or only) list on the page,
    1737          * so let's set $_POST['accp_list_count'] to "1".
    1738          */
    1739         if( !isset($_POST['accp_list_count']) ){
    1740 
    1741             $_POST['accp_list_count'] = 1;
    1742 
    1743         }else{
    1744 
    1745             /**
    1746              * If we've gotten this far and $_POST['accp_list_count']
    1747              * is already set, There's more than one list on the page.
    1748              * So, let's increment $_POST['accp_list_count'] by 1 and
    1749              * use that for the current list's ID (and repeat until
    1750              * all lists on the page have a unique list ID).             *
    1751              */
    1752             $_POST['accp_list_count'] = (int)$_POST['accp_list_count'] + 1;
    1753 
    1754         }
    1755 
    1756         $list_instance_id = filter_var( $_POST['accp_list_count'], FILTER_SANITIZE_NUMBER_INT );
    1757 
    1758         return $list_instance_id;   
    1759 
    1760     }
    1761 
    1762 
    1763193} // END ARS_Constellation_Client_Portal_Public class
Note: See TracChangeset for help on using the changeset viewer.