<?php

if (!defined('BASEPATH')) {
    exit('No direct script access allowed');
}

class Rtgc_upload_image extends \Abstract_rtgc_callback
{

    protected $config = [
        'upload_path'           => './assets/uploads/multimedia/images',
        'allowed_types'         => 'gif|jpg|png|jpeg',
        'max_size'              => '0',
        'encrypt_name'          => false,
        'callback_after_upload' => [],
        'no_image_file'         => '/assets/uploads/userinfo/author.jpg',
        // Templates
        'template_column'       => '<a href="{photo_path}" class="image-thumbnail"><img alt="" src="{thumbnail_path}" style="width: 100px;" /></a>',
        'template_field'        => '<div class="img_box">'
        . '<div class="photo" style="background: url({img}) no-repeat center 100%; background-size: cover;">'
        . '<label style="display:none" class="btn btn-success">{upload_label}'
        . '<input type="file" name="{name}" style="display: none" />'
        . '</label>'
        . '<label style="display:none" class="btn btn-danger">'
        . '<input class="del_btn" type="checkbox" data-id="del_{name}" /> {delete_label}'
        . '</label>'
        . '<input type="hidden" name="{name}" value="{value}" />'
        . '<input type="hidden" id="del_{name}" name="del_{name}" value="0" />'
        . '</div>'
        . '</div>',
        // Js
        'js_string'             => '$(function(){'
        . '$(\'.img_box\').on(\'change\', \'input[type="file"]\', function(){'
        . ' if (this.files && this.files[0]) {'
        . '  var reader = new FileReader();'
        . '  var img = $(this).parents(".img_box").find(".photo");'
        . '  reader.onload = function (e) {'
        . '   img.css({"background":\'url(\'+e.target.result+\') no-repeat center 100%\',  \'background-size\': \'cover\'}).show();'
        . '  };'
        . '  reader.readAsDataURL(this.files[0]);'
        . ' }'
        . ' $(this).parents(".img_box").find(".del_btn").prop("checked", false).change();'
        . '});'
        . '$(\'.img_box\').on(\'change\', \'.del_btn\', function(){'
        . 'var photo = $(this).parents(".img_box").find(".photo");'
        . 'if ($(this).prop("checked")) { photo.addClass("no-photo");} else {photo.removeClass("no-photo");}'
        . '$("#" + $(this).data("id")).val($(this).prop("checked") ? "1" : "0");'
        . '});'
        . '});'
    ];
    protected $ci = null;
    protected $value = '';
    protected $errors = '';

    public function __construct($config = [])
    {
        if (!empty($config)) {
            $this->merge_config($config);
        }
        $this->ci = & get_instance();

        // Set max file size
        if (empty($this->config['max_size'])) {
            $this->config['max_size'] = $this->file_upload_max_size();
        }
    }

    public function get_config()
    {
        return $this->config;
    }

    public function set_config($config = [])
    {
        $this->config = $config;

        return $this;
    }

    public function get_errors()
    {
        return $this->errors;
    }

    public function merge_config($config = [])
    {
        $this->config = array_merge($this->get_config(), $config);

        return $this;
    }

    public function column($value = '', $data = [])
    {
        // Prepare photos
        $image = $this->get_image_lib();
        $content = [
            'thumbnail_path' => $image->getImage($value, 100, 100),
            'photo_path'     => $image->getImage($value),
        ];

        return $this->ci->parser->parse_string($this->config['template_column'], $content, true);
    }

    public function field($name = 'userfile', $value = '')
    {
        if (!empty($value)) {
            $this->value = $value;
        }

        $img = (!empty($this->value)) ? ltrim(rtrim($this->config['upload_path'], '/'), '.') . '/' . $this->value : $this->config['no_image_file'];
        $html = $this->ci->parser->parse_string($this->config['template_field'] . $this->get_errors(), [
            'img'          => $img,
            'upload_label' => $this->ci->lang->line('Upload picture'),
            'delete_label' => $this->ci->lang->line('Delete'),
            'name'         => $name,
            'value'        => $this->value,
                ], TRUE);

        // Add js
        $this->ci->load->library('ciext/ciext')->load_jquery();
        $this->ci->js_css->add_js_string($this->config['js_string']);

        // Clear
        $this->value = '';

        return $html;
    }

    public function do_upload($name = 'userfile')
    {
        // Remove file if needed
        if (!empty($this->ci->input->post('del_' . $name))) {
            $this->remove_file($this->ci->input->post($name));
            $_POST[$name] = '';

            return true;
        }

        // No changes
        if (empty($_FILES[$name]['name'])) {

            return true;
        }

        // Remove old file
        $this->remove_file($this->ci->input->post($name));

        $this->ci->load->library('upload');
        $this->ci->upload->initialize($this->config);

        if (!$this->ci->upload->do_upload($name)) {
            $this->errors = $this->ci->upload->display_errors('<span class="error">', '</span>');

            return false;
        } else {
            $data = $this->ci->upload->data();
            $this->value = $data['file_name'];

            // Callback
            $callback = $this->config['callback_after_upload'];
            if (is_callable($callback)) {
                call_user_func($callback, $this->value);
            }

            $_POST[$name] = $this->value;

            return true;
        }
    }

    public function remove_file($file = '')
    {
        if (!empty($file)) {
            $tmp = explode(DIRECTORY_SEPARATOR, $file);
            $basename = array_pop($tmp);
            $old_file = $this->config['upload_path'] . '/' . $basename;
            if (file_exists($old_file) && !is_dir($old_file)) {
                unlink($old_file);
                $this->get_image_lib()->clearCropped($basename);
            }
        }

        return $this;
    }

    protected function get_image_lib()
    {
        return $this->ci->load->library('image')->setSourcePath(trim(ltrim($this->config['upload_path'], '.'), '/'));
    }

    protected function file_upload_max_size()
    {
        static $max_size = -1;

        if ($max_size < 0) {
            // Start with post_max_size.
            $max_size = $this->parse_size(ini_get('post_max_size'));

            // If upload_max_size is less, then reduce. Except if upload_max_size is
            // zero, which indicates no limit.
            $upload_max = $this->parse_size(ini_get('upload_max_filesize'));
            if ($upload_max > 0 && $upload_max < $max_size) {
                $max_size = $upload_max;
            }
        }
        return $max_size;
    }

    protected function parse_size($size)
    {
        $unit = preg_replace('/[^bkmgtpezy]/i', '', $size); // Remove the non-unit characters from the size.
        $size = preg_replace('/[^0-9\.]/', '', $size); // Remove the non-numeric characters from the size.
        if ($unit) {
            // Find the position of the unit in the ordered string which is the power of magnitude to multiply a kilobyte by.
            return round($size * pow(1024, stripos('bkmgtpezy', $unit[0])));
        } else {
            return round($size);
        }
    }

}
