diff --git a/app/Abstracts/View/Components/Transaction.php b/app/Abstracts/View/Components/Transaction.php
new file mode 100644
index 000000000..4174533cc
--- /dev/null
+++ b/app/Abstracts/View/Components/Transaction.php
@@ -0,0 +1,175 @@
+ $alias . 'general.' . $default_key,
+ 'prefix' => $alias . $prefix . '.' . $default_key,
+ 'config_general' => $alias . 'general.' . $config_key,
+ 'config_prefix' => $alias . $prefix . '.' . $config_key,
+ ];
+
+ switch ($trans_type) {
+ case 'trans':
+ foreach ($translations as $trans) {
+ if (trans($trans) !== $trans) {
+ return $trans;
+ }
+ }
+
+ break;
+ case 'trans_choice':
+ foreach ($translations as $trans_choice) {
+ if (trans_choice($trans_choice, 1) !== $trans_choice) {
+ return $trans_choice;
+ }
+ }
+
+ break;
+ }
+
+ return $translation;
+ }
+
+ public function getRouteFromConfig($type, $config_key, $config_parameters = [])
+ {
+ $route = '';
+
+ // if set config trasnlation config_key
+ if ($route = config('type.' . $type . '.route.' . $config_key)) {
+ return $route;
+ }
+
+ $alias = config('type.' . $type . '.alias');
+ $prefix = config('type.' . $type . '.route.prefix');
+
+ // if use module set module alias
+ if (!empty($alias)) {
+ $route .= $alias . '.';
+ }
+
+ if (!empty($prefix)) {
+ $route .= $prefix . '.';
+ }
+
+ $route .= $config_key;
+
+ try {
+ route($route, $config_parameters);
+ } catch (\Exception $e) {
+ try {
+ $route = Str::plural($type, 2) . '.' . $config_key;
+
+ route($route, $config_parameters);
+ } catch (\Exception $e) {
+ $route = '';
+ }
+ }
+
+ return $route;
+ }
+
+ public function getPermissionFromConfig($type, $config_key)
+ {
+ $permission = '';
+
+ // if set config trasnlation config_key
+ if ($permission = config('type.' . $type . '.permission.' . $config_key)) {
+ return $permission;
+ }
+
+ $alias = config('type.' . $type . '.alias');
+ $group = config('type.' . $type . '.group');
+ $prefix = config('type.' . $type . '.permission.prefix');
+
+ $permission = $config_key . '-';
+
+ // if use module set module alias
+ if (!empty($alias)) {
+ $permission .= $alias . '-';
+ }
+
+ // if controller in folder it must
+ if (!empty($group)) {
+ $permission .= $group . '-';
+ }
+
+ $permission .= $prefix;
+
+ return $permission;
+ }
+
+ public function getHideFromConfig($type, $config_key)
+ {
+ $hide = false;
+
+ $hides = config('type.' . $type . '.hide');
+
+ if (!empty($hides) && (in_array($config_key, $hides))) {
+ $hide = true;
+ }
+
+ return $hide;
+ }
+
+ public function getClassFromConfig($type, $config_key)
+ {
+ $class_key = 'type.' . $type . '.class.' . $config_key;
+
+ return config($class_key, '');
+ }
+
+ public function getCategoryFromConfig($type)
+ {
+ $category_type = '';
+
+ // if set config trasnlation config_key
+ if ($category_type = config('type.' . $type . '.category_type')) {
+ return $category_type;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $category_type = 'expense';
+ break;
+ case 'item':
+ $category_type = 'item';
+ break;
+ case 'other':
+ $category_type = 'other';
+ break;
+ case 'transfer':
+ $category_type = 'transfer';
+ break;
+ default:
+ $category_type = 'income';
+ break;
+ }
+
+ return $category_type;
+ }
+}
diff --git a/app/Abstracts/View/Components/TransactionShow.php b/app/Abstracts/View/Components/TransactionShow.php
new file mode 100644
index 000000000..9b2403845
--- /dev/null
+++ b/app/Abstracts/View/Components/TransactionShow.php
@@ -0,0 +1,1243 @@
+type = $type;
+ $this->transaction = $transaction;
+ $this->transactionTemplate = $this->getTransactionTemplate($type, $transactionTemplate);
+ $this->logo = $this->getLogo($logo);
+ $this->payment_methods = ($payment_methods) ?: Modules::getPaymentMethods('all');
+ $this->date_format = $this->getCompanyDateFormat();
+
+ // Navbar Hide
+ $this->hideButtonAddNew = $hideButtonAddNew;
+ $this->hideButtonMoreActions = $hideButtonMoreActions;
+ $this->hideButtonEdit = $hideButtonEdit;
+ $this->hideButtonDuplicate = $hideButtonDuplicate;
+ $this->hideButtonPrint = $hideButtonPrint;
+ $this->hideButtonShare = $hideButtonShare;
+ $this->hideButtonEmail = $hideButtonEmail;
+ $this->hideButtonPdf = $hideButtonPdf;
+ $this->hideButtonDelete = $hideButtonDelete;
+ $this->checkButtonReconciled = $checkButtonReconciled;
+ $this->hideButtonGroupDivider1 = $hideButtonGroupDivider1;
+ $this->hideButtonGroupDivider2 = $hideButtonGroupDivider2;
+ $this->hideButtonGroupDivider3 = $hideButtonGroupDivider3;
+
+ // Navbar Permission
+ $this->permissionCreate = $this->getPermissionCreate($type, $permissionCreate);
+ $this->permissionUpdate = $this->getPermissionUpdate($type, $permissionUpdate);
+ $this->permissionDelete = $this->getPermissionDelete($type, $permissionDelete);
+
+ // Navbar route
+ $this->routeButtonAddNew = $this->getRouteButtonAddNew($type, $routeButtonAddNew);
+ $this->routeButtonEdit = $this->getRouteButtonEdit($type, $routeButtonEdit);
+ $this->routeButtonDuplicate = $this->getRouteButtonDuplicate($type, $routeButtonDuplicate);
+ $this->routeButtonPrint = $this->getRouteButtonPrint($type, $routeButtonPrint);
+ $this->signedUrl = $this->getSignedUrl($type, $signedUrl);
+ $this->routeButtonEmail = $this->getRouteButtonEmail($type, $routeButtonEmail);
+ $this->routeButtonPdf = $this->getRouteButtonPdf($type, $routeButtonPdf);
+ $this->routeButtonDelete = $this->getRouteButtonDelete($type, $routeButtonDelete);
+
+ // Navbar Text
+ $this->textDeleteModal = $textDeleteModal;
+
+ // Header Hide
+ $this->hideHeader = $hideHeader;
+
+ $this->hideHeaderAccount = $hideHeaderAccount;
+ $this->hideHeaderCategory = $hideHeaderCategory;
+ $this->hideHeaderContact = $hideHeaderContact;
+ $this->hideHeaderCategory = $hideHeaderCategory;
+ $this->hideHeaderAmount = $hideHeaderAmount;
+ $this->hideHeaderPaidAt = $hideHeaderPaidAt;
+
+ // Header Text
+ $this->textHeaderAccount = $this->getTextHeaderAccount($type, $textHeaderAccount);
+ $this->textHeaderCategory = $this->getTextHeaderCategory($type, $textHeaderCategory);
+ $this->textHeaderContact = $this->getTextHeaderContact($type, $textHeaderContact);
+ $this->textHeaderAmount = $this->getTextHeaderAmount($type, $textHeaderAmount);
+ $this->textHeaderPaidAt = $this->gettextHeaderPaidAt($type, $textHeaderPaidAt);
+
+ // Header Class
+ $this->classHeaderAccount = $this->getclassHeaderAccount($type, $classHeaderAccount);
+ $this->classHeaderContact = $this->getClassHeaderContact($type, $classHeaderContact);
+ $this->classHeaderCategory = $this->getClassHeaderCategory($type, $classHeaderCategory);
+ $this->classHeaderAmount = $this->getClassHeaderAmount($type, $classHeaderAmount);
+ $this->classHeaderPaidAt = $this->getclassHeaderPaidAt($type, $classHeaderPaidAt);
+
+ // Hide Attachment
+ $this->hideAttachment = $hideAttachment;
+
+ // Company Information Hide checker
+ $this->hideCompany = $hideCompany;
+ $this->hideCompanyLogo = $hideCompanyLogo;
+ $this->hideCompanyDetails = $hideCompanyDetails;
+ $this->hideCompanyName = $hideCompanyName;
+ $this->hideCompanyAddress = $hideCompanyAddress;
+ $this->hideCompanyTaxNumber = $hideCompanyTaxNumber;
+ $this->hideCompanyPhone = $hideCompanyPhone;
+ $this->hideCompanyEmail = $hideCompanyEmail;
+
+ // Transaction Information Hide checker
+ $this->hideContentTitle = $hideContentTitle;
+ $this->hidePaidAt = $hidePaidAt;
+ $this->hideAccount = $hideAccount;
+ $this->hideCategory = $hideCategory;
+ $this->hidePaymentMethods = $hidePaymentMethods;
+ $this->hideReference = $hideReference;
+ $this->hideDescription = $hideDescription;
+ $this->hideAmount = $hideAmount;
+
+ // Transaction Information Text
+ $this->textContentTitle = $this->getTextContentTitle($type, $textContentTitle);
+ $this->textPaidAt = $this->getTextPaidAt($type, $textPaidAt);
+ $this->textAccount = $this->getTextAccount($type, $textAccount);
+ $this->textCategory = $this->getTextCategory($type, $textCategory);
+ $this->textPaymentMethods = $this->getTextPaymentMethods($type, $textPaymentMethods);
+ $this->textReference = $this->getTextReference($type, $textReference);
+ $this->textDescription = $this->getTextDescription($type, $textDescription);
+ $this->textAmount = $this->getTextAmount($type, $textAmount);
+ $this->textPaidBy = $this->getTextPaidBy($type, $textPaidBy);
+
+ // Contact Information Hide checker
+ $this->hideContact = $hideContact;
+ $this->hideContactInfo = $hideContactInfo;
+ $this->hideContactName = $hideContactName;
+ $this->hideContactAddress = $hideContactAddress;
+ $this->hideContactTaxNumber = $hideContactTaxNumber;
+ $this->hideContactPhone = $hideContactPhone;
+ $this->hideContactEmail = $hideContactEmail;
+
+ // Releated Information Hide checker
+ $this->hideReletad = $hideReletad;
+ $this->hideReletadDocumentNumber = $hideReletadDocumentNumber;
+ $this->hideReletadContact = $hideReletadContact;
+ $this->hideReletadDocumentDate = $hideReletadDocumentDate;
+ $this->hideReletadDocumentAmount = $hideReletadDocumentAmount;
+ $this->hideReletadAmount = $hideReletadAmount;
+
+ // Releated Information Text
+ $this->textReleatedTransansaction = $this->getTextReleatedTransansaction($type, $textReleatedTransansaction);
+ $this->textReleatedDocumentNumber = $this->getTextReleatedDocumentNumber($type, $textReleatedDocumentNumber);
+ $this->textReleatedContact = $this->getTextReleatedContact($type, $textReleatedContact);
+ $this->textReleatedDocumentDate = $this->getTextReleatedDocumentDate($type, $textReleatedDocumentDate);
+ $this->textReleatedDocumentAmount = $this->getTextReleatedDocumentAmount($type, $textReleatedDocumentAmount);
+ $this->textReleatedAmount = $this->getTextReleatedAmount($type, $textReleatedAmount);
+
+ $this->routeDocumentShow = $this->routeDocumentShow($type, $routeDocumentShow);
+
+ // Attachment data..
+ $this->attachment = '';
+
+ if (!empty($attachment)) {
+ $this->attachment = $attachment;
+ } else if (!empty($transaction)) {
+ $this->attachment = $transaction->attachment;
+ }
+
+ // Histories Hide
+ $this->hideFooter = $hideFooter;
+ $this->hideFooterHistories = $hideFooterHistories;
+
+ // Histories
+ $this->histories = $this->getHistories($histories);
+ $this->textHistories = $this->getTextHistories($type, $textHistories);
+ $this->classFooterHistories = $this->getClassFooterHistories($type, $classFooterHistories);
+ }
+
+ protected function getTransactionTemplate($type, $transactionTemplate)
+ {
+ if (!empty($transactionTemplate)) {
+ return $transactionTemplate;
+ }
+
+ if ($template = config('type.' . $type . 'template', false)) {
+ return $template;
+ }
+
+ if (!empty($alias = config('type.' . $type . '.alias'))) {
+ $type = $alias . '.' . str_replace('-', '_', $type);
+ }
+
+ $transactionTemplate = setting($this->getSettingKey($type, 'template')) ?: 'default';
+
+ return $transactionTemplate;
+ }
+
+ protected function getLogo($logo)
+ {
+ if (!empty($logo)) {
+ return $logo;
+ }
+
+ $media = Media::find(setting('company.logo'));
+
+ if (!empty($media)) {
+ $path = $media->getDiskPath();
+
+ if (Storage::missing($path)) {
+ return $logo;
+ }
+ } else {
+ $path = base_path('public/img/company.png');
+ }
+
+ try {
+ $image = Image::cache(function($image) use ($media, $path) {
+ $width = setting('invoice.logo_size_width');
+ $height = setting('invoice.logo_size_height');
+
+ if ($media) {
+ $image->make(Storage::get($path))->resize($width, $height)->encode();
+ } else {
+ $image->make($path)->resize($width, $height)->encode();
+ }
+ });
+ } catch (NotReadableException | \Exception $e) {
+ Log::info('Company ID: ' . company_id() . ' components/transactionshow.php exception.');
+ Log::info($e->getMessage());
+
+ $path = base_path('public/img/company.png');
+
+ $image = Image::cache(function($image) use ($path) {
+ $width = setting('invoice.logo_size_width');
+ $height = setting('invoice.logo_size_height');
+
+ $image->make($path)->resize($width, $height)->encode();
+ });
+ }
+
+ if (empty($image)) {
+ return $logo;
+ }
+
+ $extension = File::extension($path);
+
+ return 'data:image/' . $extension . ';base64,' . base64_encode($image);
+ }
+
+ protected function getRouteButtonAddNew($type, $routeButtonAddNew)
+ {
+ if (!empty($routeButtonAddNew)) {
+ return $routeButtonAddNew;
+ }
+
+ $route = $this->getRouteFromConfig($type, 'create');
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.create';
+ }
+
+ protected function getRouteButtonEdit($type, $routeButtonEdit)
+ {
+ if (!empty($routeButtonEdit)) {
+ return $routeButtonEdit;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($type, 'edit', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.edit';
+ }
+
+ protected function getRouteButtonDuplicate($type, $routeButtonDuplicate)
+ {
+ if (!empty($routeButtonDuplicate)) {
+ return $routeButtonDuplicate;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($type, 'duplicate', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.duplicate';
+ }
+
+ protected function getRouteButtonPrint($type, $routeButtonPrint)
+ {
+ if (!empty($routeButtonPrint)) {
+ return $routeButtonPrint;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($type, 'print', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.print';
+ }
+
+ protected function getSignedUrl($type, $signedUrl)
+ {
+ if (!empty($signedUrl)) {
+ return $signedUrl;
+ }
+
+ $page = config('type.' . $type . '.route.prefix');
+ $alias = config('type.' . $type . '.alias');
+
+ $route = '';
+
+ if (!empty($alias)) {
+ $route .= $alias . '.';
+ }
+
+ $route .= 'signed.' . $page . '.show';
+
+ try {
+ route($route, [$this->transaction->id, 'company_id' => company_id()]);
+
+ $signedUrl = URL::signedRoute($route, [$this->transaction->id]);
+ } catch (\Exception $e) {
+ $signedUrl = URL::signedRoute('signed.payments.show', [$this->transaction->id]);
+ }
+
+ return $signedUrl;
+ }
+
+ protected function getRouteButtonEmail($type, $routeButtonEmail)
+ {
+ if (!empty($routeButtonEmail)) {
+ return $routeButtonEmail;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($type, 'email', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.email';
+ }
+
+ protected function getRouteButtonPdf($type, $routeButtonPdf)
+ {
+ if (!empty($routeButtonPdf)) {
+ return $routeButtonPdf;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($type, 'pdf', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.pdf';
+ }
+
+ protected function getRouteButtonDelete($type, $routeButtonDelete)
+ {
+ if (!empty($routeButtonDelete)) {
+ return $routeButtonDelete;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($type, 'destroy', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'revenues.destroy';
+ }
+
+ protected function getPermissionCreate($type, $permissionCreate)
+ {
+ if (!empty($permissionCreate)) {
+ return $permissionCreate;
+ }
+
+ $permissionCreate = $this->getPermissionFromConfig($type, 'create');
+
+ return $permissionCreate;
+ }
+
+ protected function getPermissionUpdate($type, $permissionUpdate)
+ {
+ if (!empty($permissionUpdate)) {
+ return $permissionUpdate;
+ }
+
+ $permissionUpdate = $this->getPermissionFromConfig($type, 'update');
+
+ return $permissionUpdate;
+ }
+
+ protected function getPermissionDelete($type, $permissionDelete)
+ {
+ if (!empty($permissionDelete)) {
+ return $permissionDelete;
+ }
+
+ $permissionDelete = $this->getPermissionFromConfig($type, 'delete');
+
+ return $permissionDelete;
+ }
+
+ protected function getTextHeaderAccount($type, $textHeaderAccount)
+ {
+ if (!empty($textHeaderAccount)) {
+ return $textHeaderAccount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'header_account', 'accounts', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.accounts';
+ }
+
+ protected function getTextHeaderCategory($type, $textHeaderCategory)
+ {
+ if (!empty($textHeaderCategory)) {
+ return $textHeaderCategory;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'header_category', 'categories', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.categories';
+ }
+
+ protected function getTextHeaderContact($type, $textHeaderContact)
+ {
+ if (!empty($textHeaderContact)) {
+ return $textHeaderContact;
+ }
+
+ $default_key = Str::plural(config('type.' . $type . '.contact_type'), 2);
+
+ $translation = $this->getTextFromConfig($type, 'header_contact', $default_key, 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.customers';
+ }
+
+ protected function getTextHeaderAmount($type, $textHeaderAmount)
+ {
+ if (!empty($textHeaderAmount)) {
+ return $textHeaderAmount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'header_amount', 'amount');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function getTextHeaderPaidAt($type, $textHeaderPaidAt)
+ {
+ if (!empty($textHeaderPaidAt)) {
+ return $textHeaderPaidAt;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'header_paid_at', 'date');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.date';
+ }
+
+ protected function getClassHeaderAccount($type, $classHeaderAccount)
+ {
+ if (!empty($classHeaderAccount)) {
+ return $classHeaderAccount;
+ }
+
+ $class = $this->getClassFromConfig($type, 'header_account');
+
+ if (!empty($class)) {
+ return $class;
+ }
+
+ return 'col-4 col-lg-3';
+ }
+
+ protected function getClassHeaderContact($type, $classHeaderContact)
+ {
+ if (!empty($classHeaderContact)) {
+ return $classHeaderContact;
+ }
+
+ $class = $this->getClassFromConfig($type, 'header_contact');
+
+ if (!empty($class)) {
+ return $class;
+ }
+
+ return 'col-4 col-lg-2';
+ }
+
+ protected function getClassHeaderCategory($type, $classHeaderCategory)
+ {
+ if (!empty($classHeaderCategory)) {
+ return $classHeaderCategory;
+ }
+
+ $class = $this->getClassFromConfig($type, 'header_category');
+
+ if (!empty($class)) {
+ return $class;
+ }
+
+ return 'col-4 col-lg-3';
+ }
+
+ protected function getClassHeaderAmount($type, $classHeaderAmount)
+ {
+ if (!empty($classHeaderAmount)) {
+ return $classHeaderAmount;
+ }
+
+ $class = $this->getClassFromConfig($type, 'header_amount');
+
+ if (!empty($class)) {
+ return $class;
+ }
+
+ return 'col-4 col-lg-2';
+ }
+
+ protected function getClassHeaderPaidAt($type, $classHeaderPaidAt)
+ {
+ if (!empty($classHeaderPaidAt)) {
+ return $classHeaderPaidAt;
+ }
+
+ $class = $this->getClassFromConfig($type, 'header_paid_at');
+
+ if (!empty($class)) {
+ return $class;
+ }
+
+ return 'col-4 col-lg-2';
+ }
+
+ protected function getTextContentTitle($type, $textContentTitle)
+ {
+ if (!empty($textContentTitle)) {
+ return $textContentTitle;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'payment_made';
+ break;
+ default:
+ $default_key = 'revenue_received';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, $type . '_made', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'revenues.revenue_received';
+ }
+
+ protected function getTextPaidAt($type, $textPaidAt)
+ {
+ if (!empty($textPaidAt)) {
+ return $textPaidAt;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'paid_at', 'date');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.date';
+ }
+
+ protected function getTextAccount($type, $textAccount)
+ {
+ if (!empty($textAccount)) {
+ return $textAccount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'accounts', 'accounts', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.accounts';
+ }
+
+ protected function getTextCategory($type, $textCategory)
+ {
+ if (!empty($textCategory)) {
+ return $textCategory;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'categories', 'categories', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.categories';
+ }
+
+ protected function getTextPaymentMethods($type, $textPaymentMethods)
+ {
+ if (!empty($textPaymentMethods)) {
+ return $textPaymentMethods;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'payment_methods', 'payment_methods', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.payment_methods';
+ }
+
+ protected function getTextReference($type, $textReference)
+ {
+ if (!empty($textReference)) {
+ return $textReference;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'reference', 'reference');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.reference';
+ }
+
+ protected function getTextDescription($type, $textDescription)
+ {
+ if (!empty($textDescription)) {
+ return $textDescription;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'description', 'description');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.description';
+ }
+
+ protected function getTextAmount($type, $textAmount)
+ {
+ if (!empty($textAmount)) {
+ return $textAmount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'amount', 'amount');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function getTextPaidBy($type, $textPaidBy)
+ {
+ if (!empty($textPaidBy)) {
+ return $textPaidBy;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'paid_to';
+ break;
+ default:
+ $default_key = 'paid_by';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'paid_to_by', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'revenus.paid_by';
+ }
+
+ protected function getTextReleatedTransansaction($type, $textReleatedTransansaction)
+ {
+ if (!empty($textReleatedTransansaction)) {
+ return $textReleatedTransansaction;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'related_bill';
+ break;
+ default:
+ $default_key = 'related_invoice';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_type', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'revenues.related_invoice';
+ }
+
+ protected function getTextReleatedDocumentNumber($type, $textReleatedDocumentNumber)
+ {
+ if (!empty($textReleatedDocumentNumber)) {
+ return $textReleatedDocumentNumber;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_document_number', 'numbers');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.numbers';
+ }
+
+ protected function getTextReleatedContact($type, $textReleatedContact)
+ {
+ if (!empty($textReleatedContact)) {
+ return $textReleatedContact;
+ }
+
+ $default_key = Str::plural(config('type.' . $type . '.contact_type'), 2);
+
+ $translation = $this->getTextFromConfig($type, 'related_contact', $default_key, 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.customers';
+ }
+
+ protected function getTextReleatedDocumentDate($type, $textReleatedDocumentDate)
+ {
+ if (!empty($textReleatedDocumentDate)) {
+ return $textReleatedDocumentDate;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'bill_date';
+ break;
+ default:
+ $default_key = 'invoice_date';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_document_date', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'invoices.invoice_date';
+ }
+
+ protected function getTextReleatedDocumentAmount($type, $textReleatedDocumentAmount)
+ {
+ if (!empty($textReleatedDocumentAmount)) {
+ return $textReleatedDocumentAmount;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'bill_amount';
+ break;
+ default:
+ $default_key = 'invoice_amount';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_document_amount', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function getTextReleatedAmount($type, $textReleatedAmount)
+ {
+ if (!empty($textReleatedAmount)) {
+ return $textReleatedAmount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_amount', 'amount');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function routeDocumentShow($type, $routeDocumentShow)
+ {
+ if (!empty($routeDocumentShow)) {
+ return $routeDocumentShow;
+ }
+
+ if (!$this->transaction->document) {
+ return $routeDocumentShow;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($this->transaction->document->type, 'show', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'invoices.show';
+ }
+
+ protected function getHistories($histories)
+ {
+ if (!empty($histories)) {
+ return $histories;
+ }
+
+ $histories[] = $this->transaction;
+
+ return $histories;
+ }
+
+ protected function getTextHistories($type, $textHistories)
+ {
+ if (!empty($textHistories)) {
+ return $textHistories;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'histories', 'histories');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'invoices.histories';
+ }
+
+ protected function getClassFooterHistories($type, $classFooterHistories)
+ {
+ if (!empty($classFooterHistories)) {
+ return $classFooterHistories;
+ }
+
+ $class = $this->getClassFromConfig($type, 'footer_histories');
+
+ if (!empty($class)) {
+ return $class;
+ }
+
+ return 'col-sm-6 col-md-6 col-lg-6 col-xl-6';
+ }
+}
\ No newline at end of file
diff --git a/app/Abstracts/View/Components/TransactionTemplate.php b/app/Abstracts/View/Components/TransactionTemplate.php
new file mode 100644
index 000000000..91f9ba5eb
--- /dev/null
+++ b/app/Abstracts/View/Components/TransactionTemplate.php
@@ -0,0 +1,606 @@
+type = $type;
+ $this->transaction = $transaction;
+
+ $this->logo = $this->getLogo($logo);
+ $this->payment_methods = ($payment_methods) ?: Modules::getPaymentMethods('all');
+
+ // Company Information Hide checker
+ $this->hideCompany = $hideCompany;
+ $this->hideCompanyLogo = $hideCompanyLogo;
+ $this->hideCompanyDetails = $hideCompanyDetails;
+ $this->hideCompanyName = $hideCompanyName;
+ $this->hideCompanyAddress = $hideCompanyAddress;
+ $this->hideCompanyTaxNumber = $hideCompanyTaxNumber;
+ $this->hideCompanyPhone = $hideCompanyPhone;
+ $this->hideCompanyEmail = $hideCompanyEmail;
+
+ // Transaction Information Hide checker
+ $this->hideContentTitle = $hideContentTitle;
+ $this->hidePaidAt = $hidePaidAt;
+ $this->hideAccount = $hideAccount;
+ $this->hideCategory = $hideCategory;
+ $this->hidePaymentMethods = $hidePaymentMethods;
+ $this->hideReference = $hideReference;
+ $this->hideDescription = $hideDescription;
+ $this->hideAmount = $hideAmount;
+
+ // Transaction Information Text
+ $this->textContentTitle = $this->getTextContentTitle($type, $textContentTitle);
+ $this->textPaidAt = $this->getTextPaidAt($type, $textPaidAt);
+ $this->textAccount = $this->getTextAccount($type, $textAccount);
+ $this->textCategory = $this->getTextCategory($type, $textCategory);
+ $this->textPaymentMethods = $this->getTextPaymentMethods($type, $textPaymentMethods);
+ $this->textReference = $this->getTextReference($type, $textReference);
+ $this->textDescription = $this->getTextDescription($type, $textDescription);
+ $this->textAmount = $this->getTextAmount($type, $textAmount);
+ $this->textPaidBy = $this->getTextPaidBy($type, $textPaidBy);
+
+ // Contact Information Hide checker
+ $this->hideContact = $hideContact;
+ $this->hideContactInfo = $hideContactInfo;
+ $this->hideContactName = $hideContactName;
+ $this->hideContactAddress = $hideContactAddress;
+ $this->hideContactTaxNumber = $hideContactTaxNumber;
+ $this->hideContactPhone = $hideContactPhone;
+ $this->hideContactEmail = $hideContactEmail;
+
+ // Releated Information Hide checker
+ $this->hideReletad = $hideReletad;
+ $this->hideReletadDocumentNumber = $hideReletadDocumentNumber;
+ $this->hideReletadContact = $hideReletadContact;
+ $this->hideReletadDocumentDate = $hideReletadDocumentDate;
+ $this->hideReletadDocumentAmount = $hideReletadDocumentAmount;
+ $this->hideReletadAmount = $hideReletadAmount;
+
+ // Releated Information Text
+ $this->textReleatedTransansaction = $this->getTextReleatedTransansaction($type, $textReleatedTransansaction);
+ $this->textReleatedDocumentNumber = $this->getTextReleatedDocumentNumber($type, $textReleatedDocumentNumber);
+ $this->textReleatedContact = $this->getTextReleatedContact($type, $textReleatedContact);
+ $this->textReleatedDocumentDate = $this->getTextReleatedDocumentDate($type, $textReleatedDocumentDate);
+ $this->textReleatedDocumentAmount = $this->getTextReleatedDocumentAmount($type, $textReleatedDocumentAmount);
+ $this->textReleatedAmount = $this->getTextReleatedAmount($type, $textReleatedAmount);
+
+ $this->routeDocumentShow = $this->routeDocumentShow($type, $routeDocumentShow);
+ }
+
+ protected function getLogo($logo)
+ {
+ if (!empty($logo)) {
+ return $logo;
+ }
+
+ $media = Media::find(setting('company.logo'));
+
+ if (!empty($media)) {
+ $path = $media->getDiskPath();
+
+ if (Storage::missing($path)) {
+ return $logo;
+ }
+ } else {
+ $path = base_path('public/img/company.png');
+ }
+
+ try {
+ $image = Image::cache(function($image) use ($media, $path) {
+ $width = setting('invoice.logo_size_width');
+ $height = setting('invoice.logo_size_height');
+
+ if ($media) {
+ $image->make(Storage::get($path))->resize($width, $height)->encode();
+ } else {
+ $image->make($path)->resize($width, $height)->encode();
+ }
+ });
+ } catch (NotReadableException | \Exception $e) {
+ Log::info('Company ID: ' . company_id() . ' components/transactionshow.php exception.');
+ Log::info($e->getMessage());
+
+ $path = base_path('public/img/company.png');
+
+ $image = Image::cache(function($image) use ($path) {
+ $width = setting('invoice.logo_size_width');
+ $height = setting('invoice.logo_size_height');
+
+ $image->make($path)->resize($width, $height)->encode();
+ });
+ }
+
+ if (empty($image)) {
+ return $logo;
+ }
+
+ $extension = File::extension($path);
+
+ return 'data:image/' . $extension . ';base64,' . base64_encode($image);
+ }
+
+ protected function getTextContentTitle($type, $textContentTitle)
+ {
+ if (!empty($textContentTitle)) {
+ return $textContentTitle;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'payment_made';
+ break;
+ default:
+ $default_key = 'revenue_received';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, $type . '_made', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'revenues.revenue_received';
+ }
+
+ protected function getTextPaidAt($type, $textPaidAt)
+ {
+ if (!empty($textPaidAt)) {
+ return $textPaidAt;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'paid_at', 'date');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.date';
+ }
+
+ protected function getTextAccount($type, $textAccount)
+ {
+ if (!empty($textAccount)) {
+ return $textAccount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'accounts', 'accounts', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.accounts';
+ }
+
+ protected function getTextCategory($type, $textCategory)
+ {
+ if (!empty($textCategory)) {
+ return $textCategory;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'categories', 'categories', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.categories';
+ }
+
+ protected function getTextPaymentMethods($type, $textPaymentMethods)
+ {
+ if (!empty($textPaymentMethods)) {
+ return $textPaymentMethods;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'payment_methods', 'payment_methods', 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.payment_methods';
+ }
+
+ protected function getTextReference($type, $textReference)
+ {
+ if (!empty($textReference)) {
+ return $textReference;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'reference', 'reference');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.reference';
+ }
+
+ protected function getTextDescription($type, $textDescription)
+ {
+ if (!empty($textDescription)) {
+ return $textDescription;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'description', 'description');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.description';
+ }
+
+ protected function getTextAmount($type, $textAmount)
+ {
+ if (!empty($textAmount)) {
+ return $textAmount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'amount', 'amount');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function getTextPaidBy($type, $textPaidBy)
+ {
+ if (!empty($textPaidBy)) {
+ return $textPaidBy;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'paid_to';
+ break;
+ default:
+ $default_key = 'paid_by';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'paid_to_by', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'revenus.paid_by';
+ }
+
+ protected function getTextReleatedTransansaction($type, $textReleatedTransansaction)
+ {
+ if (!empty($textReleatedTransansaction)) {
+ return $textReleatedTransansaction;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'related_bill';
+ break;
+ default:
+ $default_key = 'related_invoice';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_type', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'revenues.related_invoice';
+ }
+
+ protected function getTextReleatedDocumentNumber($type, $textReleatedDocumentNumber)
+ {
+ if (!empty($textReleatedDocumentNumber)) {
+ return $textReleatedDocumentNumber;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_document_number', 'numbers');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.numbers';
+ }
+
+ protected function getTextReleatedContact($type, $textReleatedContact)
+ {
+ if (!empty($textReleatedContact)) {
+ return $textReleatedContact;
+ }
+
+ $default_key = Str::plural(config('type.' . $type . '.contact_type'), 2);
+
+ $translation = $this->getTextFromConfig($type, 'related_contact', $default_key, 'trans_choice');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.customers';
+ }
+
+ protected function getTextReleatedDocumentDate($type, $textReleatedDocumentDate)
+ {
+ if (!empty($textReleatedDocumentDate)) {
+ return $textReleatedDocumentDate;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'bill_date';
+ break;
+ default:
+ $default_key = 'invoice_date';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_document_date', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'invoices.invoice_date';
+ }
+
+ protected function getTextReleatedDocumentAmount($type, $textReleatedDocumentAmount)
+ {
+ if (!empty($textReleatedDocumentAmount)) {
+ return $textReleatedDocumentAmount;
+ }
+
+ switch ($type) {
+ case 'bill':
+ case 'expense':
+ case 'purchase':
+ $default_key = 'bill_amount';
+ break;
+ default:
+ $default_key = 'invoice_amount';
+ break;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_document_amount', $default_key);
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function getTextReleatedAmount($type, $textReleatedAmount)
+ {
+ if (!empty($textReleatedAmount)) {
+ return $textReleatedAmount;
+ }
+
+ $translation = $this->getTextFromConfig($type, 'related_amount', 'amount');
+
+ if (!empty($translation)) {
+ return $translation;
+ }
+
+ return 'general.amount';
+ }
+
+ protected function routeDocumentShow($type, $routeDocumentShow)
+ {
+ if (!empty($routeDocumentShow)) {
+ return $routeDocumentShow;
+ }
+
+ if (!$this->transaction->document) {
+ return $routeDocumentShow;
+ }
+
+ //example route parameter.
+ $parameter = 1;
+
+ $route = $this->getRouteFromConfig($this->transaction->document->type, 'show', $parameter);
+
+ if (!empty($route)) {
+ return $route;
+ }
+
+ return 'invoices.show';
+ }
+}
diff --git a/app/Events/Transaction/TransactionPrinting.php b/app/Events/Transaction/TransactionPrinting.php
new file mode 100644
index 000000000..602e02f60
--- /dev/null
+++ b/app/Events/Transaction/TransactionPrinting.php
@@ -0,0 +1,22 @@
+transaction = $transaction;
+ }
+}
diff --git a/app/Events/Transaction/TransactionSent.php b/app/Events/Transaction/TransactionSent.php
new file mode 100644
index 000000000..1ab92798e
--- /dev/null
+++ b/app/Events/Transaction/TransactionSent.php
@@ -0,0 +1,20 @@
+transaction = $transaction;
+ }
+}
diff --git a/app/Http/Controllers/Portal/Payments.php b/app/Http/Controllers/Portal/Payments.php
index d9ce57df8..4d3545b58 100644
--- a/app/Http/Controllers/Portal/Payments.php
+++ b/app/Http/Controllers/Portal/Payments.php
@@ -7,9 +7,13 @@ use App\Models\Banking\Transaction;
use App\Models\Setting\Currency;
use App\Http\Requests\Portal\PaymentShow as Request;
use App\Utilities\Modules;
+use App\Traits\Transactions;
+use Illuminate\Support\Facades\URL;
class Payments extends Controller
{
+ use Transactions;
+
/**
* Display a listing of the resource.
*
@@ -51,4 +55,62 @@ class Payments extends Controller
return $this->response('portal.currencies.index', compact('currencies'));
}
+
+ /**
+ * Show the form for viewing the specified resource.
+ *
+ * @param Transaction $payment
+ *
+ * @return Response
+ */
+ public function printPayment(Transaction $payment, Request $request)
+ {
+ event(new \App\Events\Transaction\TransactionPrinting($payment));
+
+ $revenue = $payment;
+ $view = view($payment->template_path, compact('revenue'));
+
+ return mb_convert_encoding($view, 'HTML-ENTITIES', 'UTF-8');
+ }
+
+ /**
+ * Show the form for viewing the specified resource.
+ *
+ * @param Transaction $payment
+ *
+ * @return Response
+ */
+ public function pdfPayment(Transaction $payment, Request $request)
+ {
+ event(new \App\Events\Transaction\TransactionPrinting($payment));
+
+ $currency_style = true;
+
+ $revenue = $payment;
+ $view = view($payment->template_path, compact('revenue', 'currency_style'))->render();
+ $html = mb_convert_encoding($view, 'HTML-ENTITIES', 'UTF-8');
+
+ $pdf = app('dompdf.wrapper');
+ $pdf->loadHTML($html);
+
+ //$pdf->setPaper('A4', 'portrait');
+
+ $file_name = $this->getTransactionFileName($payment);
+
+ return $pdf->download($file_name);
+ }
+
+ public function signed(Transaction $payment)
+ {
+ if (empty($payment)) {
+ return redirect()->route('login');
+ }
+
+ $payment_methods = Modules::getPaymentMethods();
+
+ $print_action = URL::signedRoute('signed.payments.print', [$payment->id]);
+ $pdf_action = URL::signedRoute('signed.payments.pdf', [$payment->id]);
+
+ return view('portal.payments.signed', compact('payment', 'payment_methods', 'print_action', 'pdf_action'));
+ }
}
diff --git a/app/Http/Controllers/Purchases/Payments.php b/app/Http/Controllers/Purchases/Payments.php
index c46880d32..f03bc37e0 100644
--- a/app/Http/Controllers/Purchases/Payments.php
+++ b/app/Http/Controllers/Purchases/Payments.php
@@ -17,11 +17,12 @@ use App\Models\Setting\Category;
use App\Models\Setting\Currency;
use App\Traits\Currencies;
use App\Traits\DateTime;
+use App\Traits\Transactions;
use App\Utilities\Modules;
class Payments extends Controller
{
- use Currencies, DateTime;
+ use Currencies, DateTime, Transactions;
/**
* Display a listing of the resource.
@@ -40,9 +41,9 @@ class Payments extends Controller
*
* @return Response
*/
- public function show()
+ public function show(Transaction $payment)
{
- return redirect()->route('payments.index');
+ return view('purchases.payments.show', compact('payment'));
}
/**
@@ -91,7 +92,7 @@ class Payments extends Controller
$response = $this->ajaxDispatch(new CreateTransaction($request));
if ($response['success']) {
- $response['redirect'] = route('payments.index');
+ $response['redirect'] = route('payments.show', $response['data']->id);
$message = trans('messages.success.added', ['type' => trans_choice('general.payments', 1)]);
@@ -206,7 +207,7 @@ class Payments extends Controller
$response = $this->ajaxDispatch(new UpdateTransaction($payment, $request));
if ($response['success']) {
- $response['redirect'] = route('payments.index');
+ $response['redirect'] = route('payments.show', $payment->id);
$message = trans('messages.success.updated', ['type' => trans_choice('general.payments', 1)]);
@@ -257,4 +258,69 @@ class Payments extends Controller
{
return $this->exportExcel(new Export, trans_choice('general.payments', 2));
}
+
+ /**
+ * Download the PDF file of payment.
+ *
+ * @param Transaction $payment
+ *
+ * @return Response
+ */
+ public function emailPayment(Transaction $payment)
+ {
+ if (empty($payment->contact->email)) {
+ return redirect()->back();
+ }
+
+ // Notify the customer
+ $payment->contact->notify(new Notification($payment, 'payment_new_customer', true));
+
+ event(new \App\Events\Transaction\TransactionSent($payment));
+
+ flash(trans('documents.messages.email_sent', ['type' => trans_choice('general.payments', 1)]))->success();
+
+ return redirect()->back();
+ }
+
+ /**
+ * Print the payment.
+ *
+ * @param Transaction $payment
+ *
+ * @return Response
+ */
+ public function printPayment(Transaction $payment)
+ {
+ event(new \App\Events\Transaction\TransactionPrinting($payment));
+
+ $view = view($payment->template_path, compact('payment'));
+
+ return mb_convert_encoding($view, 'HTML-ENTITIES', 'UTF-8');
+ }
+
+ /**
+ * Download the PDF file of payment.
+ *
+ * @param Transaction $payment
+ *
+ * @return Response
+ */
+ public function pdfPayment(Transaction $payment)
+ {
+ event(new \App\Events\Transaction\TransactionPrinting($payment));
+
+ $currency_style = true;
+
+ $view = view($payment->template_path, compact('payment', 'currency_style'))->render();
+ $html = mb_convert_encoding($view, 'HTML-ENTITIES', 'UTF-8');
+
+ $pdf = app('dompdf.wrapper');
+ $pdf->loadHTML($html);
+
+ //$pdf->setPaper('A4', 'portrait');
+
+ $file_name = $this->getTransactionFileName($payment);
+
+ return $pdf->download($file_name);
+ }
}
diff --git a/app/Http/Controllers/Sales/Revenues.php b/app/Http/Controllers/Sales/Revenues.php
index 10ec8abd0..3b8d01b8d 100644
--- a/app/Http/Controllers/Sales/Revenues.php
+++ b/app/Http/Controllers/Sales/Revenues.php
@@ -15,13 +15,15 @@ use App\Models\Banking\Transaction;
use App\Models\Common\Contact;
use App\Models\Setting\Category;
use App\Models\Setting\Currency;
+use App\Notifications\Sale\Revenue as Notification;
use App\Traits\Currencies;
use App\Traits\DateTime;
+use App\Traits\Transactions;
use App\Utilities\Modules;
class Revenues extends Controller
{
- use Currencies, DateTime;
+ use Currencies, DateTime, Transactions;
/**
* Display a listing of the resource.
@@ -40,9 +42,9 @@ class Revenues extends Controller
*
* @return Response
*/
- public function show()
+ public function show(Transaction $revenue)
{
- return redirect()->route('revenues.index');
+ return view('sales.revenues.show', compact('revenue'));
}
/**
@@ -91,7 +93,7 @@ class Revenues extends Controller
$response = $this->ajaxDispatch(new CreateTransaction($request));
if ($response['success']) {
- $response['redirect'] = route('revenues.index');
+ $response['redirect'] = route('revenues.show', $response['data']->id);
$message = trans('messages.success.added', ['type' => trans_choice('general.revenues', 1)]);
@@ -206,7 +208,7 @@ class Revenues extends Controller
$response = $this->ajaxDispatch(new UpdateTransaction($revenue, $request));
if ($response['success']) {
- $response['redirect'] = route('revenues.index');
+ $response['redirect'] = route('revenues.show', $revenue->id);
$message = trans('messages.success.updated', ['type' => trans_choice('general.revenues', 1)]);
@@ -257,4 +259,69 @@ class Revenues extends Controller
{
return $this->exportExcel(new Export, trans_choice('general.revenues', 2));
}
+
+ /**
+ * Download the PDF file of revenue.
+ *
+ * @param Transaction $revenue
+ *
+ * @return Response
+ */
+ public function emailRevenue(Transaction $revenue)
+ {
+ if (empty($revenue->contact->email)) {
+ return redirect()->back();
+ }
+
+ // Notify the customer
+ $revenue->contact->notify(new Notification($revenue, 'revenue_new_customer', true));
+
+ event(new \App\Events\Transaction\TransactionSent($revenue));
+
+ flash(trans('documents.messages.email_sent', ['type' => trans_choice('general.revenues', 1)]))->success();
+
+ return redirect()->back();
+ }
+
+ /**
+ * Print the revenue.
+ *
+ * @param Transaction $revenue
+ *
+ * @return Response
+ */
+ public function printRevenue(Transaction $revenue)
+ {
+ event(new \App\Events\Transaction\TransactionPrinting($revenue));
+
+ $view = view($revenue->template_path, compact('revenue'));
+
+ return mb_convert_encoding($view, 'HTML-ENTITIES', 'UTF-8');
+ }
+
+ /**
+ * Download the PDF file of revenue.
+ *
+ * @param Transaction $revenue
+ *
+ * @return Response
+ */
+ public function pdfRevenue(Transaction $revenue)
+ {
+ event(new \App\Events\Transaction\TransactionPrinting($revenue));
+
+ $currency_style = true;
+
+ $view = view($revenue->template_path, compact('revenue', 'currency_style'))->render();
+ $html = mb_convert_encoding($view, 'HTML-ENTITIES', 'UTF-8');
+
+ $pdf = app('dompdf.wrapper');
+ $pdf->loadHTML($html);
+
+ //$pdf->setPaper('A4', 'portrait');
+
+ $file_name = $this->getTransactionFileName($revenue);
+
+ return $pdf->download($file_name);
+ }
}
diff --git a/app/Listeners/Update/V21/Version2118.php b/app/Listeners/Update/V21/Version2118.php
new file mode 100644
index 000000000..cf2b808da
--- /dev/null
+++ b/app/Listeners/Update/V21/Version2118.php
@@ -0,0 +1,56 @@
+skipThisUpdate($event)) {
+ return;
+ }
+
+ $this->updateEmailTemplate();
+
+ Artisan::call('migrate', ['--force' => true]);
+ }
+
+ protected function updateCompanies()
+ {
+ $company_id = company_id();
+
+ $companies = Company::cursor();
+
+ foreach ($companies as $company) {
+ $company->makeCurrent();
+
+ EmailTemplate::create([
+ 'company_id' => $company->id,
+ 'alias' => 'revenue_new_customer',
+ 'class' => 'App\Notifications\Sale\Revenue',
+ 'name' => 'settings.email.templates.revenue_new_customer',
+ 'subject' => trans('email_templates.revenue_new_customer.subject'),
+ 'body' => trans('email_templates.revenue_new_customer.body'),
+ ]);
+ }
+
+ company($company_id)->makeCurrent();
+ }
+}
diff --git a/app/Models/Banking/Transaction.php b/app/Models/Banking/Transaction.php
index 9d0fe7f35..89b1f5440 100644
--- a/app/Models/Banking/Transaction.php
+++ b/app/Models/Banking/Transaction.php
@@ -371,11 +371,11 @@ class Transaction extends Model
}
if ($this->isIncome()) {
- return !empty($this->document_id) ? 'invoices.show' : 'revenues.edit';
+ return !empty($this->document_id) ? 'invoices.show' : 'revenues.show';
}
if ($this->isExpense()) {
- return !empty($this->document_id) ? 'bills.show' : 'payments.edit';
+ return !empty($this->document_id) ? 'bills.show' : 'payments.show';
}
return 'transactions.index';
@@ -391,6 +391,11 @@ class Transaction extends Model
return !empty($value) ? $value : (!empty($this->document_id) ? $this->document_id : $this->id);
}
+ public function getTemplatePathAttribute($value = null)
+ {
+ return $value ?: 'sales.revenues.print_default';
+ }
+
/**
* Create a new factory instance for the model.
*
diff --git a/app/Notifications/Sale/Revenue.php b/app/Notifications/Sale/Revenue.php
new file mode 100644
index 000000000..764f5f048
--- /dev/null
+++ b/app/Notifications/Sale/Revenue.php
@@ -0,0 +1,121 @@
+revenue = $revenue;
+ $this->template = EmailTemplate::alias($template_alias)->first();
+ $this->attach_pdf = $attach_pdf;
+ }
+
+ /**
+ * Get the mail representation of the notification.
+ *
+ * @param mixed $notifiable
+ * @return \Illuminate\Notifications\Messages\MailMessage
+ */
+ public function toMail($notifiable)
+ {
+ $message = $this->initMessage();
+
+ // Attach the PDF file
+ if ($this->attach_pdf) {
+ $message->attach($this->storeDocumentPdfAndGetPath($this->revenue), [
+ 'mime' => 'application/pdf',
+ ]);
+ }
+
+ return $message;
+ }
+
+ /**
+ * Get the array representation of the notification.
+ *
+ * @param mixed $notifiable
+ * @return array
+ */
+ public function toArray($notifiable)
+ {
+ return [
+ 'template_alias' => $this->template->alias,
+ 'revenue_id' => $this->revenue->id,
+ 'customer_name' => $this->revenue->contact->name,
+ 'amount' => $this->revenue->amount,
+ 'revenue_date' => company_date($this->revenue->paid_at),
+ ];
+ }
+
+ public function getTags()
+ {
+ return [
+ '{revenue_amount}',
+ '{revenue_date}',
+ '{revenue_guest_link}',
+ '{revenue_admin_link}',
+ '{revenue_portal_link}',
+ '{customer_name}',
+ '{company_name}',
+ '{company_email}',
+ '{company_tax_number}',
+ '{company_phone}',
+ '{company_address}',
+ ];
+ }
+
+ public function getTagsReplacement()
+ {
+ return [
+ money($this->revenue->amount, $this->revenue->currency_code, true),
+ company_date($this->revenue->paid_at),
+ URL::signedRoute('signed.payments.show', [$this->revenue->id]),
+ route('revenues.show', $this->revenue->id),
+ route('portal.payments.show', $this->revenue->id),
+ $this->revenue->contact->name,
+ $this->revenue->company->name,
+ $this->revenue->company->email,
+ $this->revenue->company->tax_number,
+ $this->revenue->company->phone,
+ nl2br(trim($this->revenue->company->address)),
+ ];
+ }
+}
diff --git a/app/Providers/Event.php b/app/Providers/Event.php
index 740d0df4d..772e7662e 100644
--- a/app/Providers/Event.php
+++ b/app/Providers/Event.php
@@ -34,6 +34,7 @@ class Event extends Provider
'App\Listeners\Update\V21\Version2114',
'App\Listeners\Update\V21\Version2116',
'App\Listeners\Update\V21\Version2117',
+ 'App\Listeners\Update\V21\Version2118',
],
'Illuminate\Auth\Events\Login' => [
'App\Listeners\Auth\Login',
diff --git a/app/Traits/Transactions.php b/app/Traits/Transactions.php
index d70e2b22e..8b090871f 100644
--- a/app/Traits/Transactions.php
+++ b/app/Traits/Transactions.php
@@ -2,6 +2,9 @@
namespace App\Traits;
+use App\Models\Banking\Transaction;
+use Illuminate\Support\Str;
+
trait Transactions
{
public function isIncome()
@@ -59,4 +62,30 @@ trait Transactions
'transaction.type.' . $index => implode(',', $types),
])->save();
}
+
+ public function getTransactionFileName(Transaction $transaction, string $separator = '-', string $extension = 'pdf'): string
+ {
+ return $this->getSafeTransactionNumber($transaction, $separator) . $separator . time() . '.' . $extension;
+ }
+
+ public function getSafeTransactionNumber(Transaction $transaction, string $separator = '-'): string
+ {
+ return Str::slug($transaction->id, $separator, language()->getShortCode());
+ }
+
+ protected function getSettingKey($type, $setting_key)
+ {
+ $key = '';
+ $alias = config('type.' . $type . '.alias');
+
+ if (!empty($alias)) {
+ $key .= $alias . '.';
+ }
+
+ $prefix = config('type.' . $type . '.setting.prefix');
+
+ $key .= $prefix . '.' . $setting_key;
+
+ return $key;
+ }
}
diff --git a/app/View/Components/Transactions/Script.php b/app/View/Components/Transactions/Script.php
new file mode 100644
index 000000000..c78ede332
--- /dev/null
+++ b/app/View/Components/Transactions/Script.php
@@ -0,0 +1,55 @@
+type = $type;
+ $this->scriptFile = ($scriptFile) ? $scriptFile : 'public/js/common/documents.js';
+ $this->version = $this->getVersion($version);
+ $this->transaction = $transaction;
+ }
+
+ /**
+ * Get the view / contents that represent the component.
+ *
+ * @return \Illuminate\Contracts\View\View|string
+ */
+ public function render()
+ {
+ return view('components.transactions.script');
+ }
+
+ protected function getVersion($version)
+ {
+ if (!empty($version)) {
+ return $version;
+ }
+
+ if ($alias = config('type.' . $this->type . '.alias')) {
+ return module_version($alias);
+ }
+
+ return version('short');
+ }
+}
diff --git a/app/View/Components/Transactions/Show/Attachment.php b/app/View/Components/Transactions/Show/Attachment.php
new file mode 100644
index 000000000..2e9e2c339
--- /dev/null
+++ b/app/View/Components/Transactions/Show/Attachment.php
@@ -0,0 +1,18 @@
+ [
'group' => 'sales',
+ 'route' => [
+ 'prefix' => 'revenues', // core use with group + prefix, module ex. estimates
+ 'parameter' => 'revenue', // sales/invoices/{parameter}/edit
+ //'create' => 'invoices.create', // if you change route, you can write full path
+ ],
'permission' => [
'prefix' => 'revenues',
//'create' => 'create-sales-revenues',
],
+ 'translation' => [
+ 'prefix' => 'revenues', // this translation file name.
+ 'related_document_amount' => 'invoices.invoice_amount',
+ ],
'contact_type' => 'customer',
],
'expense' => [
'group' => 'purchases',
+ 'route' => [
+ 'prefix' => 'payments', // core use with group + prefix, module ex. estimates
+ 'parameter' => 'payment', // sales/invoices/{parameter}/edit
+ //'create' => 'invoices.create', // if you change route, you can write full path
+ ],
'permission' => [
'prefix' => 'payments',
//'create' => 'create-purchases-payments',
],
+ 'translation' => [
+ 'prefix' => 'payments', // this translation file name.
+ 'related_document_amount' => 'bills.bill_amount',
+ ],
'contact_type' => 'vendor',
],
diff --git a/database/seeds/EmailTemplates.php b/database/seeds/EmailTemplates.php
index 78e74b551..c9eccdebf 100644
--- a/database/seeds/EmailTemplates.php
+++ b/database/seeds/EmailTemplates.php
@@ -72,6 +72,11 @@ class EmailTemplates extends Seeder
'class' => 'App\Notifications\Purchase\Bill',
'name' => 'settings.email.templates.bill_recur_admin',
],
+ [
+ 'alias' => 'revenue_new_customer',
+ 'class' => 'App\Notifications\Sale\Revenue',
+ 'name' => 'settings.email.templates.revenue_new_customer',
+ ],
];
foreach ($templates as $template) {
diff --git a/public/css/custom.css b/public/css/custom.css
index 56769238c..e98c31265 100644
--- a/public/css/custom.css
+++ b/public/css/custom.css
@@ -220,6 +220,22 @@ button:focus {
.mwpx-100 {
max-width: 100px !important;
}
+
+.mwpx-200 {
+ max-width: 200px !important;
+}
+
+.mwpx-300 {
+ max-width: 300px !important;
+}
+
+.mwpx-400 {
+ max-width: 400px !important;
+}
+
+.mwpx-500 {
+ max-width: 500px !important;
+}
/*--------Max Width 100 Pixel Finish--------*/
/*--------Form Group--------*/
diff --git a/public/css/print.css b/public/css/print.css
index fd51ee583..6a610af91 100644
--- a/public/css/print.css
+++ b/public/css/print.css
@@ -249,6 +249,13 @@ th, td
vertical-align: top;
}
+.col-16
+{
+ display: inline-block;
+ max-width: 16%;
+ vertical-align: top;
+}
+
.col-100
{
display: inline-block;
@@ -493,4 +500,57 @@ th, td
display: block;
clear: both;
content: ""
+}
+
+.show-card {
+ padding: 0px 15px;
+ border-radius: 0px;
+ box-shadow: rgb(0 0 0 / 20%) 0px 4px 16px;
+}
+
+.card-amount-badge h5 {
+ font-size: 20px;
+}
+
+.card-amount-badge span {
+ font-size: 32px;
+}
+
+.show-card-body {
+ padding: 1.5rem 2.5rem;
+}
+
+.show-card-bg-success {
+ width: 350px;
+ height: 150px;
+ border-radius: unset;
+}
+.show-company-value strong {
+ font-weight: bold;
+}
+
+.show-company p {
+ min-height: 52px;
+}
+
+@media (max-width: 1200px) {
+ .transaction-head-text {
+ max-width: 100px !important;
+ }
+}
+
+@media (max-width: 991px) {
+ .transaction-head-text {
+ max-width: 75px !important;
+ }
+}
+
+@media (max-width: 575.98px) {
+ .show-card {
+ overflow-y: scroll;
+ }
+
+ .show-card-body {
+ padding: 1.5rem 1.5rem;
+ }
}
\ No newline at end of file
diff --git a/resources/lang/en-GB/bills.php b/resources/lang/en-GB/bills.php
index 0963c31af..34f0494f5 100644
--- a/resources/lang/en-GB/bills.php
+++ b/resources/lang/en-GB/bills.php
@@ -4,6 +4,7 @@ return [
'bill_number' => 'Bill Number',
'bill_date' => 'Bill Date',
+ 'bill_amount' => 'Bill Amount',
'total_price' => 'Total Price',
'due_date' => 'Due Date',
'order_number' => 'Order Number',
diff --git a/resources/lang/en-GB/documents.php b/resources/lang/en-GB/documents.php
index 3de66089e..7aa44b7ba 100644
--- a/resources/lang/en-GB/documents.php
+++ b/resources/lang/en-GB/documents.php
@@ -3,7 +3,7 @@
return [
'edit_columns' => 'Edit Columns',
- 'empty_items' =>'You have not added any items.',
+ 'empty_items' => 'You have not added any items.',
'statuses' => [
'draft' => 'Draft',
diff --git a/resources/lang/en-GB/email_templates.php b/resources/lang/en-GB/email_templates.php
index b0267ad0d..0a4de44c6 100644
--- a/resources/lang/en-GB/email_templates.php
+++ b/resources/lang/en-GB/email_templates.php
@@ -47,4 +47,8 @@ return [
'body' => 'Hello, Based on {vendor_name} recurring circle, {bill_number} bill has been automatically created. You can see the bill details from the following link: {bill_number} . Best Regards, {company_name}',
],
+ 'revenue_new_customer' => [
+ 'subject' => '{revenue_date} payment created',
+ 'body' => 'Dear {customer_name}, We have prepared the following payment. You can see the payment details from the following link: {revenue_date} . Feel free to contact us for any question. Best Regards, {company_name}',
+ ],
];
diff --git a/resources/lang/en-GB/general.php b/resources/lang/en-GB/general.php
index 159e41cd1..08e9778d7 100644
--- a/resources/lang/en-GB/general.php
+++ b/resources/lang/en-GB/general.php
@@ -162,6 +162,7 @@ return [
'due_on' => 'Due on',
'amount_due' => 'Amount due',
'financial_year' => 'Financial Year',
+ 'created' => 'Created',
'card' => [
'cards' => 'Card|Cards',
diff --git a/resources/lang/en-GB/invoices.php b/resources/lang/en-GB/invoices.php
index c5daffdea..0bb50a0f0 100644
--- a/resources/lang/en-GB/invoices.php
+++ b/resources/lang/en-GB/invoices.php
@@ -4,6 +4,7 @@ return [
'invoice_number' => 'Invoice Number',
'invoice_date' => 'Invoice Date',
+ 'invoice_amount' => 'Invoice Amount',
'total_price' => 'Total Price',
'due_date' => 'Due Date',
'order_number' => 'Order Number',
diff --git a/resources/lang/en-GB/payments.php b/resources/lang/en-GB/payments.php
new file mode 100644
index 000000000..cd41d02ae
--- /dev/null
+++ b/resources/lang/en-GB/payments.php
@@ -0,0 +1,9 @@
+ 'Payment Made',
+ 'paid_to' => 'Paid To',
+ 'related_bill' => 'Releated Bill',
+
+];
diff --git a/resources/lang/en-GB/revenues.php b/resources/lang/en-GB/revenues.php
new file mode 100644
index 000000000..f30baace3
--- /dev/null
+++ b/resources/lang/en-GB/revenues.php
@@ -0,0 +1,9 @@
+ 'Revenue Received',
+ 'paid_by' => 'Paid By',
+ 'related_invoice' => 'Releated Invoice',
+
+];
diff --git a/resources/views/components/transactions/script.blade.php b/resources/views/components/transactions/script.blade.php
new file mode 100644
index 000000000..4bb9715dd
--- /dev/null
+++ b/resources/views/components/transactions/script.blade.php
@@ -0,0 +1 @@
+
diff --git a/resources/views/components/transactions/show/attachment.blade.php b/resources/views/components/transactions/show/attachment.blade.php
new file mode 100644
index 000000000..6ab858a27
--- /dev/null
+++ b/resources/views/components/transactions/show/attachment.blade.php
@@ -0,0 +1,9 @@
+@if ($attachment)
+
+ @foreach ($attachment as $file)
+
+ @include('partials.media.file')
+
+ @endforeach
+
+@endif
diff --git a/resources/views/components/transactions/show/content.blade.php b/resources/views/components/transactions/show/content.blade.php
new file mode 100644
index 000000000..a8533ba2c
--- /dev/null
+++ b/resources/views/components/transactions/show/content.blade.php
@@ -0,0 +1,108 @@
+@stack('content_header_start')
+@if (!$hideHeader)
+
+@endif
+@stack('content_header_end')
+
+@stack('transaction_start')
+
+@stack('transaction_end')
+
+@stack('attachment_start')
+ @if (!$hideAttachment)
+
+ @endif
+@stack('attachment_end')
+
+@stack('row_footer_start')
+ @if (!$hideFooter)
+
+ @endif
+@stack('row_footer_end')
+
+{{ Form::hidden('transaction_id', $transaction->id, ['id' => 'transaction_id']) }}
+{{ Form::hidden($type . '_id', $transaction->id, ['id' => $type . '_id']) }}
diff --git a/resources/views/components/transactions/show/footer.blade.php b/resources/views/components/transactions/show/footer.blade.php
new file mode 100644
index 000000000..3bae7fad0
--- /dev/null
+++ b/resources/views/components/transactions/show/footer.blade.php
@@ -0,0 +1,14 @@
+
+ @stack('row_footer_histories_start')
+ @if (!$hideFooterHistories)
+
+ @endif
+ @stack('row_footer_histories_end')
+
diff --git a/resources/views/components/transactions/show/header.blade.php b/resources/views/components/transactions/show/header.blade.php
new file mode 100644
index 000000000..bc31572be
--- /dev/null
+++ b/resources/views/components/transactions/show/header.blade.php
@@ -0,0 +1,81 @@
+
+ @stack('header_account_start')
+ @if (!$hideHeaderAccount)
+
+ @endif
+ @stack('header_account_end')
+
+ @stack('header_category_start')
+ @if (!$hideHeaderCategory)
+
+ @endif
+ @stack('header_category_end')
+
+ @stack('header_contact_start')
+ @if (!$hideHeaderContact)
+
+ @endif
+ @stack('header_contact_end')
+
+ @stack('header_amount_start')
+ @if (!$hideHeaderAmount)
+
+ @endif
+ @stack('header_amount_end')
+
+ @stack('header_paid_at_start')
+ @if (!$hideHeaderPaidAt)
+
+ @endif
+ @stack('header_paid_at_end')
+
\ No newline at end of file
diff --git a/resources/views/components/transactions/show/histories.blade.php b/resources/views/components/transactions/show/histories.blade.php
new file mode 100644
index 000000000..caeab6c96
--- /dev/null
+++ b/resources/views/components/transactions/show/histories.blade.php
@@ -0,0 +1,47 @@
+
+
+
+
+
+
+
+
+ @stack('row_footer_histories_head_tr_start')
+
+ @stack('row_footer_histories_head_start')
+
+ {{ trans('general.date') }}
+
+
+
+ {{ trans('general.created') }}
+
+ @stack('row_footer_histories_head_end')
+
+ @stack('row_footer_histories_head_tr_end')
+
+
+
+ @stack('row_footer_histories_body_tr_start')
+ @foreach($histories as $history)
+
+ @stack('row_footer_histories_body_td_start')
+
+ @date($history->created_at)
+
+
+
+ {{ $history->owner->name }}
+
+ @stack('row_footer_histories_body_td_end')
+
+ @endforeach
+ @stack('row_footer_histories_body_tr_end')
+
+
+
+
+
+
diff --git a/resources/views/components/transactions/show/top-buttons.blade.php b/resources/views/components/transactions/show/top-buttons.blade.php
new file mode 100644
index 000000000..9481840e9
--- /dev/null
+++ b/resources/views/components/transactions/show/top-buttons.blade.php
@@ -0,0 +1,109 @@
+@stack('button_group_start')
+@if (!$hideButtonMoreActions)
+
+@endif
+@stack('button_group_end')
+
+@stack('add_new_button_start')
+@if (!$hideButtonAddNew)
+ @can($permissionCreate)
+
+ {{ trans('general.add_new') }}
+
+ @endcan
+@endif
+@stack('add_new_button_end')
diff --git a/resources/views/components/transactions/show/transaction.blade.php b/resources/views/components/transactions/show/transaction.blade.php
new file mode 100644
index 000000000..1ce1f0d31
--- /dev/null
+++ b/resources/views/components/transactions/show/transaction.blade.php
@@ -0,0 +1,73 @@
+
+
+ @if ($transactionTemplate)
+ @switch($transactionTemplate)
+ @case('classic')
+ @break
+ @case('modern')
+ @break
+ @default
+
+ @endswitch
+ @else
+ @include($transactionTemplate)
+ @endif
+
+
diff --git a/resources/views/components/transactions/template/default.blade.php b/resources/views/components/transactions/template/default.blade.php
new file mode 100644
index 000000000..6deec82a2
--- /dev/null
+++ b/resources/views/components/transactions/template/default.blade.php
@@ -0,0 +1,337 @@
+@stack('company_start')
+@if (!$hideCompany)
+
+
+ @if (!$hideCompanyLogo)
+
+ @stack('company_logo_start')
+ @if (!empty($document->contact->logo) && !empty($document->contact->logo->id))
+
+ @else
+
+ @endif
+ @stack('company_logo_end')
+
+ @endif
+
+ @if (!$hideCompanyDetails)
+
+ @stack('company_details_start')
+ @if (!$hideCompanyName)
+
+ {{ setting('company.name') }}
+
+ @endif
+
+ @if (!$hideCompanyAddress)
+ {!! nl2br(setting('company.address')) !!}
+ @endif
+
+ @if (!$hideCompanyTaxNumber)
+
+ @if (setting('company.tax_number'))
+ {{ trans('general.tax_number') }}: {{ setting('company.tax_number') }}
+ @endif
+
+ @endif
+
+ @if (!$hideCompanyPhone)
+
+ @if (setting('company.phone'))
+ {{ setting('company.phone') }}
+ @endif
+
+ @endif
+
+ @if (!$hideCompanyEmail)
+ {{ setting('company.email') }}
+ @endif
+ @stack('company_details_end')
+
+ @endif
+
+
+@endif
+@stack('company_end')
+
+@if (!$hideContentTitle)
+
+
+
+
+ {{ trans($textContentTitle) }}
+
+
+
+
+@endif
+
+
+
+
+
+ @if (!$hidePaidAt)
+
+
+ {{ trans($textPaidAt) }}:
+
+
+
+ @date($transaction->paid_at)
+
+
+ @endif
+
+ @if (!$hideAccount)
+
+
+ {{ trans_choice($textAccount, 1) }}:
+
+
+
+ {{ $transaction->account->name }}
+
+
+ @endif
+
+ @if (!$hideCategory)
+
+
+ {{ trans_choice($textCategory, 1) }}:
+
+
+
+ {{ $transaction->category->name }}
+
+
+ @endif
+
+ @if (!$hidePaymentMethods)
+
+
+ {{ trans_choice($textPaymentMethods, 1) }}:
+
+
+
+ {{ $payment_methods[$transaction->payment_method] }}
+
+
+ @endif
+
+ @if (!$hideReference)
+
+
+ {{ trans($textReference) }}:
+
+
+
+ {{ $transaction->reference }}
+
+
+ @endif
+
+ @if (!$hideDescription)
+
+
+ {{ trans($textDescription) }}:
+
+
+
+
+ {!! nl2br($transaction->description) !!}
+
+
+
+ @endif
+
+ @if (!$hideContact)
+
+
+
+ {{ trans($textDescription) }}
+
+
+
+
+ @if ($hideContactInfo)
+
+
+ {{ trans($textContactInfo) }}
+
+
+ @endif
+
+ @stack('name_input_start')
+ @if (!$hideContactName)
+
+
+ {{ $transaction->contact->name }}
+
+
+ @endif
+ @stack('name_input_end')
+
+ @stack('address_input_start')
+ @if (!$hideContactAddress)
+
+
+
+ {!! nl2br($transaction->contact->address) !!}
+
+
+
+ @endif
+ @stack('address_input_end')
+
+ @stack('tax_number_input_start')
+ @if (!$hideContactTaxNumber)
+
+
+
+ @if ($transaction->contact->tax_number)
+ {{ trans('general.tax_number') }}: {{ $transaction->contact->tax_number }}
+ @endif
+
+
+
+ @endif
+ @stack('tax_number_input_end')
+
+ @stack('phone_input_start')
+ @if (!$hideContactPhone)
+
+
+
+ @if ($transaction->contact->phone)
+ {{ $transaction->contact->phone }}
+ @endif
+
+
+
+ @endif
+ @stack('phone_input_end')
+
+ @stack('email_start')
+ @if (!$hideContactEmail)
+
+
+
+ {{ $transaction->contact->email }}
+
+
+
+ @endif
+ @stack('email_input_end')
+ @endif
+
+
+
+ @if (!$hideAmount)
+
+
+
+
+
+ {{ trans($textAmount) }}
+
+
+
+ @money($transaction->amount, $transaction->currency_code, true)
+
+
+
+
+
+ @endif
+
+
+
+@if (!$hideReletad)
+ @if ($transaction->document)
+
+
+
+
+
+ {{ trans($textReleatedTransansaction) }}
+
+
+
+
+
+
+
+ @if (!$hideReletadDocumentNumber)
+
+ {{ trans_choice($textReleatedDocumentNumber, 1) }}
+
+ @endif
+
+ @if (!$hideReletadContact)
+
+ {{ trans_choice($textReleatedContact, 1) }}
+
+ @endif
+
+ @if (!$hideReletadDocumentDate)
+
+ {{ trans($textReleatedDocumentDate) }}
+
+ @endif
+
+ @if (!$hideReletadDocumentAmount)
+
+ {{ trans($textReleatedDocumentAmount) }}
+
+ @endif
+
+ @if (!$hideReletadAmount)
+
+ {{ trans($textReleatedAmount) }}
+
+ @endif
+
+
+
+
+
+ @if (!$hideReletadDocumentNumber)
+
+
+ {{ $transaction->document->document_number }}
+
+
+ @endif
+
+ @if (!$hideReletadContact)
+
+ {{ $transaction->document->contact_name }}
+
+ @endif
+
+ @if (!$hideReletadDocumentDate)
+
+ @date($transaction->document->due_at)
+
+ @endif
+
+ @if (!$hideReletadDocumentAmount)
+
+ @money($transaction->document->amount, $transaction->document->currency_code, true)
+
+ @endif
+
+ @if (!$hideReletadAmount)
+
+ @money($transaction->amount, $transaction->currency_code, true)
+
+ @endif
+
+
+
+ @endif
+@endif
\ No newline at end of file
diff --git a/resources/views/portal/invoices/show.blade.php b/resources/views/portal/invoices/show.blade.php
index 5bf83f11c..2403d981e 100644
--- a/resources/views/portal/invoices/show.blade.php
+++ b/resources/views/portal/invoices/show.blade.php
@@ -4,7 +4,7 @@
@section('new_button')
@stack('button_print_start')
-
+
{{ trans('general.print') }}
@stack('button_print_end')
diff --git a/resources/views/portal/payments/show.blade.php b/resources/views/portal/payments/show.blade.php
index 2b542fbf5..536190633 100644
--- a/resources/views/portal/payments/show.blade.php
+++ b/resources/views/portal/payments/show.blade.php
@@ -1,144 +1,39 @@
@extends('layouts.portal')
-@section('title', trans_choice('general.payments', 1))
+@section('title', trans_choice('general.payments', 1) . ': ' . @date($payment->paid_at))
-@section('content')
-
-
+@section('new_button')
+@stack('button_print_start')
+
+ {{ trans('general.print') }}
+
+ @stack('button_print_end')
-
-
-
-
-
- {{ trans('general.from') }}: {{ setting('company.name') }}
-
- {{ trans('general.address') }}: {{ setting('company.address') }}
- {{ trans('general.phone') }}: {{ setting('company.phone') }}
- {{ trans('general.email') }}: {{ setting('company.email') }}
-
-
-
-
-
-
- {{ trans('general.to') }}: {{ $payment->contact->name }}
-
- {{ trans('general.address') }}: {{ $payment->contact->address }}
- {{ trans('general.phone') }}: {{ $payment->contact->phone }}
- {{ trans('general.email') }}: {{ $payment->contact->email }}
-
-
-
-
- @if ($payment->description)
-
{{ trans('general.description') }}
-
{{ $payment->description }}
- @endif
-
-
-
-
-
-
-
-
-
- {{ trans('general.amount') }}
- {{ trans_choice('general.payment_methods', 1) }}
- {{ trans('general.description') }}
-
-
-
-
- @money($payment->amount, $payment->currency_code, true)
- {{ $payment_methods[$payment->payment_method] }}
- {{ $payment->description }}
-
-
-
-
-
-
-
-
-
- @if ($payment->attachment)
-
- @endif
-
+ @stack('button_pdf_start')
+
+ {{ trans('general.download') }}
+
+ @stack('button_pdf_end')
@endsection
-@push('scripts_start')
+@section('content')
+
+
+
+@endsection
+
+@push('footer_start')
+
+
@endpush
diff --git a/resources/views/portal/payments/signed.blade.php b/resources/views/portal/payments/signed.blade.php
new file mode 100644
index 000000000..9039502f6
--- /dev/null
+++ b/resources/views/portal/payments/signed.blade.php
@@ -0,0 +1,46 @@
+@extends('layouts.signed')
+
+@section('title', trans_choice('general.payments', 1) . ': ' . @date($payment->paid_at))
+
+@section('new_button')
+ @stack('button_print_start')
+
+ {{ trans('general.print') }}
+
+ @stack('button_print_end')
+
+ @stack('button_pdf_start')
+
+ {{ trans('general.download') }}
+
+ @stack('button_pdf_end')
+
+ @stack('button_dashboard_start')
+ @if (!user())
+
+ {{ trans('payments.all_payments') }}
+
+ @endif
+ @stack('button_dashboard_end')
+@endsection
+
+@section('content')
+
+
+
+@endsection
+
+@push('footer_start')
+
+
+@endpush
diff --git a/resources/views/purchases/payments/index.blade.php b/resources/views/purchases/payments/index.blade.php
index 702629a79..803aedaef 100644
--- a/resources/views/purchases/payments/index.blade.php
+++ b/resources/views/purchases/payments/index.blade.php
@@ -49,7 +49,7 @@
@if ($item->reconciled)
@date($item->paid_at)
@else
- @date($item->paid_at)
+ @date($item->paid_at)
@endif
@money($item->amount, $item->currency_code, true)
@@ -85,16 +85,20 @@