Skip to:
Content

BuddyPress.org

Ticket #4634: bp-core-avatars.php

File bp-core-avatars.php, 29.4 KB (added by NolanD626, 12 years ago)

bp-core-avatars.php

Line 
1<?php
2
3/**
4 * BuddyPress Avatars
5 */
6
7// Exit if accessed directly
8if ( !defined( 'ABSPATH' ) ) exit;
9
10/***
11 * Set up the constants we need for avatar support
12 */
13function bp_core_set_avatar_constants() {
14        global $bp;
15
16        if ( !defined( 'BP_AVATAR_THUMB_WIDTH' ) )
17                define( 'BP_AVATAR_THUMB_WIDTH', 50 );
18
19        if ( !defined( 'BP_AVATAR_THUMB_HEIGHT' ) )
20                define( 'BP_AVATAR_THUMB_HEIGHT', 50 );
21
22        if ( !defined( 'BP_AVATAR_FULL_WIDTH' ) )
23                define( 'BP_AVATAR_FULL_WIDTH', 150 );
24
25        if ( !defined( 'BP_AVATAR_FULL_HEIGHT' ) )
26                define( 'BP_AVATAR_FULL_HEIGHT', 150 );
27
28        if ( !defined( 'BP_AVATAR_ORIGINAL_MAX_WIDTH' ) )
29                define( 'BP_AVATAR_ORIGINAL_MAX_WIDTH', 450 );
30
31        if ( !defined( 'BP_AVATAR_ORIGINAL_MAX_FILESIZE' ) ) {
32                if ( !isset( $bp->site_options['fileupload_maxk'] ) ) {
33                        define( 'BP_AVATAR_ORIGINAL_MAX_FILESIZE', 5120000 ); // 5mb
34                } else {
35                        define( 'BP_AVATAR_ORIGINAL_MAX_FILESIZE', $bp->site_options['fileupload_maxk'] * 1024 );
36                }
37        }
38
39        if ( !defined( 'BP_AVATAR_DEFAULT' ) )
40                define( 'BP_AVATAR_DEFAULT', BP_PLUGIN_URL . 'bp-core/images/mystery-man.jpg' );
41
42        if ( !defined( 'BP_AVATAR_DEFAULT_THUMB' ) )
43                define( 'BP_AVATAR_DEFAULT_THUMB', BP_PLUGIN_URL . 'bp-core/images/mystery-man-50.jpg' );
44}
45add_action( 'bp_init', 'bp_core_set_avatar_constants', 3 );
46
47function bp_core_set_avatar_globals() {
48        global $bp;
49
50        $bp->avatar        = new stdClass;
51        $bp->avatar->thumb = new stdClass;
52        $bp->avatar->full  = new stdClass;
53
54        // Dimensions
55        $bp->avatar->thumb->width          = BP_AVATAR_THUMB_WIDTH;
56        $bp->avatar->thumb->height         = BP_AVATAR_THUMB_HEIGHT;
57        $bp->avatar->full->width           = BP_AVATAR_FULL_WIDTH;
58        $bp->avatar->full->height          = BP_AVATAR_FULL_HEIGHT;
59
60        // Upload maximums
61        $bp->avatar->original_max_width    = BP_AVATAR_ORIGINAL_MAX_WIDTH;
62        $bp->avatar->original_max_filesize = BP_AVATAR_ORIGINAL_MAX_FILESIZE;
63
64        // Defaults
65        $bp->avatar->thumb->default = BP_AVATAR_DEFAULT_THUMB;
66        $bp->avatar->full->default      = BP_AVATAR_DEFAULT;
67
68        // These have to be set on page load in order to avoid infinite filter loops at runtime
69        $bp->avatar->upload_path = bp_core_avatar_upload_path();
70        $bp->avatar->url                 = bp_core_avatar_url();
71
72        // Backpat for pre-1.5
73        if ( ! defined( 'BP_AVATAR_UPLOAD_PATH' ) )
74                define( 'BP_AVATAR_UPLOAD_PATH', $bp->avatar->upload_path );
75
76        // Backpat for pre-1.5
77        if ( ! defined( 'BP_AVATAR_URL' ) )
78                define( 'BP_AVATAR_URL', $bp->avatar->url );
79
80        do_action( 'bp_core_set_avatar_globals' );
81}
82add_action( 'bp_setup_globals', 'bp_core_set_avatar_globals' );
83
84/**
85 * bp_core_fetch_avatar()
86 *
87 * Fetches an avatar from a BuddyPress object. Supports user/group/blog as
88 * default, but can be extended to include your own custom components too.
89 *
90 * @global BuddyPress $bp The one true BuddyPress instance
91 * @global $current_blog WordPress global containing information and settings for the current blog being viewed.
92 * @param array $args Determine the output of this function
93 * @return string Formatted HTML <img> element, or raw avatar URL based on $html arg
94 */
95function bp_core_fetch_avatar( $args = '' ) {
96        global $bp, $current_blog;
97
98        // Set a few default variables
99        $def_object = 'user';
100        $def_type   = 'thumb';
101        $def_class  = 'avatar';
102
103        // Set the default variables array
104        $defaults = array(
105                'item_id'    => false,
106                'object'     => $def_object, // user/group/blog/custom type (if you use filters)
107                'type'       => $def_type,   // thumb or full
108                'avatar_dir' => false,       // Specify a custom avatar directory for your object
109                'width'      => false,       // Custom width (int)
110                'height'     => false,       // Custom height (int)
111                'class'      => $def_class,  // Custom <img> class (string)
112                'css_id'     => false,       // Custom <img> ID (string)
113                'alt'        => '',          // Custom <img> alt (string)
114                'email'      => false,       // Pass the user email (for gravatar) to prevent querying the DB for it
115                'no_grav'    => false,       // If there is no avatar found, return false instead of a grav?
116                'html'       => true,        // Wrap the return img URL in <img />
117                'title'      => ''           // Custom <img> title (string)
118        );
119
120        // Compare defaults to passed and extract
121        $params = wp_parse_args( $args, $defaults );
122        extract( $params, EXTR_SKIP );
123
124        /** Set item_id ***********************************************************/
125
126        if ( empty( $item_id ) ) {
127
128                switch ( $object ) {
129
130                        case 'blog'  :
131                                $item_id = $current_blog->id;
132                                break;
133
134                        case 'group' :
135                                if ( bp_is_active( 'groups' ) ) {
136                                        $item_id = $bp->groups->current_group->id;
137                                } else {
138                                        $item_id = false;
139                                }
140
141                                break;
142
143                        case 'user'  :
144                        default      :
145                                $item_id = bp_displayed_user_id();
146                                break;
147                }
148
149                $item_id = apply_filters( 'bp_core_avatar_item_id', $item_id, $object, $params );
150
151                if ( empty( $item_id ) ) {
152                        return false;
153                }
154        }
155
156        $class = apply_filters( 'bp_core_avatar_class', $class, $item_id, $object, $params );
157
158        /** Set avatar_dir ********************************************************/
159
160        if ( empty( $avatar_dir ) ) {
161
162                switch ( $object ) {
163
164                        case 'blog'  :
165                                $avatar_dir = 'blog-avatars';
166                                break;
167
168                        case 'group' :
169                                if ( bp_is_active( 'groups' ) ) {
170                                        $avatar_dir = 'group-avatars';
171                                } else {
172                                        $avatar_dir = false;
173                                }
174
175                                break;
176
177                        case 'user'  :
178                        default      :
179                                $avatar_dir = 'avatars';
180                                break;
181                }
182
183                $avatar_dir = apply_filters( 'bp_core_avatar_dir', $avatar_dir, $object, $params );
184
185                if ( empty( $avatar_dir ) ) {
186                        return false;
187                }
188        }
189
190        /** <img> alt *************************************************************/
191
192        if ( false !== strpos( $alt, '%s' ) || false !== strpos( $alt, '%1$s' ) ) {
193
194                // Get item name for alt/title tags
195                $item_name = '';
196
197                switch ( $object ) {
198
199                        case 'blog'  :
200                                $item_name = get_blog_option( $item_id, 'blogname' );
201                                break;
202
203                        case 'group' :
204                                $item_name = bp_get_group_name( groups_get_group( array( 'group_id' => $item_id ) ) );
205                                break;
206
207                        case 'user'  :
208                        default :
209                                $item_name = bp_core_get_user_displayname( $item_id );
210                                break;
211                }
212
213                $item_name = apply_filters( 'bp_core_avatar_alt', $item_name, $item_id, $object, $params );
214                $alt       = sprintf( $alt, $item_name );
215        }
216
217        /** Sanity Checks *********************************************************/
218
219        // Get a fallback for the 'alt' parameter
220        if ( empty( $alt ) )
221                $alt = __( 'Avatar Image', 'buddypress' );
222
223        // Set title tag, if it's been provided
224        if ( !empty( $title ) )
225                $title = " title='" . esc_attr( apply_filters( 'bp_core_avatar_title', $title, $item_id, $object, $params ) ) . "'";
226
227        // Set CSS ID if passed
228        if ( !empty( $css_id ) )
229                $css_id = ' id="' . $css_id . '"';
230
231        // Set image width
232        if ( false !== $width )
233                $html_width = ' width="' . $width . '"';
234        else
235                $html_width = ( 'thumb' == $type ) ? ' width="' . bp_core_avatar_thumb_width() . '"' : ' width="' . bp_core_avatar_full_width() . '"';
236
237        // Set image height
238        if ( false !== $height )
239                $html_height = ' height="' . $height . '"';
240        else
241                $html_height = ( 'thumb' == $type ) ? ' height="' . bp_core_avatar_thumb_height() . '"' : ' height="' . bp_core_avatar_full_height() . '"';
242
243        // Set img URL and DIR based on prepopulated constants
244        $avatar_loc        = new stdClass();
245        $avatar_loc->path  = trailingslashit( bp_core_avatar_upload_path() );
246        $avatar_loc->url   = trailingslashit( bp_core_avatar_url() );
247
248        $avatar_loc->dir   = trailingslashit( $avatar_dir );
249        $avatar_folder_url = apply_filters( 'bp_core_avatar_folder_url', ( $avatar_loc->url  . $avatar_loc->dir . $item_id ), $item_id, $object, $avatar_dir );
250        $avatar_folder_dir = apply_filters( 'bp_core_avatar_folder_dir', ( $avatar_loc->path . $avatar_loc->dir . $item_id ), $item_id, $object, $avatar_dir );
251
252        // Add an identifying class
253        $class .= ' ' . $object . '-' . $item_id . '-avatar';
254
255        /****
256         * Look for uploaded avatar first. Use it if it exists.
257         * Set the file names to search for, to select the full size
258         * or thumbnail image.
259         */
260        $avatar_size              = ( 'full' == $type ) ? '-bpfull' : '-bpthumb';
261        $legacy_user_avatar_name  = ( 'full' == $type ) ? '-avatar2' : '-avatar1';
262        $legacy_group_avatar_name = ( 'full' == $type ) ? '-groupavatar-full' : '-groupavatar-thumb';
263
264        // Check for directory
265        if ( file_exists( $avatar_folder_dir ) ) {
266
267                // Open directory
268                if ( $av_dir = opendir( $avatar_folder_dir ) ) {
269
270                        // Stash files in an array once to check for one that matches
271                        $avatar_files = array();
272                        while ( false !== ( $avatar_file = readdir( $av_dir ) ) ) {
273                                // Only add files to the array (skip directories)
274                                if ( 2 < strlen( $avatar_file ) ) {
275                                        $avatar_files[] = $avatar_file;
276                                }
277                        }
278
279                        // Check for array
280                        if ( 0 < count( $avatar_files ) ) {
281
282                                // Check for current avatar
283                                foreach( $avatar_files as $key => $value ) {
284                                        if ( strpos ( $value, $avatar_size )!== false ) {
285                                                $avatar_url = $avatar_folder_url . '/' . $avatar_files[$key];
286                                        }
287                                }
288
289                                // Legacy avatar check
290                                if ( !isset( $avatar_url ) ) {
291                                        foreach( $avatar_files as $key => $value ) {
292                                                if ( strpos ( $value, $legacy_user_avatar_name )!== false ) {
293                                                        $avatar_url = $avatar_folder_url . '/' . $avatar_files[$key];
294                                                }
295                                        }
296
297                                        // Legacy group avatar check
298                                        if ( !isset( $avatar_url ) ) {
299                                                foreach( $avatar_files as $key => $value ) {
300                                                        if ( strpos ( $value, $legacy_group_avatar_name )!== false ) {
301                                                                $avatar_url = $avatar_folder_url . '/' . $avatar_files[$key];
302                                                        }
303                                                }
304                                        }
305                                }
306                        }
307                }
308
309                // Close the avatar directory
310                closedir( $av_dir );
311
312                // If we found a locally uploaded avatar
313                if ( isset( $avatar_url ) ) {
314
315                        // Return it wrapped in an <img> element
316                        if ( true === $html ) {
317                                return apply_filters( 'bp_core_fetch_avatar', '<img src="' . $avatar_url . '" alt="' . esc_attr( $alt ) . '" class="' . esc_attr( $class ) . '"' . $css_id . $html_width . $html_height . $title . ' />', $params, $item_id, $avatar_dir, $css_id, $html_width, $html_height, $avatar_folder_url, $avatar_folder_dir );
318
319                        // ...or only the URL
320                        } else {
321                                return apply_filters( 'bp_core_fetch_avatar_url', $avatar_url );
322                        }
323                }
324        }
325
326        // If no avatars could be found, try to display a gravatar
327
328        // Skips gravatar check if $no_grav is passed
329        if ( ! apply_filters( 'bp_core_fetch_avatar_no_grav', $no_grav ) ) {
330
331                // Set gravatar size
332                if ( false !== $width ) {
333                        $grav_size = $width;
334                } else if ( 'full' == $type ) {
335                        $grav_size = bp_core_avatar_full_width();
336                } else if ( 'thumb' == $type ) {
337                        $grav_size = bp_core_avatar_thumb_width();
338                }
339
340                // Set gravatar type
341                if ( empty( $bp->grav_default->{$object} ) ) {
342                        $default_grav = 'wavatar';
343                } else if ( 'mystery' == $bp->grav_default->{$object} ) {
344                        $default_grav = apply_filters( 'bp_core_mysteryman_src', bp_core_avatar_default(), $grav_size );
345                } else {
346                        $default_grav = $bp->grav_default->{$object};
347                }
348
349                // Set gravatar object
350                if ( empty( $email ) ) {
351                        if ( 'user' == $object ) {
352                                $email = bp_core_get_user_email( $item_id );
353                        } else if ( 'group' == $object || 'blog' == $object ) {
354                                $email = "{$item_id}-{$object}@{bp_get_root_domain()}";
355                        }
356                }
357
358                // Set host based on if using ssl
359                $host = 'http://www.gravatar.com/avatar/';
360                if ( is_ssl() ) {
361                        $host = 'https://secure.gravatar.com/avatar/';
362                }
363
364                // Filter gravatar vars
365                $email    = apply_filters( 'bp_core_gravatar_email', $email, $item_id, $object );
366                $gravatar = apply_filters( 'bp_gravatar_url', $host ) . md5( strtolower( $email ) ) . '?d=' . $default_grav . '&amp;s=' . $grav_size;
367
368                // Gravatar rating; http://bit.ly/89QxZA
369                $rating = get_option( 'avatar_rating' );
370                if ( ! empty( $rating ) )
371                        $gravatar .= "&amp;r={$rating}";
372
373        // No avatar was found, and we've been told not to use a gravatar.
374        } else {
375                $gravatar = apply_filters( "bp_core_default_avatar_$object", BP_PLUGIN_URL . 'bp-core/images/mystery-man.jpg', $params );
376        }
377
378        if ( true === $html )
379                return apply_filters( 'bp_core_fetch_avatar', '<img src="' . $gravatar . '" alt="' . esc_attr( $alt ) . '" class="' . esc_attr( $class ) . '"' . $css_id . $html_width . $html_height . $title . ' />', $params, $item_id, $avatar_dir, $css_id, $html_width, $html_height, $avatar_folder_url, $avatar_folder_dir );
380        else
381                return apply_filters( 'bp_core_fetch_avatar_url', $gravatar );
382}
383
384/**
385 * Delete an existing avatar
386 *
387 * Accepted values for $args are:
388 *  item_id - item id which relates to the object type.
389 *  object - the objetc type user, group, blog, etc.
390 *  avatar_dir - The directory where the avatars to be uploaded.
391 *
392 * @global object $bp BuddyPress global settings
393 * @param mixed $args
394 * @return bool Success/failure
395 */
396function bp_core_delete_existing_avatar( $args = '' ) {
397        global $bp;
398
399        $defaults = array(
400                'item_id'    => false,
401                'object'     => 'user', // user OR group OR blog OR custom type (if you use filters)
402                'avatar_dir' => false
403        );
404
405        $args = wp_parse_args( $args, $defaults );
406        extract( $args, EXTR_SKIP );
407
408        if ( empty( $item_id ) ) {
409                if ( 'user' == $object )
410                        $item_id = bp_displayed_user_id();
411                else if ( 'group' == $object )
412                        $item_id = $bp->groups->current_group->id;
413                else if ( 'blog' == $object )
414                        $item_id = $current_blog->id;
415
416                $item_id = apply_filters( 'bp_core_avatar_item_id', $item_id, $object );
417
418                if ( !$item_id ) return false;
419        }
420
421        if ( empty( $avatar_dir ) ) {
422                if ( 'user' == $object )
423                        $avatar_dir = 'avatars';
424                else if ( 'group' == $object )
425                        $avatar_dir = 'group-avatars';
426                else if ( 'blog' == $object )
427                        $avatar_dir = 'blog-avatars';
428
429                $avatar_dir = apply_filters( 'bp_core_avatar_dir', $avatar_dir, $object );
430
431                if ( !$avatar_dir ) return false;
432        }
433
434        $avatar_folder_dir = apply_filters( 'bp_core_avatar_folder_dir', bp_core_avatar_upload_path() . '/' . $avatar_dir . '/' . $item_id, $item_id, $object, $avatar_dir );
435
436        if ( !file_exists( $avatar_folder_dir ) )
437                return false;
438
439        if ( $av_dir = opendir( $avatar_folder_dir ) ) {
440                while ( false !== ( $avatar_file = readdir($av_dir) ) ) {
441                        if ( ( preg_match( "/-bpfull/", $avatar_file ) || preg_match( "/-bpthumb/", $avatar_file ) ) && '.' != $avatar_file && '..' != $avatar_file )
442                                @unlink( $avatar_folder_dir . '/' . $avatar_file );
443                }
444        }
445        closedir($av_dir);
446
447        @rmdir( $avatar_folder_dir );
448
449        do_action( 'bp_core_delete_existing_avatar', $args );
450
451        return true;
452}
453
454/**
455 * Handles avatar uploading.
456 *
457 * The functions starts off by checking that the file has been uploaded properly using bp_core_check_avatar_upload().
458 * It then checks that the file size is within limits, and that it has an accepted file extension (jpg, gif, png).
459 * If everything checks out, crop the image and move it to its real location.
460 *
461 * @global object $bp BuddyPress global settings
462 * @param array $file The appropriate entry the from $_FILES superglobal.
463 * @param string $upload_dir_filter A filter to be applied to upload_dir
464 * @return bool Success/failure
465 * @see bp_core_check_avatar_upload()
466 * @see bp_core_check_avatar_type()
467 */
468function bp_core_avatar_handle_upload( $file, $upload_dir_filter ) {
469        global $bp;
470
471        /***
472         * You may want to hook into this filter if you want to override this function.
473         * Make sure you return false.
474         */
475        if ( !apply_filters( 'bp_core_pre_avatar_handle_upload', true, $file, $upload_dir_filter ) )
476                return true;
477
478        require_once( ABSPATH . '/wp-admin/includes/image.php' );
479        require_once( ABSPATH . '/wp-admin/includes/file.php' );
480
481        $uploadErrors = array(
482                0 => __("There is no error, the file uploaded with success", 'buddypress'),
483                1 => __("Your image was bigger than the maximum allowed file size of: ", 'buddypress') . size_format( bp_core_avatar_original_max_filesize() ),
484                2 => __("Your image was bigger than the maximum allowed file size of: ", 'buddypress') . size_format( bp_core_avatar_original_max_filesize() ),
485                3 => __("The uploaded file was only partially uploaded", 'buddypress'),
486                4 => __("No file was uploaded", 'buddypress'),
487                6 => __("Missing a temporary folder", 'buddypress')
488        );
489
490        if ( !bp_core_check_avatar_upload( $file ) ) {
491                bp_core_add_message( sprintf( __( 'Your upload failed, please try again. Error was: %s', 'buddypress' ), $uploadErrors[$file['file']['error']] ), 'error' );
492                return false;
493        }
494
495        if ( !bp_core_check_avatar_size( $file ) ) {
496                bp_core_add_message( sprintf( __( 'The file you uploaded is too big. Please upload a file under %s', 'buddypress'), size_format( bp_core_avatar_original_max_filesize() ) ), 'error' );
497                return false;
498        }
499
500        if ( !bp_core_check_avatar_type( $file ) ) {
501                bp_core_add_message( __( 'Please upload only JPG, GIF or PNG photos.', 'buddypress' ), 'error' );
502                return false;
503        }
504
505        // Filter the upload location
506        add_filter( 'upload_dir', $upload_dir_filter, 10, 0 );
507
508        $bp->avatar_admin->original = wp_handle_upload( $file['file'], array( 'action'=> 'bp_avatar_upload' ) );
509
510        // Move the file to the correct upload location.
511        if ( !empty( $bp->avatar_admin->original['error'] ) ) {
512                bp_core_add_message( sprintf( __( 'Upload Failed! Error was: %s', 'buddypress' ), $bp->avatar_admin->original['error'] ), 'error' );
513                return false;
514        }
515
516        // Get image size
517        $size = @getimagesize( $bp->avatar_admin->original['file'] );
518
519        // Check image size and shrink if too large
520        if ( $size[0] > bp_core_avatar_original_max_width() ) {
521                $thumb = image_resize( $bp->avatar_admin->original['file'], bp_core_avatar_original_max_width(), null );
522
523                // Check for thumbnail creation errors
524                if ( is_wp_error( $thumb ) ) {
525                        bp_core_add_message( sprintf( __( 'Upload Failed! Error was: %s', 'buddypress' ), $thumb->get_error_message() ), 'error' );
526                        return false;
527                }
528
529                // Thumbnail is good so proceed
530                $bp->avatar_admin->resized = $thumb;
531        }
532
533        // We only want to handle one image after resize.
534        if ( empty( $bp->avatar_admin->resized ) )
535                $bp->avatar_admin->image->dir = str_replace( bp_core_avatar_upload_path(), '', $bp->avatar_admin->original['file'] );
536        else {
537                $bp->avatar_admin->image->dir = str_replace( bp_core_avatar_upload_path(), '', $bp->avatar_admin->resized );
538                @unlink( $bp->avatar_admin->original['file'] );
539        }
540
541        // Check for WP_Error on what should be an image
542        if ( is_wp_error( $bp->avatar_admin->image->dir ) ) {
543                bp_core_add_message( sprintf( __( 'Upload failed! Error was: %s', 'buddypress' ), $bp->avatar_admin->image->dir->get_error_message() ), 'error' );
544                return false;
545        }
546
547        // Set the url value for the image
548        $bp->avatar_admin->image->url = bp_core_avatar_url() . $bp->avatar_admin->image->dir;
549
550        return true;
551}
552
553/**
554 * Crop an uploaded avatar
555 *
556 * $args has the following parameters:
557 *  object - What component the avatar is for, e.g. "user"
558 *  avatar_dir  The absolute path to the avatar
559 *  item_id - Item ID
560 *  original_file - The absolute path to the original avatar file
561 *  crop_w - Crop width
562 *  crop_h - Crop height
563 *  crop_x - The horizontal starting point of the crop
564 *  crop_y - The vertical starting point of the crop
565 *
566 * @param mixed $args
567 * @return bool Success/failure
568 */
569function bp_core_avatar_handle_crop( $args = '' ) {
570
571        $defaults = array(
572                'object'        => 'user',
573                'avatar_dir'    => 'avatars',
574                'item_id'       => false,
575                'original_file' => false,
576                'crop_w'        => bp_core_avatar_full_width(),
577                'crop_h'        => bp_core_avatar_full_height(),
578                'crop_x'        => 0,
579                'crop_y'        => 0
580        );
581
582        $r = wp_parse_args( $args, $defaults );
583
584        /***
585         * You may want to hook into this filter if you want to override this function.
586         * Make sure you return false.
587         */
588        if ( !apply_filters( 'bp_core_pre_avatar_handle_crop', true, $r ) )
589                return true;
590
591        extract( $r, EXTR_SKIP );
592
593        if ( !$original_file )
594                return false;
595
596        $original_file = bp_core_avatar_upload_path() . $original_file;
597
598        if ( !file_exists( $original_file ) )
599                return false;
600
601        if ( !$item_id )
602                $avatar_folder_dir = apply_filters( 'bp_core_avatar_folder_dir', dirname( $original_file ), $item_id, $object, $avatar_dir );
603        else
604                $avatar_folder_dir = apply_filters( 'bp_core_avatar_folder_dir', bp_core_avatar_upload_path() . '/' . $avatar_dir . '/' . $item_id, $item_id, $object, $avatar_dir );
605
606        if ( !file_exists( $avatar_folder_dir ) )
607                return false;
608
609        require_once( ABSPATH . '/wp-admin/includes/image.php' );
610        require_once( ABSPATH . '/wp-admin/includes/file.php' );
611
612        // Delete the existing avatar files for the object
613        bp_core_delete_existing_avatar( array( 'object' => $object, 'avatar_path' => $avatar_folder_dir ) );
614
615        // Make sure we at least have a width and height for cropping
616        if ( !(int) $crop_w )
617                $crop_w = bp_core_avatar_full_width();
618
619        if ( !(int) $crop_h )
620                $crop_h = bp_core_avatar_full_height();
621
622        // Set the full and thumb filenames
623        $full_filename  = wp_hash( $original_file . time() ) . '-bpfull.jpg';
624        $thumb_filename = wp_hash( $original_file . time() ) . '-bpthumb.jpg';
625
626        // Crop the image
627        $full_cropped  = wp_crop_image( $original_file, (int) $crop_x, (int) $crop_y, (int) $crop_w, (int) $crop_h, bp_core_avatar_full_width(), bp_core_avatar_full_height(), false, $avatar_folder_dir . '/' . $full_filename );
628        $thumb_cropped = wp_crop_image( $original_file, (int) $crop_x, (int) $crop_y, (int) $crop_w, (int) $crop_h, bp_core_avatar_thumb_width(), bp_core_avatar_thumb_height(), false, $avatar_folder_dir . '/' . $thumb_filename );
629
630        // Check for errors
631        if ( ! $full_cropped || ! $thumb_cropped || is_wp_error( $full_cropped ) || is_wp_error( $thumb_cropped ) )
632                return false;
633
634        // Remove the original
635        @unlink( $original_file );
636
637        return true;
638}
639
640/**
641 * bp_core_fetch_avatar_filter()
642 *
643 * Attempts to filter get_avatar function and let BuddyPress have a go
644 * at finding an avatar that may have been uploaded locally.
645 *
646 * @global array $authordata
647 * @param string $avatar The result of get_avatar from before-filter
648 * @param int|string|object $user A user ID, email address, or comment object
649 * @param int $size Size of the avatar image (thumb/full)
650 * @param string $default URL to a default image to use if no avatar is available
651 * @param string $alt Alternate text to use in image tag. Defaults to blank
652 * @return <type>
653 */
654function bp_core_fetch_avatar_filter( $avatar, $user, $size, $default, $alt = '' ) {
655        global $pagenow;
656
657        // Do not filter if inside WordPress options page
658        if ( 'options-discussion.php' == $pagenow )
659                return $avatar;
660
661        // If passed an object, assume $user->user_id
662        if ( is_object( $user ) )
663                $id = $user->user_id;
664
665        // If passed a number, assume it was a $user_id
666        else if ( is_numeric( $user ) )
667                $id = $user;
668
669        // If passed a string and that string returns a user, get the $id
670        else if ( is_string( $user ) && ( $user_by_email = get_user_by( 'email', $user ) ) )
671                $id = $user_by_email->ID;
672
673        // If somehow $id hasn't been assigned, return the result of get_avatar
674        if ( empty( $id ) )
675                return !empty( $avatar ) ? $avatar : $default;
676
677        if ( !$alt )
678                $alt = sprintf( __( 'Avatar of %s', 'buddypress' ), bp_core_get_user_displayname( $id ) );
679
680        // Let BuddyPress handle the fetching of the avatar
681        $bp_avatar = bp_core_fetch_avatar( array( 'item_id' => $id, 'width' => $size, 'height' => $size, 'alt' => $alt ) );
682
683        // If BuddyPress found an avatar, use it. If not, use the result of get_avatar
684        return ( !$bp_avatar ) ? $avatar : $bp_avatar;
685}
686add_filter( 'get_avatar', 'bp_core_fetch_avatar_filter', 10, 5 );
687
688/**
689 * Has the current avatar upload generated an error?
690 *
691 * @param array $file
692 * @return bool
693 */
694function bp_core_check_avatar_upload( $file ) {
695        if ( isset( $file['error'] ) && $file['error'] )
696                return false;
697
698        return true;
699}
700
701/**
702 * Is the file size of the current avatar upload permitted?
703 *
704 * @param array $file
705 * @return bool
706 */
707function bp_core_check_avatar_size( $file ) {
708        if ( $file['file']['size'] > bp_core_avatar_original_max_filesize() )
709                return false;
710
711        return true;
712}
713
714/**
715 * Does the current avatar upload have an allowed file type?
716 *
717 * Permitted file types are JPG, GIF and PNG.
718 *
719 * @param string $file
720 * @return bool
721 */
722function bp_core_check_avatar_type($file) {
723        if ( ( !empty( $file['file']['type'] ) && !preg_match('/(jpe?g|gif|png)$/i', $file['file']['type'] ) ) || !preg_match( '/(jpe?g|gif|png)$/i', $file['file']['name'] ) )
724                return false;
725
726        return true;
727}
728
729/**
730 * bp_core_avatar_upload_path()
731 *
732 * Returns the absolute upload path for the WP installation
733 *
734 * @uses wp_upload_dir To get upload directory info
735 * @return string Absolute path to WP upload directory
736 */
737function bp_core_avatar_upload_path() {
738        global $bp;
739
740        // See if the value has already been calculated and stashed in the $bp global
741        if ( isset( $bp->avatar->upload_path ) ) {
742                $basedir = $bp->avatar->upload_path;
743        } else {
744                // If this value has been set in a constant, just use that
745                if ( defined( 'BP_AVATAR_UPLOAD_PATH' ) ) {
746                        $basedir = BP_AVATAR_UPLOAD_PATH;
747                } else {
748                        if ( !bp_is_root_blog() ) {
749                                // Switch dynamically in order to support BP_ENABLE_MULTIBLOG
750                                switch_to_blog( bp_get_root_blog_id() );
751                        }
752
753                        // Get upload directory information from current site
754                        $upload_dir = wp_upload_dir();
755
756                        // Directory does not exist and cannot be created
757                        if ( !empty( $upload_dir['error'] ) ) {
758                                $basedir = '';
759
760                        } else {
761                                $basedir = $upload_dir['basedir'];
762                        }
763
764                        // Will bail if not switched
765                        restore_current_blog();
766                }
767
768                // Stash in $bp for later use
769                $bp->avatar->upload_path = $basedir;
770        }
771
772        return apply_filters( 'bp_core_avatar_upload_path', $basedir );
773}
774
775/**
776 * bp_core_avatar_url()
777 *
778 * Returns the raw base URL for root site upload location
779 *
780 * @uses wp_upload_dir To get upload directory info
781 * @return string Full URL to current upload location
782 */
783function bp_core_avatar_url() {
784        global $bp;
785
786        // See if the value has already been calculated and stashed in the $bp global
787        if ( isset( $bp->avatar->url ) ) {
788                $baseurl = $bp->avatar->url;
789
790        } else {
791                // If this value has been set in a constant, just use that
792                if ( defined( 'BP_AVATAR_URL' ) ) {
793                        $baseurl = BP_AVATAR_URL;
794                } else {
795                        // Get upload directory information from current site
796                        $upload_dir = wp_upload_dir();
797
798                        // Directory does not exist and cannot be created
799                        if ( !empty( $upload_dir['error'] ) ) {
800                                $baseurl = '';
801
802                        } else {
803                                $baseurl = $upload_dir['baseurl'];
804
805                                // If we're using https, update the protocol. Workaround for WP13941, WP15928, WP19037.
806                                if ( is_ssl() )
807                                        $baseurl = str_replace( 'http://', 'https://', $baseurl );
808
809                                // If multisite, and current blog does not match root blog, make adjustments
810                                if ( is_multisite() && bp_get_root_blog_id() != get_current_blog_id() )
811                                        $baseurl = trailingslashit( get_blog_option( bp_get_root_blog_id(), 'home' ) ) . get_blog_option( bp_get_root_blog_id(), 'upload_path' );
812                        }
813                }
814
815                // Stash in $bp for later use
816                $bp->avatar->url = $baseurl;
817        }
818
819        return apply_filters( 'bp_core_avatar_url', $baseurl );
820}
821
822/**
823 * Check if a given user ID has an uploaded avatar
824 *
825 * @since BuddyPress (1.0)
826 * @param int $user_id
827 * @return boolean
828 */
829function bp_get_user_has_avatar( $user_id = 0 ) {
830
831        if ( empty( $user_id ) )
832                $user_id = bp_displayed_user_id();
833
834        $retval = false;
835        if ( bp_core_fetch_avatar( array( 'item_id' => $user_id, 'no_grav' => true, 'html' => false ) ) != bp_core_avatar_default() )
836                $retval = true;
837
838        return (bool) apply_filters( 'bp_get_user_has_avatar', $retval, $user_id );
839}
840
841/**
842 * Utility function for fetching an avatar dimension setting
843 *
844 * @package BuddyPress
845 * @since BuddyPress (1.5)
846 *
847 * @param str $type 'thumb' for thumbs, otherwise full
848 * @param str $h_or_w 'height' for height, otherwise width
849 * @return int $dim The dimension
850 */
851function bp_core_avatar_dimension( $type = 'thumb', $h_or_w = 'height' ) {
852        global $bp;
853
854        $dim = isset( $bp->avatar->{$type}->{$h_or_w} ) ? (int) $bp->avatar->{$type}->{$h_or_w} : false;
855
856        return apply_filters( 'bp_core_avatar_dimension', $dim, $type, $h_or_w );
857}
858
859/**
860 * Get the avatar thumb width setting
861 *
862 * @package BuddyPress
863 * @since BuddyPress (1.5)
864 *
865 * @return int The thumb width
866 */
867function bp_core_avatar_thumb_width() {
868        return apply_filters( 'bp_core_avatar_thumb_width', bp_core_avatar_dimension( 'thumb', 'width' ) );
869}
870
871/**
872 * Get the avatar thumb height setting
873 *
874 * @package BuddyPress
875 * @since BuddyPress (1.5)
876 *
877 * @return int The thumb height
878 */
879function bp_core_avatar_thumb_height() {
880        return apply_filters( 'bp_core_avatar_thumb_height', bp_core_avatar_dimension( 'thumb', 'height' ) );
881}
882
883/**
884 * Get the avatar full width setting
885 *
886 * @package BuddyPress
887 * @since BuddyPress (1.5)
888 *
889 * @return int The full width
890 */
891function bp_core_avatar_full_width() {
892        return apply_filters( 'bp_core_avatar_full_width', bp_core_avatar_dimension( 'full', 'width' ) );
893}
894
895/**
896 * Get the avatar full height setting
897 *
898 * @package BuddyPress
899 * @since BuddyPress (1.5)
900 *
901 * @return int The full height
902 */
903function bp_core_avatar_full_height() {
904        return apply_filters( 'bp_core_avatar_full_height', bp_core_avatar_dimension( 'full', 'height' ) );
905}
906
907/**
908 * Get the max width for original avatar uploads
909 *
910 * @package BuddyPress
911 * @since BuddyPress (1.5)
912 *
913 * @return int The width
914 */
915function bp_core_avatar_original_max_width() {
916        global $bp;
917
918        return apply_filters( 'bp_core_avatar_original_max_width', (int) $bp->avatar->original_max_width );
919}
920
921/**
922 * Get the max filesize for original avatar uploads
923 *
924 * @package BuddyPress
925 * @since BuddyPress (1.5)
926 *
927 * @return int The filesize
928 */
929function bp_core_avatar_original_max_filesize() {
930        global $bp;
931
932        return apply_filters( 'bp_core_avatar_original_max_filesize', (int) $bp->avatar->original_max_filesize );
933}
934
935/**
936 * Get the default avatar
937 *
938 * @package BuddyPress
939 * @since BuddyPress (1.5)
940 *
941 * @return int The URL of the default avatar
942 */
943function bp_core_avatar_default() {
944        global $bp;
945
946        return apply_filters( 'bp_core_avatar_default', $bp->avatar->full->default );
947}
948
949/**
950 * Get the default avatar thumb
951 *
952 * @package BuddyPress
953 * @since BuddyPress (1.5)
954 *
955 * @return int The URL of the default avatar thumb
956 */
957function bp_core_avatar_default_thumb() {
958        global $bp;
959
960        return apply_filters( 'bp_core_avatar_thumb', $bp->avatar->thumb->default );
961}
962
963
964?>