Пользовательский аватар WordPress (Кастомные поля в профиле пользователя).

Сегодня рассмотрим вариант, как можно добавить в профиль пользователя WordPress возможность загружать изображения, в качестве аватара, а так же выведем его в комментариях, в качестве примера.

Использовать будем как обычно для вывода нужных Нам полей два события: show_user_profile и edit_user_profile. А для обработки данных personal_options_update и edit_user_profile_update. Помимо этого сделаем проверку загрузки определенного расширения и выведем при не соответствии сообщение с ошибкой. Для этого нам понадобятся ещё два события.

  • load-user-edit.php — будет выводить сообщения на странице user-edit.php, при редактировании администратором страницы юзера
  • load-profile.php — будет выводить сообщения на странице profile.php, когда пользователь редактирует свой профиль
Начнем с вывода на экран нужных полей

if(!function_exists('VAB_user_fields')){
 function VAB_user_fields($user){
  global $pagenow;
  if($pagenow=='profile.php'||$pagenow=='user-edit.php'){
   wp_nonce_field('VAB_mode_ufields_nonce','VAB_ufields_nonce');
   $id=$user->ID;
   $myAvatar=get_the_author_meta('myAvatar',$id);
   $del_But='<img style="margin-bottom:-7px!important;cursor:pointer;" id="VAB_remove" src="'.get_template_directory_uri().'/images/delete.png" width="auto" height="33">';
   $avka=!empty($myAvatar)?'<img style="width:64px;height:64px;" src="'.get_site_url()."/wp-content/uploads/myAvatar/".$myAvatar.'" />'.$del_But.'<input id="checkrem" style="display:none;" type="checkbox" name="removemyAvatar">':'';
   echo'<label for="myAvatar">'.__('Пользовательский аватар','VAB').' »» '.__('только JPEG','VAB').' <input type="file" name="filename" id="myAvatar"/></label>'.$avka.'<script type="text/javascript">jQuery(\'form\').attr(\'enctype\',\'multipart/form-data\');jQuery(\'#checkrem\').prop("checked",false);jQuery(document).on(\'click\',\'#VAB_remove\',function(){jQuery(this).prev(\'img\').remove();jQuery(this).next(\'#checkrem\').prop("checked",true);});</script>';
}}}
add_action('show_user_profile','VAB_user_fields');
add_action('edit_user_profile','VAB_user_fields');

Разберем код подробнее:

  • переменная $del_But — это просто какое-либо изображение, в данном случае корзина, при нажатии на которую будет происходить удаление из разметки аватарки с помощью jQuery (тут может быть что угодно, не обязательно изображение главно идентификатор, который важен для клика)
  • переменная $avka — через тернарное выражение определяем в переменную (при наличии мета данных в базе) либо изображение (будущая аватарка) совместно с кнопкой для удаления и скрытым полем type=»checkbox», которое будет служить сигналом для удаления данных из базы, а так же изображения из папки, либо оставим пустым значением
  • через echo выводим на экран input type=»file» для выбора изображения, переменную $avka, которая либо пустая, либо наполнена данными и скрипт, который можно выводить так же через события в подвале, либо подключать файл (я же вывел его по месту)

Разберем подробнее скрипт

jQuery('form').attr('enctype','multipart/form-data');

Для работы с файлами у формы должен быть обязательно атрибут enctype=»multipart/form-data». А что такое функционал в админки вордпресс? Это все формы. Если его не добавить будем ловить довольно знаменитую ошибку

Warning: Cannot modify header information — headers already sent by

 

jQuery('#checkrem').prop("checked",false);

В данном случае при загрузки страницы Мы на всякий случай снимаем со скрытого поля с идентификатором #checkrem флажок, т.к. в обработчике у нас по условию будет очистка данных в базе и удаление аватарки из папки при установленном флажке.

jQuery(document).on('click','#VAB_remove',function(){
 jQuery(this).prev('img').remove();
 jQuery(this).next('#checkrem').prop("checked",true);
});

