<?php

namespace WeDevs\Wpuf\Pro\Admin;

use WeDevs\Wpuf\Data\Country_State;
use WeDevs\Wpuf\Traits\TaxableTrait;

/**
* Generate Invoice on payments
*
* @since 2.5.6
*/
class Invoice {

    use TaxableTrait;

    public function __construct() {
        require_once WPUF_PRO_ROOT . '/lib/invoicr/invoicr.php';

        add_action( 'wpuf_payment_received', [ $this, 'generate_invoice' ], 100, 2 );
        add_action( 'wpuf_admin_subscription_content', [ $this, 'enable_sub_noti_email' ], 10, 1 );
        add_filter( 'wpuf_settings_sections', [ $this, 'wpuf_pro_settings_tab' ] );
        add_filter( 'wpuf_settings_fields', [ $this, 'wpuf_pro_settings_content' ] );
        // date_default_timezone_set(get_option('timezone_string'));
    }

    public function wpuf_pro_settings_tab( $settings ) {
        $settings2 = [
            [
                'id'    => 'wpuf_payment_invoices',
                'title' => __( 'Invoices', 'wpuf-pro' ),
                'icon' => 'dashicons-media-spreadsheet',
            ],
        ];

        return array_merge( $settings, $settings2 );
    }

    public function wpuf_pro_settings_content( $settings_fields ) {
        $settings_fields2 = [
            'wpuf_payment_invoices' => [
                [
                    'name'    => 'enable_invoices',
                    'label'   => __( 'Enable Invoices', 'wpuf-pro' ),
                    'desc'    => __( 'Enable sending invoices for completed payments', 'wpuf-pro' ),
                    'type'    => 'checkbox',
                    'default' => 'on',
                ],
                [
                    'name'    => 'show_invoices',
                    'label'   => __( 'Show Invoices', 'wpuf-pro' ),
                    'desc'    => __( 'Show Invoices option where <code>[wpuf_account]</code> is located', 'wpuf-pro' ),
                    'type'    => 'checkbox',
                    'default' => 'on',
                ],
                [
                    'name'     => 'set_logo',
                    'label'    => __( 'Set Invoice Logo', 'wpuf-pro' ),
                    'desc'     => __( 'This sets the company Logo to be used in Invoice', 'wpuf-pro' ),
                    'type'     => 'file',
                    'default'  => false,
                ],
                [
                    'name'     => 'set_color',
                    'label'    => __( 'Set Invoice Color', 'wpuf-pro' ),
                    'desc'     => __( 'Set color code to be used in invoice', 'wpuf-pro' ),
                    'type'     => 'text',
                    'default'  => '#e435226',
                ],
                [
                    'name'       => 'set_from_address',
                    'label'    => __( 'From Address', 'wpuf-pro' ),
                    'desc'     => sprintf(
                        /* translators: 1: line break, 2: strong tag open, 3: strong tag close, 4-7: code tags for placeholders */
                        __( 'This sets the provider information of the Invoice. Note: use the <xmp class="wpuf-xmp-tag"><br></xmp> tag to enter line breaks.', 'wpuf-pro' ),
                        '<br>',
                        '<strong>',
                        '</strong>',
                    ),
                    'type'     => 'textarea',
                ],
                [
                    'name'       => 'set_title',
                    'label'    => __( 'Invoice Title', 'wpuf-pro' ),
                    'desc'     => __( 'This sets the payment information title of the Invoice', 'wpuf-pro' ),
                    'type'     => 'text',
                ],
                [
                    'name'       => 'set_paragraph',
                    'label'    => __( 'Invoice Paragraph', 'wpuf-pro' ),
                    'desc'     => __( 'This sets the payment information paragraph of the Invoice', 'wpuf-pro' ),
                    'type'     => 'textarea',
                ],
                [
                    'name'       => 'set_footernote',
                    'label'    => __( 'Invoice Footer', 'wpuf-pro' ),
                    'desc'     => __( 'This sets the footer of the Invoice', 'wpuf-pro' ),
                    'type'     => 'text',
                ],
                [
                    'name'       => 'set_filename',
                    'label'    => __( 'Invoice Filename Prefix', 'wpuf-pro' ),
                    'desc'     => __( 'This sets the filename prefix of the Invoice', 'wpuf-pro' ),
                    'type'     => 'text',
                ],
                [
                    'name'       => 'set_mail_sub',
                    'label'    => __( 'Set Invoice Mail Subject', 'wpuf-pro' ),
                    'desc'     => __( 'This sets the mail subject of the Invoice', 'wpuf-pro' ),
                    'type'     => 'text',
                ],
                [
                    'name'       => 'set_mail_body',
                    'label'    => __( 'Set Invoice Mail Body', 'wpuf-pro' ),
                    'desc'           => sprintf(
                        /* translators: 1: line break, 2: strong tag open, 3: strong tag close, 4-9: code tags for invoice placeholders */
                        __( 'This sets the mail body of the Invoice.%1$s%2$sYou may use:%3$s %4$s %5$s %6$s %7$s %8$s %9$s', 'wpuf-pro' ),
                        '<br>',
                        '<strong>',
                        '</strong>',
                        '<code>{username}</code>',
                        '<code>{user_email}</code>',
                        '<code>{display_name}</code>',
                        '<code>{invoice_id}</code>',
                        '<code>{payment_amount}</code>',
                        '<code>{payment_type}</code>',
                    ),
                    'type'           => 'wysiwyg',
                    'sanitize_callback' => 'wp_kses_post',
                ],
                [
                    'name'           => 'send_attachment',
                    'label'          => __( 'Send Invoice as Attachment', 'wpuf-pro' ),
                    'desc'           => __( 'Enable to send the invoice PDF as an email attachment', 'wpuf-pro' ),
                    'type'           => 'checkbox',
                    'default'        => 'on',
                ],
            ],
        ];

        return array_merge( $settings_fields, $settings_fields2 );
    }

