[ Index ]

PHP Cross Reference of BuddyPress

title

Body

[close]

/src/bp-core/classes/ -> class-bp-attachment-avatar.php (source)

   1  <?php
   2  /**
   3   * Core Avatars attachment class.
   4   *
   5   * @package BuddyPress
   6   * @subpackage Core
   7   * @since 2.3.0
   8   */
   9  
  10  // Exit if accessed directly.
  11  defined( 'ABSPATH' ) || exit;
  12  
  13  /**
  14   * BP Attachment Avatar class.
  15   *
  16   * Extends BP Attachment to manage the avatar uploads.
  17   *
  18   * @since 2.3.0
  19   */
  20  class BP_Attachment_Avatar extends BP_Attachment {
  21  
  22      /**
  23       * Construct Upload parameters.
  24       *
  25       * @since 2.3.0
  26       *
  27       * @see  BP_Attachment::__construct() for list of parameters
  28       */
  29  	public function __construct() {
  30          // Allowed avatar types.
  31          $allowed_types = bp_core_get_allowed_avatar_types();
  32  
  33          parent::__construct( array(
  34              'action'                => 'bp_avatar_upload',
  35              'file_input'            => 'file',
  36              'original_max_filesize' => bp_core_avatar_original_max_filesize(),
  37  
  38              // Specific errors for avatars.
  39              'upload_error_strings'  => array(
  40                  9  => sprintf( __( 'That photo is too big. Please upload one smaller than %s', 'buddypress' ), size_format( bp_core_avatar_original_max_filesize() ) ),
  41                  10 => sprintf( _n( 'Please upload only this file type: %s.', 'Please upload only these file types: %s.', count( $allowed_types ), 'buddypress' ), self::get_avatar_types( $allowed_types ) ),
  42              ),
  43          ) );
  44      }
  45  
  46      /**
  47       * Gets the available avatar types.
  48       *
  49       * @since 2.3.0
  50       *
  51       * @param array $allowed_types Array of allowed avatar types.
  52       * @return string comma separated list of allowed avatar types.
  53       */
  54  	public static function get_avatar_types( $allowed_types = array() ) {
  55          $types = array_map( 'strtoupper', $allowed_types );
  56          $comma = _x( ',', 'avatar types separator', 'buddypress' );
  57          return join( $comma . ' ', $types );
  58      }
  59  
  60      /**
  61       * Set Upload Dir data for avatars.
  62       *
  63       * @since 2.3.0
  64       */
  65  	public function set_upload_dir() {
  66          if ( bp_core_avatar_upload_path() && bp_core_avatar_url() ) {
  67              $this->upload_path = bp_core_avatar_upload_path();
  68              $this->url         = bp_core_avatar_url();
  69              $this->upload_dir  = bp_upload_dir();
  70          } else {
  71              parent::set_upload_dir();
  72          }
  73      }
  74  
  75      /**
  76       * Avatar specific rules.
  77       *
  78       * Adds an error if the avatar size or type don't match BuddyPress needs.
  79       * The error code is the index of $upload_error_strings.
  80       *
  81       * @since 2.3.0
  82       *
  83       * @param array $file the temporary file attributes (before it has been moved).
  84       * @return array the file with extra errors if needed.
  85       */
  86  	public function validate_upload( $file = array() ) {
  87          // Bail if already an error.
  88          if ( ! empty( $file['error'] ) ) {
  89              return $file;
  90          }
  91  
  92          // File size is too big.
  93          if ( ! bp_core_check_avatar_size( array( 'file' => $file ) ) ) {
  94              $file['error'] = 9;
  95  
  96          // File is of invalid type.
  97          } elseif ( ! bp_core_check_avatar_type( array( 'file' => $file ) ) ) {
  98              $file['error'] = 10;
  99          }
 100  
 101          // Return with error code attached.
 102          return $file;
 103      }
 104  
 105      /**
 106       * Maybe shrink the attachment to fit maximum allowed width.
 107       *
 108       * @since 2.3.0
 109       * @since 2.4.0 Add the $ui_available_width parameter, to inform about the Avatar UI width.
 110       *
 111       * @param string $file               The absolute path to the file.
 112       * @param int    $ui_available_width Available width for the UI.
 113       * @return false|string|WP_Image_Editor|WP_Error
 114       */
 115  	public static function shrink( $file = '', $ui_available_width = 0 ) {
 116          // Get image size.
 117          $avatar_data = parent::get_image_data( $file );
 118  
 119          // Init the edit args.
 120          $edit_args = array();
 121  
 122          // Defaults to the Avatar original max width constant.
 123          $original_max_width = bp_core_avatar_original_max_width();
 124  
 125          // The ui_available_width is defined and it's smaller than the Avatar original max width.
 126          if ( ! empty( $ui_available_width ) && $ui_available_width < $original_max_width ) {
 127              /**
 128               * In this case, to make sure the content of the image will be fully displayed
 129               * during the cropping step, let's use the Avatar UI Available width.
 130               */
 131              $original_max_width = $ui_available_width;
 132  
 133              // $original_max_width has to be larger than the avatar's full width
 134              if ( $original_max_width < bp_core_avatar_full_width() ) {
 135                  $original_max_width = bp_core_avatar_full_width();
 136              }
 137          }
 138  
 139          // Do we need to resize the image?
 140          if ( isset( $avatar_data['width'] ) && $avatar_data['width'] > $original_max_width ) {
 141              $edit_args = array(
 142                  'max_w' => $original_max_width,
 143                  'max_h' => $original_max_width,
 144              );
 145          }
 146  
 147          // Do we need to rotate the image?
 148          $angles = array(
 149              3 => 180,
 150              6 => -90,
 151              8 =>  90,
 152          );
 153  
 154          if ( isset( $avatar_data['meta']['orientation'] ) && isset( $angles[ $avatar_data['meta']['orientation'] ] ) ) {
 155              $edit_args['rotate'] = $angles[ $avatar_data['meta']['orientation'] ];
 156          }
 157  
 158          // No need to edit the avatar, original file will be used.
 159          if ( empty( $edit_args ) ) {
 160              return false;
 161  
 162          // Add the file to the edit arguments.
 163          } else {
 164              $edit_args['file'] = $file;
 165          }
 166  
 167          return parent::edit_image( 'avatar', $edit_args );
 168      }
 169  
 170      /**
 171       * Check if the image dimensions are smaller than full avatar dimensions.
 172       *
 173       * @since 2.3.0
 174       *
 175       *
 176       * @param string $file the absolute path to the file.
 177       * @return bool
 178       */
 179  	public static function is_too_small( $file = '' ) {
 180          $uploaded_image = @getimagesize( $file );
 181          $full_width     = bp_core_avatar_full_width();
 182          $full_height    = bp_core_avatar_full_height();
 183  
 184          if ( isset( $uploaded_image[0] ) && $uploaded_image[0] < $full_width || $uploaded_image[1] < $full_height ) {
 185              return true;
 186          }
 187  
 188          return false;
 189      }
 190  
 191      /**
 192       * Crop the avatar.
 193       *
 194       * @since 2.3.0
 195       *
 196       * @see  BP_Attachment::crop for the list of parameters
 197       *
 198       * @param array $args Array of arguments for the cropping.
 199       * @return array The cropped avatars (full and thumb).
 200       */
 201  	public function crop( $args = array() ) {
 202          // Bail if the original file is missing.
 203          if ( empty( $args['original_file'] ) ) {
 204              return false;
 205          }
 206  
 207          if ( ! bp_attachments_current_user_can( 'edit_avatar', $args ) ) {
 208              return false;
 209          }
 210  
 211          if ( 'user' === $args['object'] ) {
 212              $avatar_dir = 'avatars';
 213          } else {
 214              $avatar_dir = sanitize_key( $args['object'] ) . '-avatars';
 215          }
 216  
 217          $args['item_id'] = (int) $args['item_id'];
 218  
 219          /**
 220           * Original file is a relative path to the image
 221           * eg: /avatars/1/avatar.jpg
 222           */
 223          $relative_path = sprintf( '/%s/%s/%s', $avatar_dir, $args['item_id'], basename( $args['original_file'] ) );
 224          $absolute_path = $this->upload_path . $relative_path;
 225  
 226          // Bail if the avatar is not available.
 227          if ( ! file_exists( $absolute_path ) )  {
 228              return false;
 229          }
 230  
 231          if ( empty( $args['item_id'] ) ) {
 232  
 233              /** This filter is documented in bp-core/bp-core-avatars.php */
 234              $avatar_folder_dir = apply_filters( 'bp_core_avatar_folder_dir', dirname( $absolute_path ), $args['item_id'], $args['object'], $args['avatar_dir'] );
 235          } else {
 236  
 237              /** This filter is documented in bp-core/bp-core-avatars.php */
 238              $avatar_folder_dir = apply_filters( 'bp_core_avatar_folder_dir', $this->upload_path . '/' . $args['avatar_dir'] . '/' . $args['item_id'], $args['item_id'], $args['object'], $args['avatar_dir'] );
 239          }
 240  
 241          // Bail if the avatar folder is missing for this item_id.
 242          if ( ! file_exists( $avatar_folder_dir ) ) {
 243              return false;
 244          }
 245  
 246          // Delete the existing avatar files for the object.
 247          $existing_avatar = bp_core_fetch_avatar( array(
 248              'object'  => $args['object'],
 249              'item_id' => $args['item_id'],
 250              'html' => false,
 251          ) );
 252  
 253          /**
 254           * Check that the new avatar doesn't have the same name as the
 255           * old one before deleting
 256           */
 257          if ( ! empty( $existing_avatar ) && $existing_avatar !== $this->url . $relative_path ) {
 258              bp_core_delete_existing_avatar( array( 'object' => $args['object'], 'item_id' => $args['item_id'], 'avatar_path' => $avatar_folder_dir ) );
 259          }
 260  
 261          // Make sure we at least have minimal data for cropping.
 262          if ( empty( $args['crop_w'] ) ) {
 263              $args['crop_w'] = bp_core_avatar_full_width();
 264          }
 265  
 266          if ( empty( $args['crop_h'] ) ) {
 267              $args['crop_h'] = bp_core_avatar_full_height();
 268          }
 269  
 270          // Get the file extension.
 271          $data = @getimagesize( $absolute_path );
 272          $ext  = $data['mime'] == 'image/png' ? 'png' : 'jpg';
 273  
 274          $args['original_file'] = $absolute_path;
 275          $args['src_abs']       = false;
 276          $avatar_types = array( 'full' => '', 'thumb' => '' );
 277  
 278          foreach ( $avatar_types as $key_type => $type ) {
 279              if ( 'thumb' === $key_type ) {
 280                  $args['dst_w'] = bp_core_avatar_thumb_width();
 281                  $args['dst_h'] = bp_core_avatar_thumb_height();
 282              } else {
 283                  $args['dst_w'] = bp_core_avatar_full_width();
 284                  $args['dst_h'] = bp_core_avatar_full_height();
 285              }
 286  
 287              $filename         = wp_unique_filename( $avatar_folder_dir, uniqid() . "-bp{$key_type}.{$ext}" );
 288              $args['dst_file'] = $avatar_folder_dir . '/' . $filename;
 289  
 290              $avatar_types[ $key_type ] = parent::crop( $args );
 291          }
 292  
 293          // Remove the original.
 294          @unlink( $absolute_path );
 295  
 296          // Return the full and thumb cropped avatars.
 297          return $avatar_types;
 298      }
 299  
 300      /**
 301       * Get the user id to set its avatar.
 302       *
 303       * @since 2.3.0
 304       *
 305       * @return integer The user ID.
 306       */
 307  	private function get_user_id() {
 308          $bp = buddypress();
 309          $user_id = 0;
 310  
 311          if ( bp_is_user() ) {
 312              $user_id = bp_displayed_user_id();
 313          }
 314  
 315          if ( ! empty( $bp->members->admin->user_id ) ) {
 316              $user_id = $bp->members->admin->user_id;
 317          }
 318  
 319          return $user_id;
 320      }
 321  
 322      /**
 323       * Get the group id to set its avatar.
 324       *
 325       * @since 2.3.0
 326       *
 327       * @return integer The group ID.
 328       */
 329  	private function get_group_id() {
 330          $group_id = 0;
 331  
 332          if ( bp_is_group() ) {
 333              $group_id = bp_get_current_group_id();
 334          }
 335  
 336          return $group_id;
 337      }
 338  
 339      /**
 340       * Build script datas for the Uploader UI.
 341       *
 342       * @since 2.3.0
 343       *
 344       * @return array The javascript localization data.
 345       */
 346  	public function script_data() {
 347          // Get default script data.
 348          $script_data = parent::script_data();
 349  
 350          // Defaults to Avatar Backbone script.
 351          $js_scripts = array( 'bp-avatar' );
 352  
 353          // Default object.
 354          $object = '';
 355  
 356          // Get the possible item ids.
 357          $user_id  = $this->get_user_id();
 358          $group_id = $this->get_group_id();
 359  
 360          if ( ! empty( $user_id ) ) {
 361              // Should we load the the Webcam Avatar javascript file.
 362              if ( bp_avatar_use_webcam() ) {
 363                  $js_scripts = array( 'bp-webcam' );
 364              }
 365  
 366              $script_data['bp_params'] = array(
 367                  'object'     => 'user',
 368                  'item_id'    => $user_id,
 369                  'has_avatar' => bp_get_user_has_avatar( $user_id ),
 370                  'nonces'  => array(
 371                      'set'    => wp_create_nonce( 'bp_avatar_cropstore' ),
 372                      'remove' => wp_create_nonce( 'bp_delete_avatar_link' ),
 373                  ),
 374              );
 375  
 376              // Set feedback messages.
 377              $script_data['feedback_messages'] = array(
 378                  1 => __( 'There was a problem cropping your profile photo.', 'buddypress' ),
 379                  2 => __( 'Your new profile photo was uploaded successfully.', 'buddypress' ),
 380                  3 => __( 'There was a problem deleting your profile photo. Please try again.', 'buddypress' ),
 381                  4 => __( 'Your profile photo was deleted successfully!', 'buddypress' ),
 382              );
 383          } elseif ( ! empty( $group_id ) ) {
 384              $script_data['bp_params'] = array(
 385                  'object'     => 'group',
 386                  'item_id'    => $group_id,
 387                  'has_avatar' => bp_get_group_has_avatar( $group_id ),
 388                  'nonces'     => array(
 389                      'set'    => wp_create_nonce( 'bp_avatar_cropstore' ),
 390                      'remove' => wp_create_nonce( 'bp_group_avatar_delete' ),
 391                  ),
 392              );
 393  
 394              // Set feedback messages.
 395              $script_data['feedback_messages'] = array(
 396                  1 => __( 'There was a problem cropping the group profile photo.', 'buddypress' ),
 397                  2 => __( 'The group profile photo was uploaded successfully.', 'buddypress' ),
 398                  3 => __( 'There was a problem deleting the group profile photo. Please try again.', 'buddypress' ),
 399                  4 => __( 'The group profile photo was deleted successfully!', 'buddypress' ),
 400              );
 401          } else {
 402  
 403              /**
 404               * Use this filter to include specific BuddyPress params for your object.
 405               * e.g. Blavatar.
 406               *
 407               * @since 2.3.0
 408               *
 409               * @param array $value The avatar specific BuddyPress parameters.
 410               */
 411              $script_data['bp_params'] = apply_filters( 'bp_attachment_avatar_params', array() );
 412          }
 413  
 414          // Include the specific css.
 415          $script_data['extra_css'] = array( 'bp-avatar' );
 416  
 417          // Include the specific css.
 418          $script_data['extra_js']  = $js_scripts;
 419  
 420          // Set the object to contextualize the filter.
 421          if ( isset( $script_data['bp_params']['object'] ) ) {
 422              $object = $script_data['bp_params']['object'];
 423          }
 424  
 425          /**
 426           * Use this filter to override/extend the avatar script data.
 427           *
 428           * @since 2.3.0
 429           *
 430           * @param array  $script_data The avatar script data.
 431           * @param string $object      The object the avatar belongs to (eg: user or group).
 432           */
 433          return apply_filters( 'bp_attachment_avatar_script_data', $script_data, $object );
 434      }
 435  }


Generated: Thu Sep 19 01:01:39 2019 Cross-referenced by PHPXref 0.7.1