WordPress.org

Plugin Directory

source: buddypress/trunk/bp-core/classes/class-bp-admin.php

Last change on this file was 2538855, checked in by imath, 32 hours ago

Update trunk with 8.0.0-RC1 code and create 8.0.0-RC1 tag from trunk

File size: 52.3 KB
Line 
1<?php
2/**
3 * Main BuddyPress Admin Class.
4 *
5 * @package BuddyPress
6 * @subpackage CoreAdministration
7 * @since 1.0.0
8 */
9
10// Exit if accessed directly.
11defined( 'ABSPATH' ) || exit;
12
13if ( !class_exists( 'BP_Admin' ) ) :
14
15/**
16 * Load BuddyPress plugin admin area.
17 *
18 * @todo Break this apart into each applicable Component.
19 *
20 * @since 1.6.0
21 */
22class BP_Admin {
23
24        /** Directory *************************************************************/
25
26        /**
27         * Path to the BuddyPress admin directory.
28         *
29         * @since 1.6.0
30         * @var string $admin_dir
31         */
32        public $admin_dir = '';
33
34        /** URLs ******************************************************************/
35
36        /**
37         * URL to the BuddyPress admin directory.
38         *
39         * @since 1.6.0
40         * @var string $admin_url
41         */
42        public $admin_url = '';
43
44        /**
45         * URL to the BuddyPress images directory.
46         *
47         * @since 1.6.0
48         * @var string $images_url
49         */
50        public $images_url = '';
51
52        /**
53         * URL to the BuddyPress admin CSS directory.
54         *
55         * @since 1.6.0
56         * @var string $css_url
57         */
58        public $css_url = '';
59
60        /**
61         * URL to the BuddyPress admin JS directory.
62         *
63         * @since 1.6.0
64         * @var string
65         */
66        public $js_url = '';
67
68        /** Other *****************************************************************/
69
70        /**
71         * Notices used for user feedback, like saving settings.
72         *
73         * @since 1.9.0
74         * @var array()
75         */
76        public $notices = array();
77
78        /** Methods ***************************************************************/
79
80        /**
81         * The main BuddyPress admin loader.
82         *
83         * @since 1.6.0
84         *
85         */
86        public function __construct() {
87                $this->setup_globals();
88                $this->includes();
89                $this->setup_actions();
90        }
91
92        /**
93         * Set admin-related globals.
94         *
95         * @since 1.6.0
96         */
97        private function setup_globals() {
98                $bp = buddypress();
99
100                // Paths and URLs
101                $this->admin_dir  = trailingslashit( $bp->plugin_dir  . 'bp-core/admin' ); // Admin path.
102                $this->admin_url  = trailingslashit( $bp->plugin_url  . 'bp-core/admin' ); // Admin url.
103                $this->images_url = trailingslashit( $this->admin_url . 'images'        ); // Admin images URL.
104                $this->css_url    = trailingslashit( $this->admin_url . 'css'           ); // Admin css URL.
105                $this->js_url     = trailingslashit( $this->admin_url . 'js'            ); // Admin css URL.
106
107                // Main settings page.
108                $this->settings_page = bp_core_do_network_admin() ? 'settings.php' : 'options-general.php';
109
110                // Main capability.
111                $this->capability = bp_core_do_network_admin() ? 'manage_network_options' : 'manage_options';
112        }
113
114        /**
115         * Include required files.
116         *
117         * @since 1.6.0
118         */
119        private function includes() {
120                require( $this->admin_dir . 'bp-core-admin-actions.php'    );
121                require( $this->admin_dir . 'bp-core-admin-settings.php'   );
122                require( $this->admin_dir . 'bp-core-admin-functions.php'  );
123                require( $this->admin_dir . 'bp-core-admin-components.php' );
124                require( $this->admin_dir . 'bp-core-admin-slugs.php'      );
125                require( $this->admin_dir . 'bp-core-admin-tools.php'      );
126                require( $this->admin_dir . 'bp-core-admin-optouts.php'    );
127        }
128
129        /**
130         * Set up the admin hooks, actions, and filters.
131         *
132         * @since 1.6.0
133         *
134         */
135        private function setup_actions() {
136
137                /* General Actions ***************************************************/
138
139                // Add some page specific output to the <head>.
140                add_action( 'bp_admin_head',            array( $this, 'admin_head'  ), 999 );
141
142                // Add menu item to settings menu.
143                add_action( 'admin_menu',               array( $this, 'site_admin_menus' ), 5 );
144                add_action( bp_core_admin_hook(),       array( $this, 'admin_menus' ), 5 );
145
146                // Enqueue all admin JS and CSS.
147                add_action( 'bp_admin_enqueue_scripts', array( $this, 'admin_register_styles' ), 1 );
148                add_action( 'bp_admin_enqueue_scripts', array( $this, 'admin_register_scripts' ), 1 );
149                add_action( 'bp_admin_enqueue_scripts', array( $this, 'enqueue_scripts' ) );
150
151                /* BuddyPress Actions ************************************************/
152
153                // Load the BuddyPress metabox in the WP Nav Menu Admin UI.
154                add_action( 'load-nav-menus.php', 'bp_admin_wp_nav_menu_meta_box' );
155
156                // Add settings.
157                add_action( 'bp_register_admin_settings', array( $this, 'register_admin_settings' ) );
158
159                // Add a link to BuddyPress Hello in the admin bar.
160                add_action( 'admin_bar_menu', array( $this, 'admin_bar_about_link' ), 100 );
161
162                // Add a description of new BuddyPress tools in the available tools page.
163                add_action( 'tool_box',            'bp_core_admin_available_tools_intro' );
164                add_action( 'bp_network_tool_box', 'bp_core_admin_available_tools_intro' );
165
166                // On non-multisite, catch.
167                add_action( 'load-users.php', 'bp_core_admin_user_manage_spammers' );
168
169                // Emails.
170                add_filter( 'manage_' . bp_get_email_post_type() . '_posts_columns',       array( $this, 'emails_register_situation_column' ) );
171                add_action( 'manage_' . bp_get_email_post_type() . '_posts_custom_column', array( $this, 'emails_display_situation_column_data' ), 10, 2 );
172
173                // Privacy Policy.
174                add_action( 'bp_admin_init', array( $this, 'add_privacy_policy_content' ) );
175
176                // BuddyPress Hello.
177                add_action( 'admin_footer', array( $this, 'about_screen' ) );
178
179                // BuddyPress Types administration.
180                add_action( 'load-edit-tags.php', array( 'BP_Admin_Types', 'register_types_admin' ) );
181
182                /* Filters ***********************************************************/
183
184                // Add link to settings page.
185                add_filter( 'plugin_action_links',               array( $this, 'modify_plugin_action_links' ), 10, 2 );
186                add_filter( 'network_admin_plugin_action_links', array( $this, 'modify_plugin_action_links' ), 10, 2 );
187
188                // Add "Mark as Spam" row actions on users.php.
189                add_filter( 'ms_user_row_actions', 'bp_core_admin_user_row_actions', 10, 2 );
190                add_filter( 'user_row_actions',    'bp_core_admin_user_row_actions', 10, 2 );
191
192                // Emails
193                add_filter( 'bp_admin_menu_order', array( $this, 'emails_admin_menu_order' ), 20 );
194        }
195
196        /**
197         * Register site- or network-admin nav menu elements.
198         *
199         * Contextually hooked to site or network-admin depending on current configuration.
200         *
201         * @since 1.6.0
202         */
203        public function admin_menus() {
204
205                // Bail if user cannot moderate.
206                if ( ! bp_current_user_can( 'manage_options' ) ) {
207                        return;
208                }
209
210                $hooks = array();
211
212                // Changed in BP 1.6 . See bp_core_admin_backpat_menu().
213                $hooks[] = add_menu_page(
214                        __( 'BuddyPress', 'buddypress' ),
215                        __( 'BuddyPress', 'buddypress' ),
216                        $this->capability,
217                        'bp-general-settings',
218                        'bp_core_admin_backpat_menu',
219                        'div'
220                );
221
222                $hooks[] = add_submenu_page(
223                        'bp-general-settings',
224                        __( 'BuddyPress Help', 'buddypress' ),
225                        __( 'Help', 'buddypress' ),
226                        $this->capability,
227                        'bp-general-settings',
228                        'bp_core_admin_backpat_page'
229                );
230
231                // Add the option pages.
232                $hooks[] = add_submenu_page(
233                        $this->settings_page,
234                        __( 'BuddyPress Components', 'buddypress' ),
235                        __( 'BuddyPress', 'buddypress' ),
236                        $this->capability,
237                        'bp-components',
238                        'bp_core_admin_components_settings'
239                );
240
241                $hooks[] = add_submenu_page(
242                        $this->settings_page,
243                        __( 'BuddyPress Pages', 'buddypress' ),
244                        __( 'BuddyPress Pages', 'buddypress' ),
245                        $this->capability,
246                        'bp-page-settings',
247                        'bp_core_admin_slugs_settings'
248                );
249
250                $hooks[] = add_submenu_page(
251                        $this->settings_page,
252                        __( 'BuddyPress Options', 'buddypress' ),
253                        __( 'BuddyPress Options', 'buddypress' ),
254                        $this->capability,
255                        'bp-settings',
256                        'bp_core_admin_settings'
257                );
258
259                // Credits.
260                $hooks[] = add_submenu_page(
261                        $this->settings_page,
262                        __( 'BuddyPress Credits', 'buddypress' ),
263                        __( 'BuddyPress Credits', 'buddypress' ),
264                        $this->capability,
265                        'bp-credits',
266                        array( $this, 'credits_screen' )
267                );
268
269                // For consistency with non-Multisite, we add a Tools menu in
270                // the Network Admin as a home for our Tools panel.
271                if ( is_multisite() && bp_core_do_network_admin() ) {
272                        $tools_parent = 'network-tools';
273
274                        $hooks[] = add_menu_page(
275                                __( 'Tools', 'buddypress' ),
276                                __( 'Tools', 'buddypress' ),
277                                $this->capability,
278                                $tools_parent,
279                                'bp_core_tools_top_level_item',
280                                '',
281                                24 // Just above Settings.
282                        );
283
284                        $hooks[] = add_submenu_page(
285                                $tools_parent,
286                                __( 'Available Tools', 'buddypress' ),
287                                __( 'Available Tools', 'buddypress' ),
288                                $this->capability,
289                                'available-tools',
290                                'bp_core_admin_available_tools_page'
291                        );
292                } else {
293                        $tools_parent = 'tools.php';
294                }
295
296                $hooks[] = add_submenu_page(
297                        $tools_parent,
298                        __( 'BuddyPress Tools', 'buddypress' ),
299                        __( 'BuddyPress', 'buddypress' ),
300                        $this->capability,
301                        'bp-tools',
302                        'bp_core_admin_tools'
303                );
304
305                $hooks[] = add_submenu_page(
306                        $tools_parent,
307                        __( 'Manage Opt-outs', 'buddypress' ),
308                        __( 'Manage Opt-outs', 'buddypress' ),
309                        $this->capability,
310                        'bp-optouts',
311                        'bp_core_optouts_admin'
312                );
313
314                // For network-wide configs, add a link to (the root site's) Emails screen.
315                if ( is_network_admin() && bp_is_network_activated() ) {
316                        $email_labels = bp_get_email_post_type_labels();
317                        $email_url    = get_admin_url( bp_get_root_blog_id(), 'edit.php?post_type=' . bp_get_email_post_type() );
318
319                        $hooks[] = add_menu_page(
320                                $email_labels['name'],
321                                $email_labels['menu_name'],
322                                $this->capability,
323                                '',
324                                '',
325                                'dashicons-email',
326                                26
327                        );
328
329                        // Hack: change the link to point to the root site's admin, not the network admin.
330                        $GLOBALS['menu'][26][2] = esc_url_raw( $email_url );
331                }
332
333                foreach( $hooks as $hook ) {
334                        add_action( "admin_head-$hook", 'bp_core_modify_admin_menu_highlight' );
335                }
336        }
337
338        /**
339         * Register site-admin nav menu elements.
340         *
341         * @since 2.5.0
342         */
343        public function site_admin_menus() {
344                if ( ! bp_current_user_can( 'manage_options' ) ) {
345                        return;
346                }
347
348                $hooks = array();
349
350                // Appearance > Emails.
351                $hooks[] = add_theme_page(
352                        _x( 'Emails', 'screen heading', 'buddypress' ),
353                        _x( 'Emails', 'screen heading', 'buddypress' ),
354                        $this->capability,
355                        'bp-emails-customizer-redirect',
356                        'bp_email_redirect_to_customizer'
357                );
358
359                // Emails > Customize.
360                $hooks[] = add_submenu_page(
361                        'edit.php?post_type=' . bp_get_email_post_type(),
362                        _x( 'Customize', 'email menu label', 'buddypress' ),
363                        _x( 'Customize', 'email menu label', 'buddypress' ),
364                        $this->capability,
365                        'bp-emails-customizer-redirect',
366                        'bp_email_redirect_to_customizer'
367                );
368
369                foreach( $hooks as $hook ) {
370                        add_action( "admin_head-$hook", 'bp_core_modify_admin_menu_highlight' );
371                }
372        }
373
374        /**
375         * Register the settings.
376         *
377         * @since 1.6.0
378         *
379         */
380        public function register_admin_settings() {
381
382                /* Main Section ******************************************************/
383
384                // Add the main section.
385                add_settings_section( 'bp_main', __( 'Main Settings', 'buddypress' ), 'bp_admin_setting_callback_main_section', 'buddypress' );
386
387                // Hide toolbar for logged out users setting.
388                add_settings_field( 'hide-loggedout-adminbar', __( 'Toolbar', 'buddypress' ), 'bp_admin_setting_callback_admin_bar', 'buddypress', 'bp_main' );
389                register_setting( 'buddypress', 'hide-loggedout-adminbar', 'intval' );
390
391                // Allow account deletion.
392                add_settings_field( 'bp-disable-account-deletion', __( 'Account Deletion', 'buddypress' ), 'bp_admin_setting_callback_account_deletion', 'buddypress', 'bp_main' );
393                register_setting( 'buddypress', 'bp-disable-account-deletion', 'intval' );
394
395                // Template pack picker.
396                add_settings_field( '_bp_theme_package_id', __( 'Template Pack', 'buddypress' ), 'bp_admin_setting_callback_theme_package_id', 'buddypress', 'bp_main', array( 'label_for' => '_bp_theme_package_id' ) );
397                register_setting( 'buddypress', '_bp_theme_package_id', 'sanitize_text_field' );
398
399                /* Members Section  **************************************************/
400
401                // Add the main section.
402                add_settings_section( 'bp_members', _x( 'Members Settings', 'BuddyPress setting tab', 'buddypress' ), 'bp_admin_setting_callback_members_section', 'buddypress' );
403
404                // Avatars.
405                add_settings_field( 'bp-disable-avatar-uploads', __( 'Profile Photo Uploads', 'buddypress' ), 'bp_admin_setting_callback_avatar_uploads', 'buddypress', 'bp_members' );
406                register_setting( 'buddypress', 'bp-disable-avatar-uploads', 'intval' );
407
408                // Cover images.
409                if ( bp_is_active( 'members', 'cover_image' ) ) {
410                        add_settings_field( 'bp-disable-cover-image-uploads', __( 'Cover Image Uploads', 'buddypress' ), 'bp_admin_setting_callback_cover_image_uploads', 'buddypress', 'bp_members' );
411                        register_setting( 'buddypress', 'bp-disable-cover-image-uploads', 'intval' );
412                }
413
414                // Community Invitations.
415                if ( bp_is_active( 'members', 'invitations' ) ) {
416                        add_settings_field( 'bp-enable-members-invitations', __( 'Invitations', 'buddypress' ), 'bp_admin_setting_callback_members_invitations', 'buddypress', 'bp_members' );
417                        register_setting( 'buddypress', 'bp-enable-members-invitations', 'intval' );
418                }
419
420                /* XProfile Section **************************************************/
421
422                if ( bp_is_active( 'xprofile' ) ) {
423
424                        // Add the main section.
425                        add_settings_section( 'bp_xprofile', _x( 'Profile Settings', 'BuddyPress setting tab', 'buddypress' ), 'bp_admin_setting_callback_xprofile_section', 'buddypress' );
426
427                        // Profile sync setting.
428                        add_settings_field( 'bp-disable-profile-sync',   __( 'Profile Syncing',  'buddypress' ), 'bp_admin_setting_callback_profile_sync', 'buddypress', 'bp_xprofile' );
429                        register_setting  ( 'buddypress', 'bp-disable-profile-sync', 'intval' );
430                }
431
432                /* Groups Section ****************************************************/
433
434                if ( bp_is_active( 'groups' ) ) {
435
436                        // Add the main section.
437                        add_settings_section( 'bp_groups', __( 'Groups Settings',  'buddypress' ), 'bp_admin_setting_callback_groups_section', 'buddypress' );
438
439                        // Allow subscriptions setting.
440                        add_settings_field( 'bp_restrict_group_creation', __( 'Group Creation', 'buddypress' ), 'bp_admin_setting_callback_group_creation',   'buddypress', 'bp_groups' );
441                        register_setting( 'buddypress', 'bp_restrict_group_creation', 'intval' );
442
443                        // Allow group avatars.
444                        add_settings_field( 'bp-disable-group-avatar-uploads', __( 'Group Photo Uploads', 'buddypress' ), 'bp_admin_setting_callback_group_avatar_uploads', 'buddypress', 'bp_groups' );
445                        register_setting( 'buddypress', 'bp-disable-group-avatar-uploads', 'intval' );
446
447                        // Allow group cover images.
448                        if ( bp_is_active( 'groups', 'cover_image' ) ) {
449                                add_settings_field( 'bp-disable-group-cover-image-uploads', __( 'Group Cover Image Uploads', 'buddypress' ), 'bp_admin_setting_callback_group_cover_image_uploads', 'buddypress', 'bp_groups' );
450                                register_setting( 'buddypress', 'bp-disable-group-cover-image-uploads', 'intval' );
451                        }
452                }
453
454                /* Activity Section **************************************************/
455
456                if ( bp_is_active( 'activity' ) ) {
457
458                        // Add the main section.
459                        add_settings_section( 'bp_activity', __( 'Activity Settings', 'buddypress' ), 'bp_admin_setting_callback_activity_section', 'buddypress' );
460
461                        // Activity commenting on post and comments.
462                        add_settings_field( 'bp-disable-blogforum-comments', __( 'Post Comments', 'buddypress' ), 'bp_admin_setting_callback_blogforum_comments', 'buddypress', 'bp_activity' );
463                        register_setting( 'buddypress', 'bp-disable-blogforum-comments', 'bp_admin_sanitize_callback_blogforum_comments' );
464
465                        // Activity Heartbeat refresh.
466                        add_settings_field( '_bp_enable_heartbeat_refresh', __( 'Activity auto-refresh', 'buddypress' ), 'bp_admin_setting_callback_heartbeat', 'buddypress', 'bp_activity' );
467                        register_setting( 'buddypress', '_bp_enable_heartbeat_refresh', 'intval' );
468
469                        // Allow activity akismet.
470                        if ( is_plugin_active( 'akismet/akismet.php' ) && defined( 'AKISMET_VERSION' ) ) {
471                                add_settings_field( '_bp_enable_akismet', __( 'Akismet', 'buddypress' ), 'bp_admin_setting_callback_activity_akismet', 'buddypress', 'bp_activity' );
472                                register_setting( 'buddypress', '_bp_enable_akismet', 'intval' );
473                        }
474                }
475        }
476
477        /**
478         * Add a link to BuddyPress Hello to the admin bar.
479         *
480         * @since 1.9.0
481         * @since 3.0.0 Hooked at priority 100 (was 15).
482         *
483         * @param WP_Admin_Bar $wp_admin_bar
484         */
485        public function admin_bar_about_link( $wp_admin_bar ) {
486                if ( ! is_user_logged_in() ) {
487                        return;
488                }
489
490                $wp_admin_bar->add_node( array(
491                        'parent' => 'wp-logo',
492                        'id'     => 'bp-about',
493                        'title'  => esc_html_x( 'Hello, BuddyPress!', 'Colloquial alternative to "learn about BuddyPress"', 'buddypress' ),
494                        'href'   => bp_get_admin_url( '?hello=buddypress' ),
495                        'meta'   => array(
496                                'class' => 'say-hello-buddypress',
497                        ),
498                ) );
499        }
500
501        /**
502         * Add Settings link to plugins area.
503         *
504         * @since 1.6.0
505         *
506         * @param array  $links Links array in which we would prepend our link.
507         * @param string $file  Current plugin basename.
508         * @return array Processed links.
509         */
510        public function modify_plugin_action_links( $links, $file ) {
511
512                // Return normal links if not BuddyPress.
513                if ( plugin_basename( buddypress()->basename ) != $file ) {
514                        return $links;
515                }
516
517                // Add a few links to the existing links array.
518                return array_merge( $links, array(
519                        'settings' => '<a href="' . esc_url( add_query_arg( array( 'page' => 'bp-components' ), bp_get_admin_url( $this->settings_page ) ) ) . '">' . esc_html__( 'Settings', 'buddypress' ) . '</a>',
520                        'about'    => '<a href="' . esc_url( bp_get_admin_url( '?hello=buddypress' ) ) . '">' . esc_html_x( 'Hello, BuddyPress!', 'Colloquial alternative to "learn about BuddyPress"', 'buddypress' ) . '</a>'
521                ) );
522        }
523
524        /**
525         * Add some general styling to the admin area.
526         *
527         * @since 1.6.0
528         */
529        public function admin_head() {
530
531                // Settings pages.
532                remove_submenu_page( $this->settings_page, 'bp-page-settings' );
533                remove_submenu_page( $this->settings_page, 'bp-settings'      );
534                remove_submenu_page( $this->settings_page, 'bp-credits'       );
535
536                // Network Admin Tools.
537                remove_submenu_page( 'network-tools', 'network-tools' );
538
539                // About and Credits pages.
540                remove_submenu_page( 'index.php', 'bp-about'   );
541                remove_submenu_page( 'index.php', 'bp-credits' );
542
543                // Nonmembers Opt-outs page.
544                if ( is_network_admin() ) {
545                        remove_submenu_page( 'network-tools', 'bp-optouts' );
546                } else {
547                        remove_submenu_page( 'tools.php', 'bp-optouts' );
548                }
549        }
550
551        /**
552         * Add some general styling to the admin area.
553         *
554         * @since 1.6.0
555         */
556        public function enqueue_scripts() {
557                wp_enqueue_style( 'bp-admin-common-css' );
558
559                // BuddyPress Hello.
560                if ( 0 === strpos( get_current_screen()->id, 'dashboard' ) && ! empty( $_GET['hello'] ) && $_GET['hello'] === 'buddypress' ) {
561                        wp_enqueue_style( 'bp-hello-css' );
562                        wp_enqueue_script( 'bp-hello-js' );
563                        wp_localize_script( 'bp-hello-js', 'bpHelloStrings', array(
564                                'pageNotFound' => __( 'Sorry, the page you requested was not found.', 'buddypress' ),
565                                'modalLabel'   => __( 'Hello BuddyPress', 'buddypress' ),
566                        ) );
567                }
568        }
569
570        /**
571         * Registers BuddyPress's suggested privacy policy language.
572         *
573         * @since 4.0.0
574         */
575        public function add_privacy_policy_content() {
576                // Nothing to do if we're running < WP 4.9.6.
577                if ( bp_is_running_wp( '4.9.6', '<' ) ) {
578                        return;
579                }
580
581                $suggested_text = '<strong class="privacy-policy-tutorial">' . esc_html__( 'Suggested text:', 'buddypress' ) . ' </strong>';
582                $content = '';
583
584                $content .= '<div class="wp-suggested-text">';
585
586                $content .= '<h2>' . esc_html__( 'What personal data we collect and why we collect it', 'buddypress' ) . '</h2>';
587                $content .= '<p class="privacy-policy-tutorial">' . esc_html__( 'Sites powered by BuddyPress rely heavily on user-provided data. In this section, you should note what data you collect, from both registered users and anonymous visitors.', 'buddypress' ) . '</p>';
588
589                if ( bp_is_active( 'xprofile' ) ) {
590                        $content .= '<h3>' . esc_html__( 'Profile Data', 'buddypress' ) . '</h3>';
591                        $content .= '<p class="privacy-policy-tutorial">' . esc_html__( 'In this section you should note what information is collected on user profiles. The suggested text gives an overview of the kinds of profile data collected by BuddyPress.', 'buddypress' ) . '</p>';
592
593                        $content .= '<p>' . $suggested_text . esc_html__( 'When you register for the site, you may be asked to provide certain personal data for display on your profile. The "Name" field is required as well as public, and user profiles are visible to any site visitor. Other profile information may be required or optional, as configured by the site administrator.', 'buddypress' ) . '</p>';
594                        $content .= '<p>' . esc_html__( 'User information provided during account registration can be modified or removed on the Profile > Edit panel. In most cases, users also have control over who is able to view a particular piece of profile content, limiting visibility on a field-by-field basis to friends, logged-in users, or administrators only. Site administrators can read and edit all profile data for all users.', 'buddypress' ) . '</p>';
595                }
596
597                if ( bp_is_active( 'activity' ) ) {
598                        $content .= '<h3>' . esc_html__( 'Activity', 'buddypress' ) . '</h3>';
599                        $content .= '<p class="privacy-policy-tutorial">' . esc_html__( 'In this section you should describe the kinds of information collected in the activity stream, how and whether it can be edited or deleted, and to whom the activity is visible.', 'buddypress' ) . '</p>';
600
601                        $content .= '<p>' . $suggested_text . esc_html__( 'This site records certain user actions, in the form of "activity" data. Activity includes updates and comments posted directly to activity streams, as well as descriptions of other actions performed while using the site, such as new friendships, newly joined groups, and profile updates.', 'buddypress' ) . '</p>';
602                        $content .= '<p>' . esc_html__( 'The content of activity items obey the same privacy rules as the contexts in which the activity items are created. For example, activity updates created in a user\'s profile is publicly visible, while activity items generated in a private group are visible only to members of that group. Site administrators can view all activity items, regardless of context.', 'buddypress' ) . '</p>';
603                        $content .= '<p>' . esc_html__( 'Activity items may be deleted at any time by users who created them. Site administrators can edit all activity items.', 'buddypress' ) . '</p>';
604                }
605
606                if ( bp_is_active( 'messages' ) ) {
607                        $content .= '<h3>' . esc_html__( 'Messages', 'buddypress' ) . '</h3>';
608                        $content .= '<p class="privacy-policy-tutorial">' . esc_html__( 'In this section you should describe any personal data related to private messages.', 'buddypress' ) . '</p>';
609
610                        $content .= '<p>' . $suggested_text . esc_html__( 'The content of private messages is visible only to the sender and the recipients of the message. With the exception of site administrators, who can read all private messages, private message content is never visible to other users or site visitors. Site administrators may delete the content of any message.', 'buddypress' ) . '</p>';
611                }
612
613                $content .= '<h3>' . esc_html__( 'Cookies', 'buddypress' ) . '</h3>';
614                $content .= '<p class="privacy-policy-tutorial">' . esc_html__( 'In this section you should describe the BuddyPress-specific cookies that your site collects. The suggested text describes the default cookies.', 'buddypress' ) . '</p>';
615
616                $content .= '<p>' . $suggested_text . esc_html__( 'We use a cookie to show success and failure messages to logged-in users, in response to certain actions, like joining a group. These cookies contain no personal data, and are deleted immediately after the next page load.', 'buddypress' ) . '</p>';
617
618                $content .= '<p>' . esc_html__( 'We use cookies on group, member, and activity directories to keep track of a user\'s browsing preferences. These preferences include the last-selected values of the sort and filter dropdowns, as well as pagination information. These cookies contain no personal data, and are deleted after 24 hours.', 'buddypress' ) . '</p>';
619
620                if ( bp_is_active( 'groups' ) ) {
621                        $content .= '<p>' . esc_html__( 'When a logged-in user creates a new group, we use a number of cookies to keep track of the group creation process. These cookies contain no personal data, and are deleted either upon the successful creation of the group or after 24 hours.', 'buddypress' ) . '</p>';
622                }
623
624                $content .= '</div><!-- .wp-suggested-text -->';
625
626                wp_add_privacy_policy_content(
627                        'BuddyPress',
628                        wp_kses_post( wpautop( $content, false ) )
629                );
630        }
631
632        /** About *****************************************************************/
633
634        /**
635         * Output the BuddyPress Hello template.
636         *
637         * @since 1.7.0 Screen content.
638         * @since 3.0.0 Now outputs BuddyPress Hello template.
639         */
640        public function about_screen() {
641                if ( 0 !== strpos( get_current_screen()->id, 'dashboard' ) || empty( $_GET['hello'] ) || $_GET['hello'] !== 'buddypress' ) {
642                        return;
643                }
644
645                // Get BuddyPress stable version.
646                $version      =  self::display_version();
647                $version_slug = 'version-' . str_replace( '.', '-', $version );
648        ?>
649
650                <div id="bp-hello-container">
651                        <div id="plugin-information-scrollable" role="document">
652                                <div id='plugin-information-title' class="with-banner">
653                                        <div class='vignette'></div>
654                                        <h1>
655                                                <?php printf(
656                                                        /* translators: %s is the placeholder for the BuddyPress version number. */
657                                                        esc_html__( 'BuddyPress %s', 'buddypress' ),
658                                                        $version
659                                                ); ?>
660                                        </h1>
661                                </div>
662                                <div id="plugin-information-tabs">
663                                        <a name="whats-new" href="#whats-new" class="current"><?php esc_html_e( 'What\'s new?', 'buddypress' ); ?></a>
664                                        <a name="changelog" href="#changelog" class="dynamic" data-slug="<?php echo esc_attr( $version_slug ); ?>" data-endpoint="https://codex.buddypress.org/wp-json/wp/v2/pages"><?php esc_html_e( 'Changelog', 'buddypress' ); ?></a>
665                                        <a name="get-involved" href="#get-involved" class="dynamic" data-slug="participate-and-contribute" data-endpoint="https://codex.buddypress.org/wp-json/wp/v2/pages"><?php esc_html_e( 'Get involved', 'buddypress' ); ?></a>
666                                </div>
667
668                                <div class="bp-hello-content">
669                                        <div id="dynamic-content"></div>
670                                        <div id="top-features">
671                                                <h2><?php esc_html_e( 'Your current members are the best way to recruit fantastic new members for your community.', 'buddypress' ); ?></h2>
672                                                <p>
673                                                        <?php esc_html_e( 'Whether public registration is enabled or not, you can activate this great new opt-in feature from your site\'s BuddyPress settings; with it, your trusted members will handpick new members who will enrich your community', 'buddypress' ); ?>
674                                                </p>
675                                                <figure class="bp-hello-aligncenter">
676                                                        <img src="<?php echo esc_url( buddypress()->plugin_url . 'bp-core/images/bp-members-invitations-invite-screen.png' ); ?>" alt="<?php esc_attr_e( 'Illustration showing the Members Invite Screen.', 'buddypress' ); ?>" />
677                                                </figure>
678                                                <p><?php esc_html_e( 'Once activated, each member will be able to send new Member Invitation emails and manage the pending invitations directly from his or her profile area.', 'buddypress' ); ?>
679                                                <figure class="bp-hello-aligncenter">
680                                                        <img src="<?php echo esc_url( buddypress()->plugin_url . 'bp-core/images/bp-members-invitations-manage-admin-screen.png' ); ?>" alt="<?php esc_attr_e( 'Illustration showing the Members Invite Screen.', 'buddypress' ); ?>" />
681                                                </figure>
682                                                <p>
683                                                        <?php esc_html_e( 'You keep control of everything thanks to two new screens we added to the BuddyPress Tools dashboard: invitations and opt-outs management.', 'buddypress' ); ?>
684                                                        <?php printf(
685                                                                /* translators: %s is the placeholder for the link to the BP Members Invitations developer note. */
686                                                                esc_html__( 'Read more about the feature in this %s.', 'buddypress' ),
687                                                                sprintf(
688                                                                        '<a href="%1$s">%2$s</a>',
689                                                                        esc_url( 'https://bpdevel.wordpress.com/2021/05/26/bp-8-0-introduces-site-membership-invitations/' ),
690                                                                        esc_html__( 'developer note', 'buddypress' )
691                                                                )
692                                                        ); ?>
693                                                </p>
694
695                                                <hr class="bp-hello-divider"/>
696
697                                                <h2><?php esc_html_e( 'Improved registration experience.', 'buddypress' ); ?></h2>
698                                                <p>
699                                                        <?php esc_html_e( 'First, you can select any xProfile field from any xProfile field group to use on your site\'s registration form.', 'buddypress' ); ?>
700                                                        <?php printf(
701                                                                /* translators: %s is the placeholder for the link to the Selectable Signup Fields developer note. */
702                                                                esc_html__( 'Learn more about it reading this %s.', 'buddypress' ),
703                                                                sprintf(
704                                                                        '<a href="%1$s">%2$s</a>',
705                                                                        esc_url( 'https://bpdevel.wordpress.com/2021/05/06/selectable-xprofile-sign-up-fields-in-8-0-0/' ),
706                                                                        esc_html__( 'developer note', 'buddypress' )
707                                                                )
708                                                        ); ?>
709                                                </p>
710                                                <figure class="bp-hello-aligncenter">
711                                                        <img src="<?php echo esc_url( buddypress()->plugin_url . 'bp-core/images/bp-xprofile-admin-signup-fields.png' ); ?>" alt="<?php esc_attr_e( 'Illustration showing the xProfile Administration Screen.', 'buddypress' ); ?>" />
712                                                </figure>
713                                                <p>
714                                                        <?php esc_html_e( 'Second, if your site requires that users accept specific rules such as terms of service or a code of conduct, you can now take advantage of the new Checkbox Acceptance xProfile Field type to record their agreement.', 'buddypress' ); ?>
715                                                        <?php printf(
716                                                                /* translators: %s is the placeholder for the link to the Checkbox Acceptance field type developer note. */
717                                                                esc_html__( 'This %s will teach you more about it.', 'buddypress' ),
718                                                                sprintf(
719                                                                        '<a href="%1$s">%2$s</a>',
720                                                                        esc_url( 'https://bpdevel.wordpress.com/2021/05/05/new-xprofile-field-type-checkbox-acceptance-will-be-introduced-in-buddypress-8-0-0/' ),
721                                                                        esc_html__( 'developer note', 'buddypress' )
722                                                                )
723                                                        ); ?>
724                                                </p>
725                                                <figure class="bp-hello-aligncenter">
726                                                        <img src="<?php echo esc_url( buddypress()->plugin_url . 'bp-core/images/bp-xprofile-checkbox-acceptance-field-type.png' ); ?>" alt="<?php esc_attr_e( 'Illustration showing an example of Checkbox Acceptance xProfile field type display.', 'buddypress' ); ?>" />
727                                                </figure>
728                                                <p>
729                                                        <?php esc_html_e( 'Third, once a user activates his or her account, BuddyPress will send a welcome email to help get him or her engaged with your community.', 'buddypress' ); ?>
730                                                        <?php esc_html_e( 'You can customize the content of this email from the Emails menu of your WordPress dashboard.', 'buddypress' ); ?>
731                                                        <?php printf(
732                                                                /* translators: %s is the placeholder for the link to the Welcome Email developer note. */
733                                                                esc_html__( 'Have a look to this %s to find out more about it.', 'buddypress' ),
734                                                                sprintf(
735                                                                        '<a href="%1$s">%2$s</a>',
736                                                                        esc_url( 'https://bpdevel.wordpress.com/2021/05/24/8-0-0-will-include-a-bp-email-to-welcome-new-community-members/' ),
737                                                                        esc_html__( 'developer note', 'buddypress' )
738                                                                )
739                                                        ); ?>
740                                                </p>
741
742                                                <hr class="bp-hello-divider"/>
743
744                                                <h2><?php esc_html_e( 'WP xProfile field types.', 'buddypress' ); ?></h2>
745                                                <p>
746                                                        <?php esc_html_e( 'Two new field types can now be used to include WordPress-specific information about the member in xProfile field loops without duplicating data.', 'buddypress' ); ?>
747                                                </p>
748                                                <figure class="bp-hello-aligncenter">
749                                                        <img src="<?php echo esc_url( buddypress()->plugin_url . 'bp-core/images/bp-xprofile-wp-field-type.png' ); ?>" alt="<?php esc_attr_e( 'Illustration showing the xProfile Field Edit Screen.', 'buddypress' ); ?>" />
750                                                </figure>
751                                                <p>
752                                                        <?php esc_html_e( 'The WP Biography field type lets you include the user\'s Biographical Info and thanks to the WP Textbox field you can include the first & last name, the Website URL as well as any of the custom contact methods of your users.', 'buddypress' ); ?>
753                                                        <?php printf(
754                                                                /* translators: %s is the placeholder for the link to the WP xProfile Field Type developer note. */
755                                                                esc_html__( 'Read more about it in this %s.', 'buddypress' ),
756                                                                sprintf(
757                                                                        '<a href="%1$s">%2$s</a>',
758                                                                        esc_url( 'https://bpdevel.wordpress.com/2021/03/24/wordpress-xprofile-field-types/' ),
759                                                                        esc_html__( 'developer note', 'buddypress' )
760                                                                )
761                                                        ); ?>
762                                                </p>
763
764                                                <hr class="bp-hello-divider"/>
765
766                                                <h2><?php esc_html_e( 'Under the hood', 'buddypress' ); ?></h2>
767                                                <p>
768                                                        <?php esc_html_e( '8.0.0 includes more than 45 changes to improve the Activity component, BP Nouveau Template pack, the BP REST API and many more components and features.', 'buddypress' ); ?>
769                                                        <?php esc_html_e( 'Click on the "Changelog" tab to discover them all!', 'buddypress' ); ?>
770                                                </p>
771                                                <figure class="bp-hello-aligncenter">
772                                                        <div class="dashicons dashicons-buddicons-buddypress-logo big"></div>
773                                                </figure>
774
775                                                <hr class="bp-hello-divider"/>
776
777                                                <h2><?php echo esc_html( _x( 'Your feedback', 'screen heading', 'buddypress' ) ); ?></h2>
778                                                <p>
779                                                        <?php esc_html_e( 'How are you using BuddyPress? Receiving your feedback and suggestions for future versions of BuddyPress genuinely motivates and encourages our contributors.', 'buddypress' ); ?>
780                                                        <?php
781                                                        printf(
782                                                                /* translators: %s is the placeholder for the link to BuddyPress support forums. */
783                                                                esc_html__( 'Please %s about this version of BuddyPress on our website.', 'buddypress' ),
784                                                                sprintf(
785                                                                        '<a href="%1$s">%2$s</a>',
786                                                                        esc_url( 'https://buddypress.org/support/' ),
787                                                                        esc_html__( 'share your feedback', 'buddypress' )
788                                                                )
789                                                        );
790                                                        ?>
791                                                </p>
792                                                <p><?php esc_html_e( 'Thank you for using BuddyPress! 😊', 'buddypress' ); ?></p>
793
794                                                <br /><br />
795                                        </div>
796                                </div>
797                        </div>
798                        <div id="plugin-information-footer">
799                                <div class="bp-hello-social-cta">
800                                        <p>
801                                                <?php
802                                                printf(
803                                                        /* translators: 1: heart dashicons. 2: BP Credits screen url. 3: number of BuddyPress contributors to this version. */
804                                                        _n( 'Built with %1$s by <a href="%2$s">%3$d volunteer</a>.', 'Built with %1$s by <a href="%2$s">%3$d volunteers</a>.', 55, 'buddypress' ),
805                                                        '<span class="dashicons dashicons-heart"></span>',
806                                                        esc_url( bp_get_admin_url( 'admin.php?page=bp-credits' ) ),
807                                                        number_format_i18n( 31 )
808                                                );
809                                                ?>
810                                        </p>
811                                </div>
812
813                                <div class="bp-hello-social-links">
814                                        <ul class="bp-hello-social">
815                                                <li>
816                                                        <?php
817                                                        printf(
818                                                                '<a class="twitter bp-tooltip" data-bp-tooltip="%1$s" href="%2$s"><span class="screen-reader-text">%3$s</span></a>',
819                                                                esc_attr__( 'Follow BuddyPress on Twitter', 'buddypress' ),
820                                                                esc_url( 'https://twitter.com/buddypress' ),
821                                                                esc_html__( 'Follow BuddyPress on Twitter', 'buddypress' )
822                                                        );
823                                                        ?>
824                                                </li>
825
826                                                <li>
827                                                        <?php
828                                                        printf(
829                                                                '<a class="support bp-tooltip" data-bp-tooltip="%1$s" href="%2$s"><span class="screen-reader-text">%3$s</span></a>',
830                                                                esc_attr__( 'Visit the Support Forums', 'buddypress' ),
831                                                                esc_url( 'https://buddypress.org/support/' ),
832                                                                esc_html__( 'Visit the Support Forums', 'buddypress' )
833                                                        );
834                                                        ?>
835                                                </li>
836                                        </ul>
837                                </div>
838                        </div>
839                </div>
840
841                <?php
842        }
843
844        /**
845         * Output the credits screen.
846         *
847         * Hardcoding this in here is pretty janky. It's fine for now, but we'll
848         * want to leverage api.wordpress.org eventually.
849         *
850         * @since 1.7.0
851         */
852        public function credits_screen() {
853        ?>
854
855                <div class="wrap bp-about-wrap">
856
857                <h1 class="wp-heading-inline"><?php esc_html_e( 'BuddyPress Settings', 'buddypress' ); ?></h1>
858                <hr class="wp-header-end">
859
860                <h2 class="nav-tab-wrapper"><?php bp_core_admin_tabs( esc_html__( 'Credits', 'buddypress' ) ); ?></h2>
861
862                        <p class="about-description"><?php esc_html_e( 'Meet the contributors behind BuddyPress:', 'buddypress' ); ?></p>
863
864                        <h3 class="wp-people-group"><?php esc_html_e( 'Project Leaders', 'buddypress' ); ?></h3>
865                        <ul class="wp-people-group " id="wp-people-group-project-leaders">
866                                <li class="wp-person" id="wp-person-johnjamesjacoby">
867                                        <a class="web" href="https://profiles.wordpress.org/johnjamesjacoby"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/7a2644fb53ae2f7bfd7143b504af396c?s=120">
868                                        John James Jacoby</a>
869                                        <span class="title"><?php esc_html_e( 'Project Lead', 'buddypress' ); ?></span>
870                                </li>
871                                <li class="wp-person" id="wp-person-boonebgorges">
872                                        <a class="web" href="https://profiles.wordpress.org/boonebgorges"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/9cf7c4541a582729a5fc7ae484786c0c?s=120">
873                                        Boone B. Gorges</a>
874                                        <span class="title"><?php esc_html_e( 'Lead Developer', 'buddypress' ); ?></span>
875                                </li>
876                                <li class="wp-person" id="wp-person-djpaul">
877                                        <a class="web" href="https://profiles.wordpress.org/djpaul"><img alt="" class="gravatar" src="https://avatars2.githubusercontent.com/u/1275914?s=120">
878                                        Paul Gibbs</a>
879                                        <span class="title"><?php esc_html_e( 'Lead Developer', 'buddypress' ); ?></span>
880                                </li>
881                                <li class="wp-person" id="wp-person-r-a-y">
882                                        <a class="web" href="https://profiles.wordpress.org/r-a-y"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/3bfa556a62b5bfac1012b6ba5f42ebfa?s=120">
883                                        Ray</a>
884                                        <span class="title"><?php esc_html_e( 'Lead Developer', 'buddypress' ); ?></span>
885                                </li>
886                                <li class="wp-person" id="wp-person-imath">
887                                        <a class="web" href="https://profiles.wordpress.org/imath"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/8b208ca408dad63888253ee1800d6a03?s=120">
888                                        Mathieu Viet</a>
889                                        <span class="title"><?php esc_html_e( 'Lead Developer', 'buddypress' ); ?></span>
890                                </li>
891                                <li class="wp-person" id="wp-person-mercime">
892                                        <a class="web" href="https://profiles.wordpress.org/mercime"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/fae451be6708241627983570a1a1817a?s=120">
893                                        Mercime</a>
894                                        <span class="title"><?php esc_html_e( 'Lead Developer', 'buddypress' ); ?></span>
895                                </li>
896                        </ul>
897
898                        <h3 class="wp-people-group"><?php esc_html_e( 'BuddyPress Team', 'buddypress' ); ?></h3>
899                        <ul class="wp-people-group " id="wp-people-group-core-team">
900                                <li class="wp-person" id="wp-person-hnla">
901                                        <a class="web" href="https://profiles.wordpress.org/hnla"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/3860c955aa3f79f13b92826ae47d07fe?s=120">
902                                        Hugo Ashmore</a>
903                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
904                                </li>
905                                <li class="wp-person" id="wp-person-dcavins">
906                                        <a class="web" href="https://profiles.wordpress.org/dcavins"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/a5fa7e83d59cb45ebb616235a176595a?s=120">
907                                        David Cavins</a>
908                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
909                                </li>
910                                <li class="wp-person" id="wp-person-tw2113">
911                                        <a class="web" href="https://profiles.wordpress.org/tw2113"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/a5d7c934621fa1c025b83ee79bc62366?s=120">
912                                        Michael Beckwith</a>
913                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
914                                </li>
915                                <li class="wp-person" id="wp-person-henry-wright">
916                                        <a class="web" href="https://profiles.wordpress.org/henry.wright"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/0da2f1a9340d6af196b870f6c107a248?s=120">
917                                        Henry Wright</a>
918                                        <span class="title"><?php esc_html_e( 'Community Support', 'buddypress' ); ?></span>
919                                </li>
920                                <li class="wp-person" id="wp-person-danbp">
921                                        <a class="web" href="https://profiles.wordpress.org/danbp"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/0deae2e7003027fbf153500cd3fa5501?s=120">
922                                        danbp</a>
923                                        <span class="title"><?php esc_html_e( 'Community Support', 'buddypress' ); ?></span>
924                                </li>
925                                <li class="wp-person" id="wp-person-shanebp">
926                                        <a class="web" href="https://profiles.wordpress.org/shanebp"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/ffd294ab5833ba14aaf175f9acc71cc4?s=120">
927                                        shanebp</a>
928                                        <span class="title"><?php esc_html_e( 'Community Support', 'buddypress' ); ?></span>
929                                </li>
930                                <li class="wp-person" id="wp-person-slaffik">
931                                        <a class="web" href="https://profiles.wordpress.org/r-a-y"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/61fb07ede3247b63f19015f200b3eb2c?s=120">
932                                        Slava Abakumov</a>
933                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
934                                </li>
935                                <li class="wp-person" id="wp-person-offereins">
936                                        <a class="web" href="https://profiles.wordpress.org/Offereins"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/2404ed0a35bb41aedefd42b0a7be61c1?s=120">
937                                        Laurens Offereins</a>
938                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
939                                </li>
940                                <li class="wp-person" id="wp-person-netweb">
941                                        <a class="web" href="https://profiles.wordpress.org/netweb"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/97e1620b501da675315ba7cfb740e80f?s=120">
942                                        Stephen Edgar</a>
943                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
944                                </li>
945                                <li class="wp-person" id="wp-person-espellcaste">
946                                        <a class="web" href="https://profiles.wordpress.org/espellcaste"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/b691e67be0ba5cad6373770656686bc3?s=120">
947                                        Renato Alves</a>
948                                        <span class="title"><?php esc_html_e( 'Core Developer', 'buddypress' ); ?></span>
949                                </li>
950                                <li class="wp-person" id="wp-person-venutius">
951                                        <a class="web" href="https://profiles.wordpress.org/venutius"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/6a7c42a77fd94b82b217a7a97afdddbc?s=120">
952                                        Venutius</a>
953                                        <span class="title"><?php esc_html_e( 'Community Support', 'buddypress' ); ?></span>
954                                </li>
955                        </ul>
956
957                        <h3 class="wp-people-group">
958                                <?php
959                                printf(
960                                        /* translators: %s: BuddyPress version number */
961                                        esc_html__( 'Noteworthy Contributors to %s', 'buddypress' ),
962                                        self::display_version()
963                                );
964                                ?>
965                        </h3>
966                        <ul class="wp-people-group " id="wp-people-group-noteworthy">
967                                <li class="wp-person" id="wp-person-vapvarun">
968                                        <a class="web" href="https://profiles.wordpress.org/vapvarun"><img alt="" class="gravatar" src="//gravatar.com/avatar/78a3bf7eb3a1132fc667f96f2631e448?s=120">
969                                        Varun Dubey</a>
970                                </li>
971                                <li class="wp-person" id="wp-person-sbrajesh">
972                                        <a class="web" href="https://profiles.wordpress.org/sbrajesh/"><img alt="" class="gravatar" src="//gravatar.com/avatar/2106622ee90d53d15ac1402806616aca?s=120">
973                                        Brajesh Singh</a>
974                                </li>
975                                <li class="wp-person" id="wp-person-oztaser">
976                                        <a class="web" href="https://profiles.wordpress.org/oztaser/"><img alt="" class="gravatar" src="//gravatar.com/avatar/06eb4dd13c0113bf826968ae16a13e52?s=120">
977                                        Adil Oztaser</a>
978                                </li>
979                        </ul>
980
981                        <h3 class="wp-people-group">
982                                <?php
983                                printf(
984                                        /* translators: %s: BuddyPress version number */
985                                        esc_html__( 'All Contributors to BuddyPress %s', 'buddypress' ),
986                                        self::display_version()
987                                );
988                                ?>
989                        </h3>
990                        <p class="wp-credits-list">
991                                <a href="https://profiles.wordpress.org/oztaser/">Adil Oztaser (oztaser)</a>,
992                                <a href="https://profiles.wordpress.org/dontdream/">Andrea Tarantini (dontdream)</a>,
993                                <a href="https://profiles.wordpress.org/boonebgorges/">Boone B Gorges (boonebgorges)</a>,
994                                <a href="https://profiles.wordpress.org/sbrajesh/">Brajesh Singh (sbrajesh)</a>,
995                                <a href="https://profiles.wordpress.org/needle/">Christian Wach (needle)</a>,
996                                <a href="https://profiles.wordpress.org/comminski/">comminski</a>,
997                                <a href="https://profiles.wordpress.org/dcavins/">David Cavins (dcavins)</a>,
998                                <a href="https://github.com/dominic-ks/">dominic-ks</a>,
999                                <a href="https://github.com/edusperoni/">Eduardo Speroni (edusperoni)</a>,
1000                                <a href="https://profiles.wordpress.org/hz_i3/">hz_i3</a>,
1001                                <a href="https://profiles.wordpress.org/johnjamesjacoby/">John James Jacoby (johnjamesjacoby)</a>,
1002                                <a href="https://profiles.wordpress.org/krupajnanda/">Krupa (krupajnanda)</a>,
1003                                <a href="https://profiles.wordpress.org/offereins/">Laurens Offereins</a>,
1004                                <a href="https://profiles.wordpress.org/mahdiar/">mahdiar</a>,
1005                                <a href="https://profiles.wordpress.org/imath/">Mathieu Viet (imath)</a>,
1006                                <a href="https://profiles.wordpress.org/mattneil/">mattneil</a>,
1007                                <a href="https://profiles.wordpress.org/meijioro/">meijioro</a>,
1008                                <a href="https://profiles.wordpress.org/modemlooper/">modemlooper</a>,
1009                                <a href="https://profiles.wordpress.org/DJPaul/">Paul Gibbs (DJPaul)</a>,
1010                                <a href="https://profiles.wordpress.org/r-a-y/">r-a-y</a>,
1011                                <a href="https://profiles.wordpress.org/espellcaste/">Renato Alves (espellcaste)</a>,
1012                                <a href="https://profiles.wordpress.org/slaffik/">Slava Abakumov (slaffik)</a>,
1013                                <a href="https://profiles.wordpress.org/sabernhardt/">Stephen Bernhardt (sabernhardt)</a>,
1014                                <a href="https://profiles.wordpress.org/netweb/">Stephen Edgar (netweb)</a>,
1015                                <a href="https://profiles.wordpress.org/studiocrafted/">studiocrafted</a>,
1016                                <a href="https://profiles.wordpress.org/sippis/">Timi Wahalahti (sippis)</a>,
1017                                <a href="https://profiles.wordpress.org/topher1kenobe/">Topher (topher1kenobe)</a>,
1018                                <a href="https://profiles.wordpress.org/utsav72640/">Utsav tilava (utsav72640)</a>,
1019                                <a href="https://profiles.wordpress.org/vapvarun/">Varun Dubey (vapvarun)</a>,
1020                                <a href="https://profiles.wordpress.org/venutius/">Venutius</a>,
1021                                <a href="https://profiles.wordpress.org/weddywood/">WeddyWood</a>.
1022                        </p>
1023
1024                        <h3 class="wp-people-group"><?php esc_html_e( 'With our thanks to these Open Source projects', 'buddypress' ); ?></h3>
1025                        <p class="wp-credits-list">
1026                                <a href="https://github.com/ichord/At.js">At.js</a>,
1027                                <a href="https://bbpress.org">bbPress</a>,
1028                                <a href="https://github.com/ichord/Caret.js">Caret.js</a>,
1029                                <a href="https://tedgoas.github.io/Cerberus/">Cerberus</a>,
1030                                <a href="https://ionicons.com/">Ionicons</a>,
1031                                <a href="https://github.com/carhartl/jquery-cookie">jquery.cookie</a>,
1032                                <a href="https://mattbradley.github.io/livestampjs/">Livestamp.js</a>,
1033                                <a href="https://www.mediawiki.org/wiki/MediaWiki">MediaWiki</a>,
1034                                <a href="https://momentjs.com/">Moment.js</a>,
1035                                <a href="https://wordpress.org">WordPress</a>.
1036                        </p>
1037
1038                        <h3 class="wp-people-group"><?php esc_html_e( 'Contributor Emeriti', 'buddypress' ); ?></h3>
1039                        <ul class="wp-people-group " id="wp-people-group-emeriti">
1040                                <li class="wp-person" id="wp-person-apeatling">
1041                                        <a class="web" href="https://profiles.wordpress.org/johnjamesjacoby"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/bb29d699b5cba218c313b61aa82249da?s=120">
1042                                        Andy Peatling</a>
1043                                        <span class="title"><?php esc_html_e( 'Project Founder', 'buddypress' ); ?></span>
1044                                </li>
1045                                <li class="wp-person" id="wp-person-burtadsit">
1046                                        <a class="web" href="https://profiles.wordpress.org/burtadsit"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/185e1d3e2d653af9d49a4e8e4fc379df?s=120">
1047                                        Burt Adsit</a>
1048                                </li>
1049                                <li class="wp-person" id="wp-person-dimensionmedia">
1050                                        <a class="web" href="https://profiles.wordpress.org/dimensionmedia"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/7735aada1ec39d0c1118bd92ed4551f1?s=120">
1051                                        David Bisset</a>
1052                                </li>
1053                                <li class="wp-person" id="wp-person-jeffsayre">
1054                                        <a class="web" href="https://profiles.wordpress.org/jeffsayre"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/8e009a84ff5d245c22a69c7df6ab45f7?s=120">
1055                                        Jeff Sayre</a>
1056                                </li>
1057                                <li class="wp-person" id="wp-person-karmatosed">
1058                                        <a class="web" href="https://profiles.wordpress.org/karmatosed"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/ca7d4273a689cdbf524d8332771bb1ca?s=120">
1059                                        Tammie Lister</a>
1060                                </li>
1061                                <li class="wp-person" id="wp-person-modemlooper">
1062                                        <a class="web" href="https://profiles.wordpress.org/modemlooper"><img alt="" class="gravatar" src="//www.gravatar.com/avatar/1c07be1016e845de514931477c939307?s=120">
1063                                        modemlooper</a>
1064                                </li>
1065                        </ul>
1066                </div>
1067
1068                <?php
1069        }
1070
1071        /** Emails ****************************************************************/
1072
1073        /**
1074         * Registers 'Situations' column on Emails dashboard page.
1075         *
1076         * @since 2.6.0
1077         *
1078         * @param array $columns Current column data.
1079         * @return array
1080         */
1081        public function emails_register_situation_column( $columns = array() ) {
1082                $situation = array(
1083                        'situation' => _x( 'Situations', 'Email post type', 'buddypress' )
1084                );
1085
1086                // Inject our 'Situations' column just before the last 'Date' column.
1087                return array_slice( $columns, 0, -1, true ) + $situation + array_slice( $columns, -1, null, true );
1088        }
1089
1090        /**
1091         * Output column data for our custom 'Situations' column.
1092         *
1093         * @since 2.6.0
1094         *
1095         * @param string $column  Current column name.
1096         * @param int    $post_id Current post ID.
1097         */
1098        public function emails_display_situation_column_data( $column = '', $post_id = 0 ) {
1099                if ( 'situation' !== $column ) {
1100                        return;
1101                }
1102
1103                // Grab email situations for the current post.
1104                $situations = wp_list_pluck( get_the_terms( $post_id, bp_get_email_tax_type() ), 'description' );
1105
1106                // Output each situation as a list item.
1107                echo '<ul><li>';
1108                echo implode( '</li><li>', $situations );
1109                echo '</li></ul>';
1110        }
1111
1112        /** Helpers ***************************************************************/
1113
1114        /**
1115         * Return true/false based on whether a query argument is set.
1116         *
1117         * @see bp_do_activation_redirect()
1118         *
1119         * @since 2.2.0
1120         *
1121         * @return bool
1122         */
1123        public static function is_new_install() {
1124                return (bool) isset( $_GET['is_new_install'] );
1125        }
1126
1127        /**
1128         * Return a user-friendly version-number string, for use in translations.
1129         *
1130         * @since 2.2.0
1131         *
1132         * @return string
1133         */
1134        public static function display_version() {
1135
1136                // Use static variable to prevent recalculations.
1137                static $display = '';
1138
1139                // Only calculate on first run.
1140                if ( '' === $display ) {
1141
1142                        // Get current version.
1143                        $version = bp_get_version();
1144
1145                        // Check for prerelease hyphen.
1146                        $pre     = strpos( $version, '-' );
1147
1148                        // Strip prerelease suffix.
1149                        $display = ( false !== $pre )
1150                                ? substr( $version, 0, $pre )
1151                                : $version;
1152                }
1153
1154                // Done!
1155                return $display;
1156        }
1157
1158        /**
1159         * Add Emails menu item to custom menus array.
1160         *
1161         * Several BuddyPress components have top-level menu items in the Dashboard,
1162         * which all appear together in the middle of the Dashboard menu. This function
1163         * adds the Emails screen to the array of these menu items.
1164         *
1165         * @since 2.4.0
1166         *
1167         * @param array $custom_menus The list of top-level BP menu items.
1168         * @return array $custom_menus List of top-level BP menu items, with Emails added.
1169         */
1170        public function emails_admin_menu_order( $custom_menus = array() ) {
1171                array_push( $custom_menus, 'edit.php?post_type=' . bp_get_email_post_type() );
1172
1173                if ( is_network_admin() && bp_is_network_activated() ) {
1174                        array_push(
1175                                $custom_menus,
1176                                get_admin_url( bp_get_root_blog_id(), 'edit.php?post_type=' . bp_get_email_post_type() )
1177                        );
1178                }
1179
1180                return $custom_menus;
1181        }
1182
1183        /**
1184         * Register styles commonly used by BuddyPress wp-admin screens.
1185         *
1186         * @since 2.5.0
1187         */
1188        public function admin_register_styles() {
1189                $min = bp_core_get_minified_asset_suffix();
1190                $url = $this->css_url;
1191
1192                /**
1193                 * Filters the BuddyPress Core Admin CSS file path.
1194                 *
1195                 * @since 1.6.0
1196                 *
1197                 * @param string $file File path for the admin CSS.
1198                 */
1199                $common_css = apply_filters( 'bp_core_admin_common_css', "{$url}common{$min}.css" );
1200
1201                /**
1202                 * Filters the BuddyPress admin stylesheet files to register.
1203                 *
1204                 * @since 2.5.0
1205                 *
1206                 * @param array $value Array of admin stylesheet file information to register.
1207                 */
1208                $styles = apply_filters( 'bp_core_admin_register_styles', array(
1209                        // Legacy.
1210                        'bp-admin-common-css' => array(
1211                                'file'         => $common_css,
1212                                'dependencies' => array(),
1213                        ),
1214
1215                        // 2.5
1216                        'bp-customizer-controls' => array(
1217                                'file'         => "{$url}customizer-controls{$min}.css",
1218                                'dependencies' => array(),
1219                        ),
1220
1221                        // 3.0
1222                        'bp-hello-css' => array(
1223                                'file'         => "{$url}hello{$min}.css",
1224                                'dependencies' => array( 'bp-admin-common-css', 'thickbox' ),
1225                        ),
1226                ) );
1227
1228                $version = bp_get_version();
1229
1230                foreach ( $styles as $id => $style ) {
1231                        wp_register_style( $id, $style['file'], $style['dependencies'], $version );
1232                        wp_style_add_data( $id, 'rtl', 'replace' );
1233
1234                        if ( $min ) {
1235                                wp_style_add_data( $id, 'suffix', $min );
1236                        }
1237                }
1238        }
1239
1240        /**
1241         * Register JS commonly used by BuddyPress wp-admin screens.
1242         *
1243         * @since 2.5.0
1244         */
1245        public function admin_register_scripts() {
1246                $min = bp_core_get_minified_asset_suffix();
1247                $url = $this->js_url;
1248
1249                /**
1250                 * Filters the BuddyPress admin JS files to register.
1251                 *
1252                 * @since 2.5.0
1253                 *
1254                 * @param array $value Array of admin JS file information to register.
1255                 */
1256                $scripts = apply_filters( 'bp_core_admin_register_scripts', array(
1257                        // 2.5
1258                        'bp-customizer-controls' => array(
1259                                'file'         => "{$url}customizer-controls{$min}.js",
1260                                'dependencies' => array( 'jquery' ),
1261                                'footer'       => true,
1262                        ),
1263
1264                        // 3.0
1265                        'bp-hello-js' => array(
1266                                'file'         => "{$url}hello{$min}.js",
1267                                'dependencies' => array( 'thickbox', 'bp-api-request' ),
1268                                'footer'       => true,
1269                        ),
1270                ) );
1271
1272                $version = bp_get_version();
1273
1274                foreach ( $scripts as $id => $script ) {
1275                        wp_register_script( $id, $script['file'], $script['dependencies'], $version, $script['footer'] );
1276                }
1277        }
1278}
1279endif; // End class_exists check.
Note: See TracBrowser for help on using the repository browser.