    public function generate_invoice( $data, $recurring ) {
        global $wpdb;

        $enable_invoices  = wpuf_get_option( 'enable_invoices', 'wpuf_payment_invoices', 'on' );
        $show_invoice     = wpuf_get_option( 'show_invoices', 'wpuf_payment_invoices', 'on' );
        $inv_logo         = wpuf_get_option( 'set_logo', 'wpuf_payment_invoices' );
        $inv_color        = wpuf_get_option( 'set_color', 'wpuf_payment_invoices', '#e435226' );
        $inv_from_addr    = wpuf_get_option( 'set_from_address', 'wpuf_payment_invoices' );
        $inv_from_addr    = explode( '<br>', $inv_from_addr );
        $inv_to_addr      = [];
        $addr             = [];
        $addr_options     = get_option( 'wpuf_address_options', false );
        if ( $addr_options && ! empty( $addr_options['show_address'] ) ) {
            if ( ! empty( $data['payer_address'] ) ) {
                $payer_address = $data['payer_address'];
            } else {
                $payer_address = $wpdb->get_var(
                    $wpdb->prepare(
                        "SELECT payer_address FROM {$wpdb->prefix}wpuf_transaction WHERE transaction_id = %s",
                        $data['transaction_id']
                    )
                );
            }

            if ( ! empty( $payer_address ) ) {
                $addr = maybe_unserialize( $payer_address );
            }
        }

        if ( ! empty( $data['payer_first_name'] ) && ! empty( $data['payer_last_name'] ) ) {
            $inv_to_addr[] = $data['payer_first_name'] . ' ' . $data['payer_last_name'];
        } else {
            $inv_to_addr[] = $data['payer_email'];
        }

        if ( ! empty( $addr['billing_country'] ) ) {
            $country_state = new Country_State();
            $countries     = $country_state->countries();
            $country       = $country_state->getCountry( $addr['billing_country'] );

            if ( ! empty( $countries[ $addr['billing_country'] ] ) ) {
                $addr['billing_country'] = $countries[ $addr['billing_country'] ];
            }

            if ( ! empty( $country[6][ $addr['billing_state'] ] ) ) {
                $addr['billing_state'] = $country[6][ $addr['billing_state'] ];
            }

            if ( array_key_exists( 'billing_country', $addr ) ) {
                foreach ( $addr as $key => $val ) {
                    unset( $addr[ $key ] );
                    $addr[ str_replace( 'billing_', '', $key ) ] = $val;
                }
            }

            foreach ( $addr as $key => $value ) {
                if ( ! empty( $addr_options[ $key ] ) && 'hidden' === $addr_options[ $key ] ) {
                    continue;
                }

                $inv_to_addr[] = $value;
            }
        }

        $inv_title        = wpuf_get_option( 'set_title', 'wpuf_payment_invoices' );
        $inv_para         = wpuf_get_option( 'set_paragraph', 'wpuf_payment_invoices' );
        $inv_foot         = wpuf_get_option( 'set_footernote', 'wpuf_payment_invoices' );
        $inv_filename     = wpuf_get_option( 'set_filename', 'wpuf_payment_invoices' );
        $inv_u_id         = $data['user_id'];
        $inv_status       = $data['status'];
        $inv_subtotal     = $data['subtotal'];
        $inv_cost         = $data['cost'];
        $inv_pack         = $data['pack_id'];
        $inv_u_fname      = $data['payer_first_name'];
        $inv_u_lname      = $data['payer_last_name'];
        $inv_u_email      = $data['payer_email'];
        $inv_payment_type = $data['payment_type'];
        $inv_id           = isset( $data['transaction_id'] ) ? $data['transaction_id'] : 1;
        $inv_dt           = $data['created'];
        $inv_dt           = new \DateTime( $inv_dt );
        $inv_date         = $inv_dt->format( 'Y-m-d' );

        $currency         = wpuf_get_option( 'currency', 'wpuf_payment', 'USD' );

        $invoice          = new \invoicr( 'A4', $currency, 'en' );

        $invoice->setNumberFormat( '.', ',' );

        $inv_logo = $this->is_invoice_image_exists( $inv_logo ) ? $inv_logo : WPUF_PRO_ROOT . '/lib/invoicr/req/dummy_logo.jpg';


        if ( $inv_logo ) {
            $invoice->setLogo( $inv_logo, 100, 88 );
        }

        $post_id = ! empty( $data['post_id'] ) ? intval( $data['post_id'] ) : $inv_pack;

        $post      = get_post( $post_id );
        $item_name = mb_strimwidth( $post->post_title, 0, 20, '...' );

        if ( 'post' === $post->post_type ) {
            $item_name = sprintf( __( 'Payment for post submission', 'wpuf-pro' ) . ' (%s)', $item_name );
        }

        $tax_amount = $this->wpuf_current_tax_rate();
        $invoice->setColor( $inv_color );
        $invoice->setType( __( 'Invoice', 'wpuf-pro' ) );
        $invoice->setReference( $inv_id );
        $invoice->setDate( $inv_date );
        $invoice->setFrom( $inv_from_addr );
        $invoice->setTo( $inv_to_addr );
        $invoice->addItem( $item_name, false, $inv_subtotal, $tax_amount . '%', $inv_cost, false, $inv_subtotal );
        $invoice->addTotal( __( 'Total', 'wpuf-pro' ), $inv_subtotal );
        $invoice->addTotal( __( 'Payment Type', 'wpuf-pro' ), $inv_payment_type );
        $invoice->addTotal( __( 'Total due', 'wpuf-pro' ), $inv_subtotal, true );
        $invoice->addBadge( $inv_status );
        $invoice->addTitle( $inv_title );
        $invoice->addParagraph( $inv_para );
        $invoice->setFooternote( $inv_foot );

        $inv_dir = WP_CONTENT_DIR . '/uploads/wpuf-invoices/';

        if ( ! file_exists( $inv_dir ) ) {
            mkdir( $inv_dir, 0777, true );
        }

        $pdf_file = $inv_dir . "{$inv_u_id}_{$inv_filename}_{$inv_id}.pdf";

        if ( ! $pdf_file ) {
            $pdf_file = $inv_u_id . 'invoice.pdf';
        }

        $dl_link = content_url() . '/uploads/wpuf-invoices/' . "{$inv_u_id}_{$inv_filename}_{$inv_id}.pdf";

        update_user_meta( $inv_u_id, '_invoice_link' . $inv_id, $dl_link );

        global $pagenow;

        if ( 'on' === $enable_invoices ) {
            if ( $pagenow === 'profile.php' || $pagenow === 'user-edit.php' ) {
                $invoice->render( $pdf_file, 'F' );
                $assign_noti = ( get_user_meta( $inv_u_id, '_pack_assign_notification', true ) === 'true' ) ? true : false;

                if ( $assign_noti ) {
                    $this->send_invoice( $pdf_file, $inv_u_email, $data );
                }
            } else {
                $invoice->render( $pdf_file, 'F' );
                $this->send_invoice( $pdf_file, $inv_u_email, $data );
            }
        }
    }