Ну а сдесь Мы по нажатию на изображение корзина, удаляем из разметки предыдущий тег из разметки (это тег img — наша аватарка) и на следующий за корзиной скрытый инпут (идентификатор #checkrem) выставляем флажок (checked — отмеченый), благодаря чему, нажав на кнопку «Обновить профиль» произойдет удаление данных.

Обработчик - пояснение оставлю в коде

if(!function_exists('save_VAB_user_fields')){
 function save_VAB_user_fields($user_id){
  $nonce=filter_input(INPUT_POST,'VAB_ufields_nonce',FILTER_SANITIZE_STRING);
  if(!$nonce){return;}//проверяем наши nonce поля
  if(!wp_verify_nonce($nonce,'VAB_mode_ufields_nonce')){return;}//проверяем наши nonce поля
  $myAvatar=get_the_author_meta('myAvatar',$user_id);//проверяем данные в базе
  if(is_uploaded_file($_FILES["filename"]["tmp_name"])){//Если файл загружен при помощи HTTP POST
   $inp=$_FILES['filename'];$FILES_name=$inp['name'];$FILES_tmp_name=$inp['tmp_name'];//собираем данные на файл
   $ext=substr($FILES_name,strpos($FILES_name,'.'),strlen($FILES_name)-1);//получаем расширение файла
    if($ext==".jpg"||$ext=='.jpeg'){//если расширение jpg или jpeg
     $DiR=ABSPATH.'wp-content/uploads/myAvatar';
      if(!file_exists($DiR)){//если директории, куда будем отправлять аватарки нет
       mkdir($DiR,0777,true);}// создадим её
      move_uploaded_file($FILES_tmp_name, $DiR."/".$user_id.$ext);//перемещаем загруженный файл в директорию
      update_user_meta($user_id,'myAvatar',$user_id.$ext);//сохраняем в базе информацию о загруженном файле
    }else{//если расширение не прошло валидацию
      $erR='<div class="error"><p><strong>'.__('Ошибка','VAB').'</strong>: '.__('Выбран неверный формат изображения','VAB').'</p></div>';//формируем для вывода на экран текст ошибки
      set_transient('erRorUser',array('nonce'=>$erR),10); return;}}//и сохраняем в базе во временной опции на 10 секунд
    if(isset($_POST['removemyAvatar'])&&isset($myAvatar)){//если при нажатии на кнопку «Обновить профиль» скрытый чекбокс был отмечен и есть данные в базе
     if(file_exists(ABSPATH.'wp-content/uploads/myAvatar/'.$myAvatar)){
     unlink(ABSPATH.'wp-content/uploads/myAvatar/'.$myAvatar);}//удаляем файл, при наличии
     delete_user_meta($user_id,'myAvatar');}//удаляем мета данные из базы
}}
add_action('personal_options_update','save_VAB_user_fields');
add_action('edit_user_profile_update','save_VAB_user_fields');

Важно!!! При загрузке файла необходимо учесть и то, что пользователь может загружать файлы больших объемов и разрешений. Можно, разумеется, добавить проверку на размер файла, но в идеале, думаю, их необходимо, при необходимости, проверять и обрезать до нужных размеров, а так же оптимизировать. Для этих целей я использую самописную функцию, в которой собран нужный мне набор  Imagick. Все возможности Imagick Вы можете посмотреть здесь. Функцию выкладывать я не стал, т.к. это отдельная история…

Теперь оформим вывод ошибки в админ панели WordPress на случай, если формат будет не верным. Используем два события (add_action) load-user-edit.php и load-profile.php. Прикрепляем к ним произвольную функцию. В данном случае VAB_add_error, в которой проверяем наличие в базе временной опции get_transient(‘erRorUser’) и при наличии данных запускаем событие (add_action) admin_notices, к которому прикрепляем функцию (VAB_show_error), которая уже выводит на экран через echo данные временной опции get_transient(‘erRorUser’)

Сам код собственно

if(!function_exists('VAB_add_error')){
 function VAB_add_error(){
  $data=get_transient('erRorUser');//проверяем в базе наличие временной опции
  if($data&&$data['nonce']){//проверяем ее содержимое
   add_action('admin_notices','VAB_show_error');}}}//запускаем событие admin_notices
add_action('load-user-edit.php','VAB_add_error');
add_action('load-profile.php','VAB_add_error');
if(!function_exists('VAB_show_error')){
 function VAB_show_error(){
  $data=get_transient('erRorUser');$erRorMessage='';
  if($data&&$data['nonce']){$erRorMessage=$data['nonce'];}
  echo$erRorMessage;}}//выводим на экран содержимое временной опции

Осталось, где-то вывести загруженный файл. Для примера я решил вывести его в комментариях. У каждой темы шаблон комментариев может сильно отличаться. По умолчанию аватары выводятся через функцию вордпресс get_avatar(). Необходимо просто её заменить, либо вывести альтернативу при наличии загруженного пользователем.

Пример кода

 $myAvatar=get_the_author_meta('myAvatar',$comment->user_id);
 echo !empty($myAvatar)?'<img style="width:64px;height:64px;" src="'.get_site_url()."/wp-content/uploads/myAvatar/".$myAvatar.'" />':get_avatar($comment,52);

 // echo get_avatar($comment,52);

Собственно на этом все…

Смотреть видео на ютуб канале «Пользовательский аватар WordPress (Кастомные поля в профиле пользователя)»


Кастомные поля