diff --git a/lib/outputcomponents.php b/lib/outputcomponents.php index c378b6286d0a5..002eb33b163b9 100644 --- a/lib/outputcomponents.php +++ b/lib/outputcomponents.php @@ -259,6 +259,78 @@ public static function unalias(stdClass $record, array $extrafields=null, $idali return $return; } + + /** + * Works out the URL for the users picture. + * + * This method is recommended as it avoids costly redirects of user pictures + * if requests are made for non-existent files etc. + * + * @param renderer_base $renderer + * @return moodle_url + */ + public function get_url(moodle_page $page, renderer_base $renderer = null) { + global $CFG; + + if (is_null($renderer)) { + $renderer = $page->get_renderer('core'); + } + + if (!empty($CFG->forcelogin) and !isloggedin()) { + // protect images if login required and not logged in; + // do not use require_login() because it is expensive and not suitable here anyway + return $renderer->pix_url('u/f1'); + } + + // Sort out the filename and size. Size is only required for the gravatar + // implementation presently. + if (empty($this->size)) { + $filename = 'f2'; + $size = 35; + } else if ($this->size === true or $this->size == 1) { + $filename = 'f1'; + $size = 100; + } else if ($this->size >= 50) { + $filename = 'f1'; + $size = (int)$this->size; + } else { + $filename = 'f2'; + $size = (int)$this->size; + } + + if ($this->user->picture == 1) { + // The user has uploaded their own profile pic. In this case we will + // check that a profile pic file does actually exist + $fs = get_file_storage(); + $context = get_context_instance(CONTEXT_USER, $this->user->id); + if (!$fs->file_exists($context->id, 'user', 'icon', 0, '/', $filename.'/.png')) { + if (!$fs->file_exists($context->id, 'user', 'icon', 0, '/', $filename.'/.jpg')) { + return $renderer->pix_url('u/'.$filename); + } + } + $path = '/'; + if (clean_param($page->theme->name, PARAM_THEME) == $page->theme->name) { + // We append the theme name to the file path if we have it so that + // in the circumstance that the profile picture is not available + // when the user actually requests it they still get the profile + // picture for the correct theme. + $path .= $page->theme->name.'/'; + } + return moodle_url::make_pluginfile_url($context->id, 'user', 'icon', NULL, $path, $filename); + + } else if ($this->user->picture == 2) { + // This is just VERY basic support for gravatar to give the actual + // implementor a headstart in what to do. + if ($size < 1 || $size > 500) { + $size = 35; + } + $md5 = md5(strtolower(trim($this->user->email))); + $default = urlencode($this->pix_url('u/'.$filename)->out(false)); + return "http://www.gravatar.com/avatar/{$md5}?s={$size}&d={$default}"; + } + + return $renderer->pix_url('u/'.$filename); + } } /** diff --git a/lib/outputrenderers.php b/lib/outputrenderers.php index 1f00572bdc6d7..e7ded085814e7 100644 --- a/lib/outputrenderers.php +++ b/lib/outputrenderers.php @@ -1764,33 +1764,21 @@ protected function render_user_picture(user_picture $userpicture) { } if (empty($userpicture->size)) { - $file = 'f2'; $size = 35; } else if ($userpicture->size === true or $userpicture->size == 1) { - $file = 'f1'; $size = 100; - } else if ($userpicture->size >= 50) { - $file = 'f1'; - $size = $userpicture->size; } else { - $file = 'f2'; $size = $userpicture->size; } $class = $userpicture->class; - if ($user->picture == 1) { - $usercontext = get_context_instance(CONTEXT_USER, $user->id); - $src = moodle_url::make_pluginfile_url($usercontext->id, 'user', 'icon', NULL, '/', $file); - - } else if ($user->picture == 2) { - //TODO: gravatar user icon support - - } else { // Print default user pictures (use theme version if available) + if ($user->picture != 1 && $user->picture != 2) { $class .= ' defaultuserpic'; - $src = $this->pix_url('u/' . $file); } + $src = $userpicture->get_url($this->page, $this); + $attributes = array('src'=>$src, 'alt'=>$alt, 'title'=>$alt, 'class'=>$class, 'width'=>$size, 'height'=>$size); // get the image html output fisrt diff --git a/pluginfile.php b/pluginfile.php index cc855cc32bfef..244f8c8447b73 100644 --- a/pluginfile.php +++ b/pluginfile.php @@ -294,24 +294,32 @@ // ======================================================================================================================== } else if ($component === 'user') { if ($filearea === 'icon' and $context->contextlevel == CONTEXT_USER) { - // XXX: pix_url will initialize $PAGE, so we have to set up context here - // this temp hack should be fixed by better solution - $PAGE->set_context(get_system_context()); - if (!empty($CFG->forcelogin) and !isloggedin()) { + $redirect = false; + if (count($args) == 1) { + $themename = theme_config::DEFAULT_THEME; + $filename = array_shift($args); + } else { + $themename = array_shift($args); + $filename = array_shift($args); + } + if ((!empty($CFG->forcelogin) and !isloggedin())) { // protect images if login required and not logged in; // do not use require_login() because it is expensive and not suitable here anyway - redirect($OUTPUT->pix_url('u/f1')); + $redirect = true; } - $filename = array_pop($args); - if ($filename !== 'f1' and $filename !== 'f2') { - redirect($OUTPUT->pix_url('u/f1')); + if (!$redirect and ($filename !== 'f1' and $filename !== 'f2')) { + $filename = 'f1'; + $redirect = true; } - if (!$file = $fs->get_file($context->id, 'user', 'icon', 0, '/', $filename.'/.png')) { + if (!$redirect && !$file = $fs->get_file($context->id, 'user', 'icon', 0, '/', $filename.'/.png')) { if (!$file = $fs->get_file($context->id, 'user', 'icon', 0, '/', $filename.'/.jpg')) { - redirect($OUTPUT->pix_url('u/'.$filename)); + $redirect = true; } } - + if ($redirect) { + $theme = theme_config::load($themename); + redirect($theme->pix_url('u/'.$filename, 'moodle')); + } send_stored_file($file, 60*60*24); // enable long caching, there are many images on each page } else if ($filearea === 'private' and $context->contextlevel == CONTEXT_USER) {