    public function enable_sub_noti_email( $user_id ) {
        $checked = ( get_user_meta( $user_id, '_pack_assign_notification', true ) === 'true' ) ? 'checked' : '';
        ?>
        <table>
            <tr>
            <td><label style="margin-left: 15px;">Send invoice to mail</label></td>
            <td><input type="hidden" name="wpuf_profile_mail_noti" value="false"></td>
            <td><input type="checkbox" name="wpuf_profile_mail_noti" value="true" <?php echo $checked; ?> style="margin-left: 20px;"></td>
            </tr>
        </table>
        <?php
    }

    public function send_invoice( $pdf_file, $inv_u_email, $data = [] ) {
        if ( ! file_exists( $pdf_file ) ) {
            return false;
        }

        $attach     = [];
        $to         = $inv_u_email;
        $subj       = wpuf_get_option( 'set_mail_sub', 'wpuf_payment_invoices' );
        $text_body  = wpuf_get_option( 'set_mail_body', 'wpuf_payment_invoices' );
        $send_attachment = wpuf_get_option( 'send_attachment', 'wpuf_payment_invoices', 'on' );

        if ( $subj === '' ) {
            $subj = 'Invoice for your payment';
        }

        if ( $text_body === '' ) {
            $text_body = "Dear Subscriber,\r\nPlease, check attachment for the invoice of your transaction.";
        }

        // Replace placeholders if data is provided
        if ( ! empty( $data ) ) {
            $subj = $this->replace_email_placeholders( $subj, $data );
            $text_body = $this->replace_email_placeholders( $text_body, $data );
        }

        $headers  = "MIME-Version: 1.0\r\n";
        $headers .= 'From: ' . get_bloginfo( 'name' ) . ' <' . get_bloginfo( 'admin_email' ) . ">\r\n";
        $headers .= 'Content-Type: text/html; charset=UTF-8' . "\r\n";

        // Only attach PDF if send_attachment is enabled
        $attach = ( wpuf_is_checkbox_or_toggle_on( $send_attachment ) ) ? [ $pdf_file ] : [];

        // Format email body with proper HTML structure
        $mail_body = get_formatted_mail_body( $text_body, $subj );

        wp_mail( $to, $subj, $mail_body, $headers, $attach );

        //unlink( $pdf_file );

    }

