Skip to:
Content

BuddyPress.org

Ticket #6534: 6534.patch

File 6534.patch, 25.6 KB (added by imath, 4 years ago)
  • src/bp-core/bp-core-classes.php

    diff --git src/bp-core/bp-core-classes.php src/bp-core/bp-core-classes.php
    index 41be065..0a65aa1 100644
    require dirname( __FILE__ ) . '/classes/class-bp-recursive-query.php'; 
    2323require dirname( __FILE__ ) . '/classes/class-bp-media-extractor.php';
    2424require dirname( __FILE__ ) . '/classes/class-bp-attachment.php';
    2525require dirname( __FILE__ ) . '/classes/class-bp-attachment-avatar.php';
     26require dirname( __FILE__ ) . '/classes/class-bp-single-item-navigation.php';
  • src/bp-core/bp-core-filters.php

    diff --git src/bp-core/bp-core-filters.php src/bp-core/bp-core-filters.php
    index b5e857a..1c23fbe 100644
    function bp_modify_page_title( $title = '', $sep = '»', $seplocation = 'ri 
    731731
    732732        // A single item from a component other than groups
    733733        } elseif ( bp_is_single_item() ) {
    734                 $title_parts = array( $bp->bp_options_title, $bp->bp_options_nav[ bp_current_item() ][ bp_current_action() ]['name'] );
     734                if ( isset( $bp->{$bp->current_component}->nav->main ) ) {
     735                        $component_nav_section = '';
     736
     737                        // Get the component nav section name
     738                        foreach ( $bp->{$bp->current_component}->nav->main as $component_nav_item ) {
     739                                if ( bp_current_action() !== $component_nav_item['slug'] ) {
     740                                        continue;
     741                                }
     742
     743                                $component_nav_section = $component_nav_item['name'];
     744                        }
     745
     746                        $title_parts = array( $bp->bp_options_title, $component_nav_section );
     747                } else {
     748                        $title_parts = array( $bp->bp_options_title, $bp->bp_options_nav[ bp_current_item() ][ bp_current_action() ]['name'] );
     749                }
    735750
    736751        // An index or directory
    737752        } elseif ( bp_is_directory() ) {
  • src/bp-core/bp-core-template.php

    diff --git src/bp-core/bp-core-template.php src/bp-core/bp-core-template.php
    index 5cebddf..1c88693 100644
    function bp_get_options_nav( $parent_slug = '' ) { 
    8787}
    8888
    8989/**
     90 * Output a component's single item main nav
     91 *
     92 * @since BuddyPress (2.4.0)
     93 *
     94 * @param  string $component the component id
     95 */
     96function bp_single_item_main_nav( $component = '' ) {
     97        $bp = buddypress();
     98
     99        if ( empty( $component ) ) {
     100                $component = bp_current_component();
     101        }
     102
     103        if ( ! isset( $bp->{$component}->nav ) || ! is_a( $bp->{$component}->nav, 'BP_Single_Item_Navigation' ) ) {
     104                return;
     105        }
     106
     107        $bp->{$component}->nav->display_main_nav();
     108}
     109
     110/**
     111 * Output a component's single item options nav
     112 *
     113 * @since BuddyPress (2.4.0)
     114 *
     115 * @param  string $component the component id
     116 */
     117function bp_single_item_sub_nav( $component = '' ) {
     118        $bp = buddypress();
     119
     120        if ( empty( $component ) ) {
     121                $component = bp_current_component();
     122        }
     123
     124        if ( ! bp_is_single_item() || ! isset( $bp->{$component}->nav ) || ! is_a( $bp->{$component}->nav, 'BP_Single_Item_Navigation' ) ) {
     125                return;
     126        }
     127
     128        $bp->{$component}->nav->display_sub_nav();
     129}
     130
     131/**
    90132 * Get the 'bp_options_title' property from the BP global.
    91133 *
    92134 * Not currently used in BuddyPress.
  • src/bp-core/classes/class-bp-single-item-navigation.php

    diff --git src/bp-core/classes/class-bp-single-item-navigation.php src/bp-core/classes/class-bp-single-item-navigation.php
    index e69de29..c47387e 100644
     
     1<?php
     2/**
     3 * Core component classes.
     4 *
     5 * @package BuddyPress
     6 * @subpackage Core
     7 */
     8
     9// Exit if accessed directly
     10defined( 'ABSPATH' ) || exit;
     11
     12/**
     13 * API to create a component's single item navigation.
     14 *
     15 * @since BuddyPress (2.4.0)
     16 */
     17class BP_Single_Item_Navigation {
     18
     19        /**
     20         * The single item main nav
     21         *
     22         * @since BuddyPress (2.4.0)
     23         * @var array
     24         */
     25        public $main = array();
     26
     27        /**
     28         * The single item sub nav
     29         *
     30         * @since BuddyPress (2.4.0)
     31         * @var array
     32         */
     33        public $sub  = array();
     34
     35        /**
     36         * The default args to be merged with the
     37         * ones passed to the constructor
     38         *
     39         * @since BuddyPress (2.4.0)
     40         * @var array
     41         */
     42        protected $default_args = array(
     43                'component_id'           => '',
     44                'component_slug'         => '',
     45                'single_item_name'       => '',
     46        );
     47
     48        /**
     49         * Constructor
     50         *
     51         * @since BuddyPress (2.4.0)
     52         *
     53         * @param array $args {
     54         *     Array of arguments.
     55         *     @type string $component_id String describing the component id (eg: blogs, groups...).
     56         *     @type string $component_slug The root slug of the component (eg: blogs, sites, groups...)
     57         *     @type string $single_item_name Required. The single item name (eg: blog, group...)
     58         * }
     59         */
     60        public function __construct( $args = array() ) {
     61                if ( empty( $args['single_item_name'] ) ) {
     62                        return false;
     63                }
     64
     65                // Merge args
     66                $params = wp_parse_args( $args, $this->default_args, $args['single_item_name'] . '_single_item_nav_params' );
     67
     68                foreach ( $params as $key => $param ) {
     69                        // Sanitize slug
     70                        if ( 'component_slug' === $key ) {
     71                                $this->{$key} = sanitize_title( $param );
     72
     73                        // Sanitize other keys
     74                        } else {
     75                                $this->{$key} = sanitize_key( $param );
     76                        }
     77                }
     78
     79                // Use the current component as a fallback
     80                if ( empty( $this->component_id ) ) {
     81                        $this->component_id = bp_current_component();
     82                }
     83
     84                // Use the component root slug as a fallback
     85                if ( empty( $this->component_slug ) && is_callable( 'bp_get_' . $this->component_id . '_root_slug' ) ) {
     86                        $this->component_slug = call_user_func( 'bp_get_' . $this->component_id . '_root_slug' );
     87                }
     88        }
     89
     90        /**
     91         * Setup the single item navigation
     92         *
     93         * @since BuddyPress (2.4.0)
     94         *
     95         * @param  array  $main_nav list of associative arrays containing the nav items params
     96         * @param  array  $sub_nav  list of associative arrays containing the sub nav items params
     97         */
     98        public function setup_nav( $main_nav = array(), $sub_nav = array() ) {
     99                // Bail if the component slug or the component id are not set
     100                if ( ! $this->component_slug || ! $this->component_id ) {
     101                        return false;
     102                }
     103
     104                // No sub nav items without a main nav item
     105                if ( ! empty( $main_nav ) ) {
     106                        foreach( (array) $main_nav as $item ) {
     107                                $this->new_main_nav_item( $item );
     108                        }
     109
     110                        // Sub nav items are not required
     111                        if ( ! empty( $sub_nav ) ) {
     112                                foreach( (array) $sub_nav as $sub_item ) {
     113                                        $this->new_sub_nav_item( $sub_item );
     114                                }
     115                        }
     116                }
     117
     118                /**
     119                 * Fires at the end of the setup_nav method inside BP_Single_Item_Navigation.
     120                 *
     121                 * This is a dynamic hook that is based on the component string ID.
     122                 *
     123                 * @since BuddyPress (2.4.0)
     124                 */
     125                do_action( 'bp_' . $this->component_id . '_single_item_setup_nav' );
     126        }
     127
     128        /**
     129         * Add a new nav item to main nav
     130         *
     131         * @since BuddyPress (2.4.0)
     132         *
     133         * @param  array  $args associative array containing the item params
     134         */
     135        public function new_main_nav_item( $args = array() ) {
     136                // Bail if the component slug or the component id are not set
     137                if ( ! $this->component_slug || ! $this->component_id ) {
     138                        return false;
     139                }
     140
     141                // Get BuddyPress instance
     142                $bp = buddypress();
     143
     144                $slug = false;
     145                if ( ! empty( $args['slug'] ) ) {
     146                        $slug = $args['slug'];
     147                }
     148
     149                $item = bp_parse_args( $args, array(
     150                        'name'                    => false, // Display name for the nav item
     151                        'slug'                    => false, // URL slug for the nav item
     152                        'item_css_id'             => false, // The CSS ID to apply to the HTML of the nav item
     153                        'item_admin_only'         => false, // Can only item admins see this nav item?
     154                        'position'                => 99,    // Index of where this nav item should be positioned
     155                        'screen_function'         => false, // The name of the function to run when clicked
     156                        'default_subnav_slug'     => false  // The slug of the default subnav item to select when clicked
     157                ), $this->single_item_name . '_main_nav_item_' . $slug );
     158
     159                // If we don't have the required info we need, don't create this nav item
     160                if ( empty( $item['name'] ) || empty( $item['slug'] ) || empty( $item['screen_function'] ) ) {
     161                        return false;
     162                }
     163
     164                // If this is for site admins only and the user is not one, don't create the subnav item
     165                if ( ! empty( $item['item_admin_only'] ) && ! bp_is_item_admin() ) {
     166                        return false;
     167                }
     168
     169                if ( empty( $item['item_css_id'] ) ) {
     170                        $item['item_css_id'] = $item['slug'];
     171                }
     172
     173                /**
     174                 * Link is composed by:
     175                 * 1. the root domain          eg: http://site.url
     176                 * 2. the component root slug  eg: sites
     177                 * 3. the current item slug    eg: blog_slug
     178                 * 4. the nav item slug        eg: home
     179                 */
     180                $link = bp_get_root_domain() . '/' . $this->component_slug . '/' . bp_current_item() . '/' . $item['slug'];
     181
     182                $this->main[ $item['slug'] ] = array(
     183                        'name'                    => $item['name'],
     184                        'slug'                    => $item['slug'],
     185                        'link'                    => trailingslashit( $link ),
     186                        'css_id'                  => $item['item_css_id'],
     187                        'position'                => $item['position'],
     188                        'screen_function'         => &$item['screen_function'],
     189                        'default_subnav_slug'     => $item['default_subnav_slug']
     190                );
     191
     192                /**
     193                 * If this condition is true, this means the url looks like
     194                 * http://site.url/sites/blog_slug/home
     195                 */
     196                if ( bp_is_current_action( $item['slug'] ) ) {
     197                        /**
     198                         * If the default subnav match the first action variable move all left
     199                         */
     200                        if ( ! empty( $item['default_subnav_slug'] ) && bp_is_action_variable( $item['default_subnav_slug'], 0 ) && ! bp_action_variable( 1 ) ) {
     201                                unset( $bp->canonical_stack['action_variables'][0] );
     202
     203                        // No action variable it's the root of the nav
     204                        } elseif ( ! bp_action_variable( 0 ) ) {
     205
     206                                // Add our screen hook if screen function is callable
     207                                if ( is_callable( $item['screen_function'] ) ) {
     208                                        add_action( 'bp_screens', $item['screen_function'], 3 );
     209                                }
     210
     211                                if ( ! empty( $item['default_subnav_slug'] ) ) {
     212                                        /**
     213                                         * Filters the component's single nav default subnav item.
     214                                         *
     215                                         * @since BuddyPress (2.4.0)
     216                                         *
     217                                         * @param string $default_subnav_slug The slug of the default subnav item
     218                                         *                                    to select when clicked.
     219                                         * @param array  $r                   Parsed arguments for the nav item.
     220                                         */
     221                                        $bp->current_action = apply_filters( 'bp_single_item_default_subnav', $item['default_subnav_slug'], $item );
     222                                }
     223                        }
     224                }
     225        }
     226
     227        /**
     228         * Add a new sub nav item to sub nav
     229         *
     230         * @since BuddyPress (2.4.0)
     231         *
     232         * @param  array  $args associative array containing the sub item params
     233         */
     234        public function new_sub_nav_item( $args = array() ) {
     235                // Bail if the component slug or the component id are not set
     236                if ( ! $this->component_slug || ! $this->component_id ) {
     237                        return false;
     238                }
     239
     240                $slug = false;
     241                if ( ! empty( $args['slug'] ) ) {
     242                        $slug = $args['slug'];
     243                }
     244
     245                $sub_item = bp_parse_args( $args, array(
     246                        'name'              => false, // Display name for the nav item
     247                        'slug'              => false, // URL slug for the nav item
     248                        'parent_slug'       => false, // URL slug of the parent nav item
     249                        'parent_url'        => false, // URL of the parent item
     250                        'item_css_id'       => false, // The CSS ID to apply to the HTML of the nav item
     251                        'user_has_access'   => true,  // Can the logged in user see this nav item?
     252                        'no_access_url'     => '',
     253                        'item_admin_only'   => false, // Can only item admins see this nav item?
     254                        'position'          => 90,    // Index of where this nav item should be positioned
     255                        'screen_function'   => false, // The name of the function to run when clicked
     256                        'link'              => '',    // The link for the subnav item; optional, not usually required.
     257                        'show_in_admin_bar' => false, // Show the Manage link in the current group's "Edit" Admin Bar menu
     258                ), $this->single_item_name . '_sub_nav_item_' . $slug );
     259
     260
     261                // If we don't have the required info we need, don't create this subnav item
     262                if ( empty( $sub_item['name'] ) || empty( $sub_item['slug'] ) || empty( $sub_item['parent_slug'] ) || empty( $sub_item['parent_url'] ) || empty( $sub_item['screen_function'] ) ) {
     263                        return false;
     264                }
     265
     266                // If this is for site admins only and the user is not one, don't create the subnav item
     267                if ( ! empty( $sub_item['item_admin_only'] ) && ! bp_is_item_admin() ) {
     268                        return false;
     269                }
     270
     271                if ( empty( $sub_item['link'] ) ) {
     272                        $sub_item['link'] = trailingslashit( $sub_item['parent_url'] . $sub_item['slug'] );
     273
     274                        // If this sub item is the default for its parent, skip the slug
     275                        if ( $sub_item['slug'] === $this->main[ $sub_item['parent_slug'] ]['default_subnav_slug'] ) {
     276                                $sub_item['link'] = trailingslashit( $sub_item['parent_url'] );
     277                        }
     278                }
     279
     280                if ( empty( $sub_item['item_css_id'] ) ) {
     281                        $sub_item['item_css_id'] = $sub_item['slug'];
     282                }
     283
     284                $this->sub[ $sub_item['parent_slug'] ][ $sub_item['slug'] ] = array(
     285                        'name'              => $sub_item['name'],
     286                        'link'              => $sub_item['link'],
     287                        'slug'              => $sub_item['slug'],
     288                        'css_id'            => $sub_item['item_css_id'],
     289                        'position'          => $sub_item['position'],
     290                        'user_has_access'   => $sub_item['user_has_access'],
     291                        'no_access_url'     => $sub_item['no_access_url'],
     292                        'screen_function'   => &$sub_item['screen_function'],
     293                        'show_in_admin_bar' => (bool) $sub_item['show_in_admin_bar'],
     294                );
     295
     296                if ( ! bp_is_current_component( $this->component_id ) && ! bp_is_current_action( $sub_item['parent_slug'] ) ) {
     297                        return false;
     298                }
     299
     300                if ( bp_action_variable( 0 ) && bp_is_action_variable( $sub_item['slug'], 0 ) ) {
     301
     302                        $hooked = bp_core_maybe_hook_new_subnav_screen_function( $this->sub[ $sub_item['parent_slug'] ][ $sub_item['slug'] ] );
     303
     304                        // If redirect args have been returned, perform the redirect now
     305                        if ( ! empty( $hooked['status'] ) && 'failure' === $hooked['status'] && isset( $hooked['redirect_args'] ) ) {
     306                                bp_core_no_access( $hooked['redirect_args'] );
     307                        }
     308                }
     309        }
     310
     311        /**
     312         * Sort the main nav items and output the main nav.
     313         *
     314         * @since BuddyPress (2.4.0)
     315         *
     316         * @return HTML output
     317         */
     318        public function display_main_nav() {
     319                // Bail if the component slug or the component id are not set
     320                if ( ! $this->component_slug || ! $this->component_id ) {
     321                        return false;
     322                }
     323
     324                // Sort the main nav just before it's displayed
     325                $main_nav = bp_sort_by_key( $this->main, 'position', 'num' );
     326
     327                // Loop throw each nav item
     328                foreach ( (array) $main_nav as $main_nav_item ) {
     329                        // Defaults to none
     330                        $selected = '';
     331
     332                        if ( bp_is_current_action( $main_nav_item['slug'] ) ) {
     333                                $selected = ' class="current selected"';
     334                        }
     335
     336                        /**
     337                         * Filters the component's "main nav", the first-level single item navigation menu.
     338                         *
     339                         * This is a dynamic filter that is dependent on the component's single item and the provided css_id value.
     340                         *
     341                         * @since BuddyPress (2.4.0)
     342                         *
     343                         * @param string $value         HTML list item for the submenu item.
     344                         * @param array  $subnav_item   Main nav array item being displayed.
     345                         */
     346                        echo apply_filters_ref_array( 'bp_' . $this->single_item_name . '_main_nav_' . $main_nav_item['css_id'], array( '<li id="' . esc_attr( $main_nav_item['css_id'] ) . '-' . esc_attr( $this->component_id ) . '-li" ' . $selected . '><a id="' . esc_attr( $this->single_item_name ) . '-' . esc_attr( $main_nav_item['slug'] ) . '" href="' . esc_url( $main_nav_item['link'] ) . '">' . $main_nav_item['name'] . '</a></li>', &$main_nav_item ) );
     347                }
     348        }
     349
     350        /**
     351         * Sort the sub nav items and output the sub nav
     352         *
     353         * @since BuddyPress (2.4.0)
     354         *
     355         * @return HTML output
     356         */
     357        public function display_sub_nav() {
     358                // Bail if the component slug or the component id are not set
     359                if ( ! $this->component_slug || ! $this->component_id ) {
     360                        return false;
     361                }
     362
     363                $the_index = bp_current_action();
     364
     365                if ( bp_action_variable( 0 ) ) {
     366                        $selected_item = bp_action_variable( 0 );
     367                } else {
     368                        $selected_item = $the_index;
     369                }
     370
     371                if ( empty( $this->sub[ $the_index ] ) ) {
     372                        return;
     373                }
     374
     375                // Sort the main nav just before it's displayed
     376                $sub_nav = bp_sort_by_key( $this->sub[ $the_index ], 'position', 'num' );
     377
     378                // Loop throw each nav item
     379                foreach ( (array) $sub_nav as $sub_nav_item ) {
     380
     381                        if ( empty( $sub_nav_item['user_has_access'] ) ) {
     382                                continue;
     383                        }
     384
     385                        // If the current action or an action variable matches the nav item id, then add a highlight CSS class.
     386                        if ( $sub_nav_item['slug'] === $selected_item ) {
     387                                $selected = ' class="current selected"';
     388                        } else {
     389                                $selected = '';
     390                        }
     391
     392                        /**
     393                         * Filters the component's "single nav", the secondary-level single item navigation menu.
     394                         *
     395                         * This is a dynamic filter that is dependent on the component's id and the provided css_id value.
     396                         *
     397                         * @since BuddyPress (2.4.0)
     398                         *
     399                         * @param string $value         HTML list item for the submenu item.
     400                         * @param array  $subnav_item   Submenu array item being displayed.
     401                         * @param string $selected_item Current action.
     402                         */
     403                        echo apply_filters( 'bp_' . $this->single_item_name . '_single_subnav_' . $sub_nav_item['css_id'], '<li id="' . esc_attr( $sub_nav_item['css_id'] . '-' . $this->component_id . '-' . $this->single_item_name . '-li' ) . '" ' . $selected . '><a id="' . esc_attr( $sub_nav_item['css_id'] ) . '" href="' . esc_url( $sub_nav_item['link'] ) . '">' . $sub_nav_item['name'] . '</a></li>', $sub_nav_item, $selected_item );
     404                }
     405        }
     406
     407        /**
     408         * Get the sub nav items for the provided parent slug
     409         *
     410         * @since BuddyPress (2.4.0)
     411         *
     412         * @param  string $parent_slug the main nav parent slug
     413         * @return HTML   output
     414         */
     415        public function get_sub_nav_by_parent_slug( $parent_slug = '' ) {
     416                if ( empty( $parent_slug ) || empty( $this->sub[ $parent_slug ] ) ) {
     417                        return false;
     418                }
     419
     420                // Sort the sub nav items
     421                $sub_nav_items = bp_sort_by_key( $this->sub[ $parent_slug ], 'position', 'num' );
     422
     423                return $sub_nav_items;
     424        }
     425
     426        /**
     427         * Remove a main nav item for component's single item
     428         *
     429         * @since BuddyPress (2.4.0)
     430         *
     431         * @param  string $component        the component id
     432         * @param  string $main_nav_item_id the main nav item id
     433         * @return bool                     true if the main nav was removed, false otherwise
     434         */
     435        public static function remove_main_nav_item( $component ='', $main_nav_item_id = '' ) {
     436                $bp = buddypress();
     437
     438                if ( empty( $component ) || empty( $main_nav_item_id ) || ! isset( $bp->{$component}->nav->main[ $main_nav_item_id ] ) ) {
     439                        return false;
     440                }
     441
     442                // Unset sub_nav items for this nav item
     443                if ( isset( $bp->{$component}->nav->sub[ $main_nav_item_id ] ) && is_array( $bp->{$component}->nav->sub[ $main_nav_item_id ] ) ) {
     444                        foreach( (array) $bp->{$component}->nav->sub[ $main_nav_item_id ] as $sub_nav_item ) {
     445                                self::remove_sub_nav_item( $component, $main_nav_item_id, $sub_nav_item['slug'] );
     446                        }
     447                }
     448
     449                $screen_function = false;
     450                if ( isset( $bp->{$component}->nav->main[ $main_nav_item_id ]['screen_function'] ) ) {
     451                        $screen_function = $bp->{$component}->nav->main[ $main_nav_item_id ]['screen_function'];
     452                }
     453
     454                if ( ! empty( $screen_function ) ) {
     455                        // Remove our screen hook if screen function is callable
     456                        if ( is_callable( $screen_function ) ) {
     457                                remove_action( 'bp_screens', $screen_function, 3 );
     458                        }
     459                }
     460
     461                unset( $bp->{$component}->nav->main[ $main_nav_item_id ] );
     462                return true;
     463        }
     464
     465        /**
     466         * Remove a sub nav item for component's single item main nav
     467         *
     468         * @since BuddyPress (2.4.0)
     469         *
     470         * @param  string $component         the component id
     471         * @param  string $main_nav_item_id  the main nav item id
     472         * @param  string $sub_nav_item_slug the sub nav slug
     473         * @return bool                      true if the sub nav was removed, false otherwise
     474         */
     475        public static function remove_sub_nav_item( $component ='', $main_nav_item_id = '', $sub_nav_item_slug = '' ) {
     476                $bp = buddypress();
     477
     478                if ( empty( $component ) || empty( $main_nav_item_id ) || empty( $sub_nav_item_slug ) || ! isset( $bp->{$component}->nav->sub[ $main_nav_item_id ][ $sub_nav_item_slug ] ) ) {
     479                        return false;
     480                }
     481
     482                $screen_function = false;
     483                if ( isset( $bp->{$component}->nav->sub[ $main_nav_item_id ][ $sub_nav_item_slug ]['screen_function'] ) ) {
     484                        $screen_function = $bp->{$component}->nav->sub[ $main_nav_item_id ][ $sub_nav_item_slug ]['screen_function'];
     485                }
     486
     487                if ( ! empty( $screen_function ) ) {
     488                        // Remove our screen hook if screen function is callable
     489                        if ( is_callable( $screen_function ) ) {
     490                                remove_action( 'bp_screens', $screen_function, 3 );
     491                        }
     492                }
     493
     494                unset( $bp->{$component}->nav->sub[ $main_nav_item_id ][ $sub_nav_item_slug ] );
     495                return true;
     496        }
     497}
  • tests/phpunit/testcases/core/class-bp-single-item-navigation.php

    diff --git tests/phpunit/testcases/core/class-bp-single-item-navigation.php tests/phpunit/testcases/core/class-bp-single-item-navigation.php
    index e69de29..981d987 100644
     
     1<?php
     2
     3/**
     4 * @group core
     5 * @group BP_Single_Item_Navigation
     6 * @group single_item_nav
     7 */
     8class BP_Tests_BP_Single_Item_Navigation extends BP_UnitTestCase {
     9        public function setUp() {
     10                parent::setUp();
     11                $this->current_user = get_current_user_id();
     12        }
     13
     14        public function tearDown() {
     15                $this->set_current_user( $this->current_user );
     16                parent::tearDown();
     17        }
     18        /**
     19         * @group blogs_item_nav
     20         */
     21        public function test_class_for_blogs_single_item() {
     22                if ( ! is_multisite() ) {
     23                        $this->markTestSkipped( __METHOD__ . ' is a multisite-only test.' );
     24                }
     25
     26                $bp = buddypress();
     27
     28                $reset_is_single_item = $bp->is_single_item;
     29                $reset_current_item   = $bp->current_item;
     30                $reset_current_action = $bp->current_action;
     31
     32                $a = $this->factory->user->create();
     33                $b = $this->factory->blog->create( array( 'user_id' => $a ) );
     34
     35                $u = $this->factory->user->create();
     36
     37                // Init the single nav
     38                $bp->blogs->nav = new BP_Single_Item_Navigation( array(
     39                        'component_id'     => $bp->blogs->id,
     40                        'component_slug'   => bp_get_blogs_root_slug(),
     41                        'single_item_name' => 'blog',
     42                ) );
     43
     44                $bp->blogs->current_blog = get_blog_details( $b );
     45                $bp->blogs->current_blog->slug = trim( str_replace( get_current_site()->path, '', $bp->blogs->current_blog->path ), '/' );
     46
     47                // It's a blog single item
     48                $bp->is_single_item  = true;
     49                $bp->current_item    = $bp->blogs->current_blog->slug;
     50
     51                // Public blogs
     52                $bp->blogs->current_blog->user_has_access = true;
     53
     54                // Admin is loggedin
     55                $this->set_current_user( $a );
     56                bp_update_is_item_admin( true, $bp->blogs->id );
     57
     58                $blog_link = trailingslashit( bp_get_root_domain() . '/' . bp_get_blogs_root_slug() . '/'. $bp->blogs->current_blog->slug );
     59
     60                $item_main_nav = array(
     61                        trailingslashit( $blog_link . 'home' ) => array(
     62                                'name'                => __( 'Home', 'buddypress' ),
     63                                'slug'                => 'home',
     64                                'position'            => 0,
     65                                'screen_function'     => 'screen_blog_home',
     66                                'default_subnav_slug' => false,
     67                        ),
     68                        trailingslashit( $blog_link . 'manage' ) => array(
     69                                'name'                => __( 'Manage', 'buddypress' ),
     70                                'slug'                => 'manage',
     71                                'position'            => 1000,
     72                                'screen_function'     => 'screen_blog_settings',
     73                                'default_subnav_slug' => 'manage',
     74                                'item_admin_only'     => true,
     75                        ),
     76                );
     77
     78                $item_sub_nav = array(
     79                        trailingslashit( $blog_link . 'manage' ) => array(
     80                                'name'              => __( 'Settings','buddypress' ),
     81                                'slug'              => 'manage',
     82                                'parent_url'        => trailingslashit( $blog_link . 'manage' ),
     83                                'parent_slug'       => 'manage',
     84                                'screen_function'   => 'screen_blog_settings',
     85                                'position'          => 0,
     86                                'item_admin_only'   => true,
     87                        ),
     88                );
     89
     90                // Setup the nav for the admin
     91                $bp->blogs->nav->setup_nav( $item_main_nav, $item_sub_nav );
     92
     93                $tested = array();
     94
     95                // Catch the main nav
     96                ob_start();
     97                $bp->blogs->nav->display_main_nav();
     98                $tested['main'] = ob_get_contents();
     99                ob_end_clean();
     100
     101                // Set the manage action
     102                $bp->current_action = 'manage';
     103
     104                // Catch the sub nav
     105                ob_start();
     106                $bp->blogs->nav->display_sub_nav();
     107                $tested['sub'] = ob_get_contents();
     108                ob_end_clean();
     109
     110                // Test main nav links
     111                preg_match_all( '#href=(["\'])([^"\']+)\1#i', $tested['main'], $main_matches );
     112                $this->assertSame( array_keys( $item_main_nav ), $main_matches[2] );
     113
     114                // Test sub nav links
     115                preg_match_all( '#href=(["\'])([^"\']+)\1#i', $tested['sub'], $sub_matches );
     116                $this->assertSame( array_keys( $item_sub_nav ), $sub_matches[2] );
     117
     118                // Test if reseting the nav is ok
     119                foreach ( $item_main_nav as $item ) {
     120                        $bp->blogs->nav->remove_main_nav_item( $bp->blogs->id, $item['slug'] );
     121                }
     122
     123                $this->assertEmpty( $bp->blogs->nav->main );
     124
     125                $tested = array();
     126
     127                // a random user is loggedin
     128                $this->set_current_user( $u );
     129                bp_update_is_item_admin( false, $bp->blogs->id );
     130
     131                // Set the home action
     132                $bp->current_action = 'home';
     133
     134                // Setup the nav for the user
     135                $bp->blogs->nav->setup_nav( $item_main_nav, $item_sub_nav );
     136
     137                // Catch the main nav
     138                ob_start();
     139                $bp->blogs->nav->display_main_nav();
     140                $tested['main'] = ob_get_contents();
     141                ob_end_clean();
     142
     143                // Set the manage action
     144                $bp->current_action = 'manage';
     145
     146                // Catch the sub nav
     147                ob_start();
     148                $bp->blogs->nav->display_sub_nav();
     149                $tested['sub'] = ob_get_contents();
     150                ob_end_clean();
     151
     152                // Test main nav links
     153                preg_match_all( '#href=(["\'])([^"\']+)\1#i', $tested['main'], $main_matches );
     154                $this->assertSame( array( trailingslashit( $blog_link . 'home' ) ), $main_matches[2] );
     155
     156                // Sub nav should be empty
     157                $this->assertEmpty( $tested['sub'] );
     158
     159                // Reset the blogs component
     160                unset( $bp->blogs->nav );
     161                unset( $bp->blogs->current_blog );
     162
     163                // Reset globals
     164                $bp->is_single_item = $reset_is_single_item;
     165                $bp->current_item   = $reset_current_item;
     166                $bp->current_action = $reset_current_action;
     167        }
     168}