За последние 24 часа нас посетили 34316 программистов и 1751 робот. Сейчас ищут 965 программистов ...

Как правильно обрезать фото и вывести его из бд php

Тема в разделе "PHP для новичков", создана пользователем eanautt, 11 июл 2017.

  1. eanautt

    eanautt Новичок

    С нами с:
    10 июл 2017
    Сообщения:
    27
    Симпатии:
    0
    Буду очень рад, если мне кто-нибудь поможет. Сразу скажу я новичок и мне нужен более полный код, чтобы я смог его понять со своим начальным уровнем знаний php
    --- Добавлено ---
    У меня есть код отправки фотографий в БД и код их вывода. Мне добавить возможности:
    1) Мне необходим скрипт обрезки фото по заданным размерам, например: 150px * 150px
    2) Скрипт вывода фото из бд в формате:
    2.1)
    HTML:
    1. <img src="">
    2.2)
    HTML:
    1. <div style="background: url();"></div>
    Вот мой скрипт, который есть на данный момент:

    PHP:
    1. <?php require "/includes/lgsn.php"; ?>
    2. <!DOCTYPE html>
    3. <html>
    4. <head>
    5.     <title>Upload test</title>
    6. </head>
    7. <body>
    8. <?php
    9. echo 'Test uploader';
    10. $connection = mysqli_connect("127.0.0.1", "/*Имя пользователя*/", "", "/*ДБ имя*/");
    11. if ( ! $connection) {
    12.     echo 'DB connection error!';
    13. }
    14.  
    15. $id = $_SESSION['ud_ae']['id'];
    16.  
    17. ?>
    18.  
    19.  
    20.  
    21.  
    22. <?php
    23. if( isset($_POST['do_avatar']) ) {
    24.  
    25. if( !empty( $_FILES['image']['name'] ) ) {
    26.   if ( $_FILES['image']['error'] == 0 ) {
    27.  
    28.     if( substr($_FILES['image']['type'], 0, 5)=='image' ) {
    29.    
    30.       $image = file_get_contents( $_FILES['image']['tmp_name'] );
    31.    
    32.       $image = mysql_escape_string( $image );
    33.    
    34.       $query = "UPDATE `users` SET `avatar`='".$image."' WHERE id=$id ";
    35.    
    36.       mysqli_query($connection, $query);
    37.  
    38.       echo 'Аватар успешно загружен';
    39.     }
    40.   }
    41. } else {
    42.     echo 'Выберите изображение';
    43. }
    44. }
    45. ?>
    46.  
    47. <form enctype="multipart/form-data" method="POST" action="/avatar.php">
    48. Изображение: <input type="file" name="image">
    49. <input type="submit" name="do_avatar" value="Загрузить">
    50. </form>
    51.  
    52. <p>Ваш аватар</p>
    53.  
    54.  
    55. <?php
    56. $get_avatar = "SELECT `avatar` FROM `users` WHERE `id`=".$id;
    57. $res = mysqli_query($connection, $get_avatar);
    58. if ( mysqli_num_rows( $res ) > 0 )
    59.     while( $img = mysqli_fetch_array( $res ) )
    60.         echo '<img src="data:image/jpeg;base64,'.base64_encode($img['avatar']).'" />';
    61.  
    62.     ?>
    63.  
    64.  
    65.     <div style="width: 152px; height: 152px; background: url(); background-repeat: no-repeat; background-size: cover;">
    66.      
    67.     </div>
    68.  
    69.  
    70. </body>
    71. </html>
    --- Добавлено ---
     
  2. ADSoft

    ADSoft Старожил

    С нами с:
    12 мар 2007
    Сообщения:
    3.866
    Симпатии:
    753
    Адрес:
    Татарстан
    не очень хорошая идея хранить изображения в бд
     
    Maputo нравится это.
  3. eanautt

    eanautt Новичок

    С нами с:
    10 июл 2017
    Сообщения:
    27
    Симпатии:
    0
    Я буду рад любым предложениям, связанным с реализацией данной идеи. Если это "не хорошая идея", можете подсказать как лучше это реализовать?
     
  4. ADSoft

    ADSoft Старожил

    С нами с:
    12 мар 2007
    Сообщения:
    3.866
    Симпатии:
    753
    Адрес:
    Татарстан
    обычно изображения хранят на диске в папочке, в БД лишь ссылка к этим файлам...
    подходы уменьшения картинок разные, с своими + и -
    1. "На лету". Хранить изображение как есть, при запросе динамически в памяти изменять размер (gd2, imagick) - отдавать изображение
    2. Допустим знаем, что всегда только 150х150 размер нужен будет и оригинал. Тогда лучше генерить файлик превью и ложить рядом оригиналом. При запросе - отдавать оригинал или превью.
    3. Каждый раз размер разный. Делаем как в 2, с той разницей, что предварительно проверяем - не был ли уже создан такой файл, если нет - то генерим превью заданого размера, если был - отдаем уже существующий

    возможно есть другие варианты.... и их комбинации

    1. Минусы - будет конкретно тормозить при достаточном количестве отображения миниатюр, например галерея превьюх. Вплоть до занятия всей озу и вылета скрипта. Отсутствие кеширования (каждый раз будет генерить снова). Плюсы - доп место не занимает
    2. Минусы - ограниченность одним, (2-3) размерами, доп место на диске. Плюсы - не будет грузить озу и скрипт, это обычная картинка и она будет кешироваться стандартно веб сервером
    3. Минусы - место на диске, Плюсы - гибкость, пониженная нагрузка чем в 1, чуть выше чем в 2, кешируемость

    выбирайте что вам нужно и реализуйте
     
  5. Maputo

    Maputo Активный пользователь

    С нами с:
    30 июл 2015
    Сообщения:
    1.136
    Симпатии:
    173
    Для начала, извлеченные из базы данные необходимо запихнуть в ресурс изображения (image resource) вот этой функцией, чтобы можно было эту картинку обрабатывать встроенными методами
    PHP:
    1. $base_image = imagecreatefromstring ($img['avatar']);
    далее стоит узнать размеры картинки
    PHP:
    1. $w1 = imagesx($base_image);
    2. $h1 = imagesy($base_image);
    Создать новое изображение требуемых размеров с помощью вот этой функции
    PHP:
    1. $width = 200;
    2. $height = 200;
    3. $new_avatar = imagecreatetruecolor ($width , $height);
    Вычислить какую часть картинки стоит вырезать под новое соотношение сторон
    PHP:
    1. //Потребуются еще 6 значений, зависящих от размеров исходного и нового изображений
    2. $new_x = 0; // Координаты верхнего левого угла прямоугольника на новой картинке для вставки куска
    3. $new_y = 0; // из старой картинки (как правило верхний левый угол нового изображения)
    4. $old_x = ... // Координаты на старом изображении верхнего левого
    5. $old_y = ... // угла того куска, который будет вырезан $old_x = 0, $old_y = 0
    6. $old_w = ... // Ширина и высота, вырезаемого
    7. $old_h = ... // на старом изображении куска $old_w = $w1, $old_h = $h1
    Потом с помощью этой функции вырезать кусок с исходного изображения и поместить его в новое
    PHP:
    1. imagecopyresampled ( $new_avatar, $base_image, $new_x, $new_y, $old_x, $old_y, $width, $height, $old_w, $old_h);
    Потом финт ушами. Не нашел другого способа - может кто подскажет.
    Буферизуем вывод. Выводим полученное изображение в буфер этой функцией. Извлекаем новое изображение из буфера. Опустошаем и закрываем этот буфер.
    PHP:
    1. imagejpeg($new_avatar, null, 100);
    2. $avatar_image =  ob_get_contents();
    Теперь его можно кодировать в base64
    PHP:
    1. base64_encode($avatar_image)
     
    #5 Maputo, 11 июл 2017
    Последнее редактирование: 11 июл 2017
  6. _ne_scaju_

    _ne_scaju_ Старожил

    С нами с:
    25 ноя 2016
    Сообщения:
    2.149
    Симпатии:
    118
    @Maputo
    надо будет попробовать ну чуть позже)
     
  7. Maputo

    Maputo Активный пользователь

    С нами с:
    30 июл 2015
    Сообщения:
    1.136
    Симпатии:
    173
    Не храните изображения в базе данных)
     
  8. _ne_scaju_

    _ne_scaju_ Старожил

    С нами с:
    25 ноя 2016
    Сообщения:
    2.149
    Симпатии:
    118
    @Maputo
    Это уже проходил, узнавал когда то даже получалось все, в базе храню названия изображения, его еще можно сохранять в другом названии, применить какие-то функции для изменения имени. Но с обрезкой проблемы были и еще остаются, но к этому чуть позже дойду, тогда задам вопрос, если не смогу разобраться сам)
     
  9. Познающий php

    Познающий php Новичок

    С нами с:
    23 мар 2017
    Сообщения:
    381
    Симпатии:
    74
    Обрезание все таки или изменение размера изображения? Если не знаешь разницы, обратись к евреям, они тебе объяснят.

    Обрезание через Imagick:
    PHP:
    1. $img = new Imagick('photo.jpg'); // создаем объект
    2. $img->cropImage(150, 150,0,0); // обрезаем
    3. $img->writeImage('photo_150.jpg'); // сохраняем обрезанную картинку photo_150.jpg