    /**
     * Replace email placeholders with actual values
     *
     * @since 4.1.7
     *
     * @param string $content The email content with placeholders
     * @param array $data The payment data
     *
     * @return string The content with placeholders replaced
     */
    private function replace_email_placeholders( $content, $data ) {
        if ( empty( $data ) || empty( $content ) ) {
            return $content;
        }

        // Get user information
        $user_id = isset( $data['user_id'] ) ? $data['user_id'] : 0;
        if ( $user_id ) {
            $user = get_userdata( $user_id );
            $username = $user ? $user->user_login : '';
            $user_email = $user ? $user->user_email : '';
            $display_name = $user ? $user->display_name : '';
        } else {
            $username = isset( $data['payer_first_name'] ) ? $data['payer_first_name'] : '';
            $user_email = isset( $data['payer_email'] ) ? $data['payer_email'] : '';
            $display_name = '';
            if ( isset( $data['payer_first_name'] ) && isset( $data['payer_last_name'] ) ) {
                $display_name = $data['payer_first_name'] . ' ' . $data['payer_last_name'];
            }
        }

        // Get payment information
        $invoice_id = isset( $data['transaction_id'] ) ? $data['transaction_id'] : '';
        $payment_amount = isset( $data['cost'] ) ? wpuf_format_price( $data['cost'] ) : '';
        $payment_type = isset( $data['payment_type'] ) ? $data['payment_type'] : '';

        // Define replacements
        $replacements = [
            '{username}'           => $username,
            '{user_email}'         => $user_email,
            '{display_name}'       => $display_name,
            '{invoice_id}'         => $invoice_id,
            '{payment_amount}'     => $payment_amount,
            '{payment_type}'       => $payment_type,
        ];

        // Replace placeholders
        foreach ( $replacements as $placeholder => $value ) {
            $content = str_replace( $placeholder, $value, $content );
        }

        return $content;
    }

    /**
     * Check if invoice image file exists
     *
     * @since 3.4.11
     *
     * @param  string $url The url to the remote image.
     *
     * @return bool  Whether the remote image exists.
     */
    public function is_invoice_image_exists( $url ) {
        $response = wp_remote_head( $url );

        return 200 === wp_remote_retrieve_response_code( $response );
    }
}
