From 4cb4be377482a4b90bded94854a9aaf8dfd22502 Mon Sep 17 00:00:00 2001 From: Alexandre SPANGARO Date: Tue, 11 Mar 2025 03:20:26 +0100 Subject: [PATCH] NEW Supplier orders - Add tags/categories (#33386) * NEW Supplier orders - Add tags/categories * Fix CI * Fix CI --------- Co-authored-by: Laurent Destailleur --- htdocs/categories/class/categorie.class.php | 167 +++++++++--------- htdocs/categories/viewcat.php | 95 +++++++++- htdocs/core/class/html.form.class.php | 103 +++++++++++ htdocs/core/menus/standard/eldy.lib.php | 6 + htdocs/core/modules/modCategorie.class.php | 37 +++- .../class/fournisseur.commande.class.php | 29 +++ htdocs/fourn/commande/card.php | 103 ++++++++--- htdocs/langs/en_US/categories.lang | 4 + 8 files changed, 437 insertions(+), 107 deletions(-) diff --git a/htdocs/categories/class/categorie.class.php b/htdocs/categories/class/categorie.class.php index ca01e2935fb..9d3e7c0d627 100644 --- a/htdocs/categories/class/categorie.class.php +++ b/htdocs/categories/class/categorie.class.php @@ -14,6 +14,7 @@ * Copyright (C) 2022-2023 Solution Libre SAS * Copyright (C) 2023-2024 Benjamin Falière * Copyright (C) 2024 MDW + * Copyright (C) 2025 Alexandre Spangaro * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -49,23 +50,25 @@ require_once DOL_DOCUMENT_ROOT.'/knowledgemanagement/class/knowledgerecord.class class Categorie extends CommonObject { // Categories types (we use string because we want to accept any modules/types in a future) - const TYPE_PRODUCT = 'product'; - const TYPE_SUPPLIER = 'supplier'; - const TYPE_CUSTOMER = 'customer'; - const TYPE_MEMBER = 'member'; - const TYPE_CONTACT = 'contact'; - const TYPE_USER = 'user'; - const TYPE_PROJECT = 'project'; - const TYPE_ACCOUNT = 'bank_account'; - const TYPE_BANK_LINE = 'bank_line'; - const TYPE_WAREHOUSE = 'warehouse'; - const TYPE_ACTIONCOMM = 'actioncomm'; - const TYPE_WEBSITE_PAGE = 'website_page'; - const TYPE_TICKET = 'ticket'; - const TYPE_KNOWLEDGEMANAGEMENT = 'knowledgemanagement'; - const TYPE_FICHINTER = 'fichinter'; - const TYPE_ORDER = 'order'; - const TYPE_INVOICE = 'invoice'; + const TYPE_PRODUCT = 'product'; + const TYPE_SUPPLIER = 'supplier'; + const TYPE_CUSTOMER = 'customer'; + const TYPE_MEMBER = 'member'; + const TYPE_CONTACT = 'contact'; + const TYPE_USER = 'user'; + const TYPE_PROJECT = 'project'; + const TYPE_ACCOUNT = 'bank_account'; + const TYPE_BANK_LINE = 'bank_line'; + const TYPE_WAREHOUSE = 'warehouse'; + const TYPE_ACTIONCOMM = 'actioncomm'; + const TYPE_WEBSITE_PAGE = 'website_page'; + const TYPE_TICKET = 'ticket'; + const TYPE_KNOWLEDGEMANAGEMENT = 'knowledgemanagement'; + const TYPE_FICHINTER = 'fichinter'; + const TYPE_ORDER = 'order'; + const TYPE_INVOICE = 'invoice'; + const TYPE_SUPPLIER_ORDER = 'supplier_order'; + /** * @var string String with name of icon for myobject. Must be the part after the 'object_' into object_myobject.png @@ -77,23 +80,24 @@ class Categorie extends CommonObject * @var array Table of mapping between type string and ID used for field 'type' in table llx_categories */ public $MAP_ID = array( - 'product' => 0, - 'supplier' => 1, - 'customer' => 2, - 'member' => 3, - 'contact' => 4, - 'bank_account' => 5, - 'project' => 6, - 'user' => 7, - 'bank_line' => 8, - 'warehouse' => 9, - 'actioncomm' => 10, - 'website_page' => 11, - 'ticket' => 12, - 'knowledgemanagement' => 13, - 'fichinter' => 14, - 'order' => 16, - 'invoice' => 17, + 'product' => 0, + 'supplier' => 1, + 'customer' => 2, + 'member' => 3, + 'contact' => 4, + 'bank_account' => 5, + 'project' => 6, + 'user' => 7, + 'bank_line' => 8, + 'warehouse' => 9, + 'actioncomm' => 10, + 'website_page' => 11, + 'ticket' => 12, + 'knowledgemanagement' => 13, + 'fichinter' => 14, + 'order' => 16, + 'invoice' => 17, + 'supplier_order' => 20 ); /** @@ -119,6 +123,7 @@ class Categorie extends CommonObject 14 => 'fichinter', 16 => 'order', 17 => 'invoice', + 20 => 'supplier_order' ); /** @@ -150,23 +155,24 @@ class Categorie extends CommonObject * @note Move to const array when PHP 5.6 will be our minimum target */ public $MAP_OBJ_CLASS = array( - 'product' => 'Product', - 'customer' => 'Societe', - 'supplier' => 'Fournisseur', - 'member' => 'Adherent', - 'contact' => 'Contact', - 'user' => 'User', - 'account' => 'Account', // old for bank account - 'bank_account' => 'Account', - 'project' => 'Project', - 'warehouse' => 'Entrepot', - 'actioncomm' => 'ActionComm', - 'website_page' => 'WebsitePage', - 'ticket' => 'Ticket', - 'knowledgemanagement' => 'KnowledgeRecord', - 'fichinter' => 'Fichinter', - 'order' => 'Commande', - 'invoice' => 'Facture' + 'product' => 'Product', + 'customer' => 'Societe', + 'supplier' => 'Fournisseur', + 'member' => 'Adherent', + 'contact' => 'Contact', + 'user' => 'User', + 'account' => 'Account', // old for bank account + 'bank_account' => 'Account', + 'project' => 'Project', + 'warehouse' => 'Entrepot', + 'actioncomm' => 'ActionComm', + 'website_page' => 'WebsitePage', + 'ticket' => 'Ticket', + 'knowledgemanagement' => 'KnowledgeRecord', + 'fichinter' => 'Fichinter', + 'order' => 'Commande', + 'invoice' => 'Facture', + 'supplier_order' => 'CommandeFournisseur' ); /** @@ -175,23 +181,24 @@ class Categorie extends CommonObject * @note Move to const array when PHP 5.6 will be our minimum target */ public static $MAP_TYPE_TITLE_AREA = array( - 'product' => 'ProductsCategoriesArea', - 'customer' => 'CustomersCategoriesArea', - 'supplier' => 'SuppliersCategoriesArea', - 'member' => 'MembersCategoriesArea', - 'contact' => 'ContactsCategoriesArea', - 'user' => 'UsersCategoriesArea', - 'account' => 'AccountsCategoriesArea', // old for bank account - 'bank_account' => 'AccountsCategoriesArea', - 'project' => 'ProjectsCategoriesArea', - 'warehouse' => 'StocksCategoriesArea', - 'actioncomm' => 'ActioncommCategoriesArea', - 'website_page' => 'WebsitePagesCategoriesArea', - 'ticket' => 'TicketsCategoriesArea', - 'knowledgemanagement' => 'KnowledgemanagementsCategoriesArea', - 'fichinter' => 'FichintersCategoriesArea', - 'order' => 'OrderCategoriesArea', - 'invoice' => 'InvoiceCategoriesArea' + 'product' => 'ProductsCategoriesArea', + 'customer' => 'CustomersCategoriesArea', + 'supplier' => 'SuppliersCategoriesArea', + 'member' => 'MembersCategoriesArea', + 'contact' => 'ContactsCategoriesArea', + 'user' => 'UsersCategoriesArea', + 'account' => 'AccountsCategoriesArea', // old for bank account + 'bank_account' => 'AccountsCategoriesArea', + 'project' => 'ProjectsCategoriesArea', + 'warehouse' => 'StocksCategoriesArea', + 'actioncomm' => 'ActioncommCategoriesArea', + 'website_page' => 'WebsitePagesCategoriesArea', + 'ticket' => 'TicketsCategoriesArea', + 'knowledgemanagement' => 'KnowledgemanagementsCategoriesArea', + 'fichinter' => 'FichintersCategoriesArea', + 'order' => 'OrderCategoriesArea', + 'invoice' => 'InvoicesCategoriesArea', + 'supplier_order' => 'SuppliersOrdersCategoriesArea' ); /** @@ -199,17 +206,18 @@ class Categorie extends CommonObject * This array may be completed by external modules with hook "constructCategory" */ public $MAP_OBJ_TABLE = array( - 'customer' => 'societe', - 'supplier' => 'societe', - 'member' => 'adherent', - 'contact' => 'socpeople', - 'account' => 'bank_account', // old for bank account - 'project' => 'projet', - 'warehouse' => 'entrepot', - 'knowledgemanagement' => 'knowledgemanagement_knowledgerecord', - 'fichinter' => 'fichinter', - 'order' => 'commande', - 'invoice' => 'facture' + 'customer' => 'societe', + 'supplier' => 'societe', + 'member' => 'adherent', + 'contact' => 'socpeople', + 'account' => 'bank_account', // old for bank account + 'project' => 'projet', + 'warehouse' => 'entrepot', + 'knowledgemanagement' => 'knowledgemanagement_knowledgerecord', + 'fichinter' => 'fichinter', + 'order' => 'commande', + 'invoice' => 'facture', + 'supplier_order' => 'commande_fournisseur' ); /** @@ -276,6 +284,7 @@ class Categorie extends CommonObject * @see Categorie::TYPE_FICHINTER * @see Categorie::TYPE_ORDER * @see Categorie::TYPE_INVOICE + * @see Categorie::TYPE_SUPPLIER_ORDER */ public $type; diff --git a/htdocs/categories/viewcat.php b/htdocs/categories/viewcat.php index aeb42e48008..78c14a62f94 100644 --- a/htdocs/categories/viewcat.php +++ b/htdocs/categories/viewcat.php @@ -182,6 +182,11 @@ if ($id > 0 && $removeelem > 0 && $action == 'unlink') { // Test on permission n $tmpobject = new Facture($db); $result = $tmpobject->fetch($removeelem); $elementtype = 'invoice'; + } elseif ($type == Categorie::TYPE_SUPPLIER_ORDER && $user->hasRight('fournisseur', 'commande', 'creer')) { + require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.commande.class.php'; + $tmpobject = new CommandeFournisseur($db); + $result = $tmpobject->fetch($removeelem); + $elementtype = 'invoice'; } else { dol_print_error(null, "Not supported value of type = ".$type); } @@ -257,6 +262,10 @@ if ($elemid && $action == 'addintocategory') { // Test on permission not require require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php'; $newobject = new Facture($db); $elementtype = 'invoice'; + } elseif ($type == Categorie::TYPE_SUPPLIER_ORDER && $user->hasRight('fournisseur', 'commande', 'creer')) { + require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.commande.class.php'; + $newobject = new CommandeFournisseur($db); + $elementtype = 'order_supplier'; } else { dol_print_error(null, "Not supported value of type = ".$type); } @@ -1473,7 +1482,7 @@ if ($type == Categorie::TYPE_ORDER) { // @phan-suppress-next-line PhanPluginSuspiciousParamOrder print_barre_liste($langs->trans("Orders"), $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, 'bill', 0, $newcardbutton, '', $limit); - print "\n"; + print "
\n"; print ''."\n"; if (count($objects) > 0) { @@ -1485,7 +1494,7 @@ if ($type == Categorie::TYPE_ORDER) { } print "\t".''."\n"; - print '\n"; print '\n"; @@ -1551,7 +1560,7 @@ if ($type == Categorie::TYPE_INVOICE) { // @phan-suppress-next-line PhanPluginSuspiciousParamOrder print_barre_liste($langs->trans("BillsCustomers"), $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, 'bill', 0, $newcardbutton, '', $limit); - print "
'.$langs->trans("Ref").'
'; + print ''; print $order->getNomUrl(1); print "'.$order->ref."
\n"; + print "
\n"; print ''."\n"; if (count($objects) > 0) { @@ -1563,7 +1572,7 @@ if ($type == Categorie::TYPE_INVOICE) { } print "\t".''."\n"; - print '\n"; print '\n"; @@ -1586,6 +1595,84 @@ if ($type == Categorie::TYPE_INVOICE) { } } +// List of Supplier Orders +if ($type == Categorie::TYPE_SUPPLIER_ORDER) { + require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.commande.class.php'; + + $permission = $user->rights->fournisseur->commande->creer; + + $objects = $object->getObjectsInCateg($type, 0, $limit, $offset); + if ($objects < 0) { + dol_print_error($db, $object->error, $object->errors); + } else { + // Form to add record into a category + $showclassifyform = $user->hasRight('fournisseur', 'commande', 'creer');; + if ($showclassifyform) { + print '
'; + print ''; + print ''; + print ''; + print ''; + print ''; + print ''; + print '
'.$langs->trans("Ref").'
'; + print ''; print $invoice->getNomUrl(1); print "'.$invoice->ref."
'; + print ''; + print ''; + print '
'; + print $langs->trans("AddSupplierOrderIntoCategory").'  '; + $form->selectSupplierOrder('', 'elemid'); + print '
'; + print ''; + } + + print '
'; + print ''; + print ''; + print ''; + print ''; + print ''; + + print '
'; + $param = '&limit='.$limit.'&id='.$id.'&type='.$type; $num = count($objects); $nbtotalofrecords = ''; $newcardbutton = ''; + + // @phan-suppress-next-line PhanPluginSuspiciousParamOrder + print_barre_liste($langs->trans("SuppliersOrders"), $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, 'supplier_order', 0, $newcardbutton, '', $limit); + + print "\n"; + print ''."\n"; + + if (count($objects) > 0) { + $i = 0; + foreach ($objects as $key => $supplier_order) { + $i++; + if ($i > $limit) { + break; + } + + print "\t".''."\n"; + print '\n"; + print '\n"; + // Link to delete from category + print '\n"; + } + } else { + print ''; + } + print "
'.$langs->trans("Ref").'
'; + print $supplier_order->getNomUrl(1); + print "'.$supplier_order->ref."'; + if ($permission) { + print ""; + print $langs->trans("DeleteFromCat"); + print img_picto($langs->trans("DeleteFromCat"), 'unlink', '', 0, 0, 0, '', 'paddingleft'); + print ""; + } + print "
'.$langs->trans("ThisCategoryHasNoItems").'
\n"; + + print '
'."\n"; + } +} + // Note that $action and $object may have been modified by some hooks $parameters = array('type' => $type, 'id' => $id, 'label' => $label); $reshook = $hookmanager->executeHooks('addMoreCategoriesList', $parameters, $object, $action); diff --git a/htdocs/core/class/html.form.class.php b/htdocs/core/class/html.form.class.php index 5360bac4c93..7f2c8de8bcd 100644 --- a/htdocs/core/class/html.form.class.php +++ b/htdocs/core/class/html.form.class.php @@ -11387,6 +11387,109 @@ class Form } } + /** + * Output a combo list with supplier orders qualified for a third party + * + * @param string $selected Id supplier order preselected + * @param string $htmlname Name of HTML select + * @param int $maxlength Maximum length of label + * @param int $option_only Return only html options lines without the select tag + * @param string $show_empty Add an empty line ('1' or string to show for empty line) + * @param int $discard_closed Discard closed projects (0=Keep,1=hide completely,2=Disable) + * @param int $forcefocus Force focus on field (works with javascript only) + * @param int $disabled Disabled + * @param string $morecss More css added to the select component + * + * @return int Nbr of project if OK, <0 if KO + */ + public function selectSupplierOrder($selected = '', $htmlname = 'supplierorderid', $maxlength = 24, $option_only = 0, $show_empty = '1', $discard_closed = 0, $forcefocus = 0, $disabled = 0, $morecss = 'maxwidth500') + { + global $user, $conf, $langs; + + $out = ''; + + $hideunselectables = false; + if (getDolGlobalString('SUPPLIER_ORDER_HIDE_UNSELECTABLES')) { + $hideunselectables = true; + } + + // Search all supplier orders + $sql = "SELECT cf.rowid, cf.ref"; + $sql .= ' FROM '.$this->db->prefix().'commande_fournisseur as cf'; + $sql .= " ORDER BY cf.ref ASC"; + + $resql = $this->db->query($sql); + if ($resql) { + // Use select2 selector + if (!empty($conf->use_javascript_ajax)) { + include_once DOL_DOCUMENT_ROOT.'/core/lib/ajax.lib.php'; + $comboenhancement = ajax_combobox($htmlname, array(), 0, $forcefocus); + $out .= $comboenhancement; + $morecss = 'minwidth200imp maxwidth500'; + } + + if (empty($option_only)) { + $out .= ''; + } + + print $out; + + $this->db->free($resql); + return $num; + } else { + dol_print_error($this->db); + return -1; + } + } + /** * Output the component to make advanced search criteries * diff --git a/htdocs/core/menus/standard/eldy.lib.php b/htdocs/core/menus/standard/eldy.lib.php index 83809e1f850..566205d2724 100644 --- a/htdocs/core/menus/standard/eldy.lib.php +++ b/htdocs/core/menus/standard/eldy.lib.php @@ -1454,6 +1454,12 @@ function get_left_menu_commercial($mainmenu, &$newmenu, $usemenuhider = 1, $left } else { $newmenu->add("/commande/stats/index.php?leftmenu=orders_suppliers&mode=supplier", $langs->trans("Statistics"), 1, $user->hasRight('fournisseur', 'commande', 'lire')); } + + // Categories + if (isModEnabled('category')) { + $langs->load("categories"); + $newmenu->add("/categories/index.php?leftmenu=cat&type=20", $langs->trans("Categories"), 1, $user->hasRight('categorie', 'lire'), '', $mainmenu, 'cat'); + } } // Contrat diff --git a/htdocs/core/modules/modCategorie.class.php b/htdocs/core/modules/modCategorie.class.php index 6a431545860..93dcbd1020f 100644 --- a/htdocs/core/modules/modCategorie.class.php +++ b/htdocs/core/modules/modCategorie.class.php @@ -3,9 +3,10 @@ * Copyright (C) 2005-2014 Laurent Destailleur * Copyright (C) 2012-2016 Juanjo Menent * Copyright (C) 2020 Stéphane Lesage - * Copyright (C) 2022-2023 Solution Libre SAS + * Copyright (C) 2022-2025 Solution Libre SAS * Copyright (C) 2024 MDW * Copyright (C) 2025 Frédéric France + * Copyright (C) 2025 Alexandre Spangaro * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -173,6 +174,9 @@ class modCategorie extends DolibarrModules if (isModEnabled('invoice')) { $typeexample .= ($typeexample ? " / " : "")."17=Invoice"; } + if ((isModEnabled('fournisseur') && !getDolGlobalString('MAIN_USE_NEW_SUPPLIERMOD')) || (isModEnabled('supplier_order'))) { + $typeexample .= ($typeexample ? " / " : "")."20=Supplier order"; + } // Definition of vars $this->export_fields_array[$r] = array('cat.rowid' => "CategId", 'cat.label' => "Label", 'cat.type' => "Type", 'cat.description' => "Description", 'cat.fk_parent' => "ParentCategoryID", 'pcat.label' => "ParentCategoryLabel", 'cat.color' => "Color", 'cat.date_creation' => "DateCreation", 'cat.tms' => "DateLastModification"); @@ -513,6 +517,23 @@ class modCategorie extends DolibarrModules ); } + // 20 Supplier order + if ((isModEnabled('fournisseur') && !getDolGlobalString('MAIN_USE_NEW_SUPPLIERMOD')) || (isModEnabled('supplier_order'))) { + ++$r; + $this->exportTagLinks( + $r, + 'supplier_order', + 'CommandeFournisseur', + '(isModEnabled("fournisseur") && !getDolGlobalString("MAIN_USE_NEW_SUPPLIERMOD")) || (isModEnabled("supplier_order"))', + ['fournisseur', 'commande', 'export'], + [ + 'rowid' => [ + 'name' => 'SupplierOrderID', + 'type' => 'Numeric' + ] + ] + ); + } // Imports //-------- @@ -530,7 +551,7 @@ class modCategorie extends DolibarrModules 'ca.label' => "Label*", 'ca.type' => "Type*", 'ca.description' => "Description", 'ca.fk_parent' => 'ParentCategory' ); - $this->import_regex_array[$r] = array('ca.type' => '^(0|1|2|3|4|5|6|7|8|9|10|11|16|17)$'); + $this->import_regex_array[$r] = array('ca.type' => '^(0|1|2|3|4|5|6|7|8|9|10|11|16|17|20)$'); $this->import_convertvalue_array[$r] = array( 'ca.fk_parent' => array( 'rule' => 'fetchidfromcodeandlabel', @@ -724,6 +745,18 @@ class modCategorie extends DolibarrModules 'Facture' ); } + + // 20 Supplier order + if ((isModEnabled('fournisseur') && !getDolGlobalString('MAIN_USE_NEW_SUPPLIERMOD')) || (isModEnabled('supplier_order'))) { + ++$r; + $this->importTagLinks( + $r, + 'supplier_order', + '/fourn/class/fournisseur.commande.class.php', + 'CommandeFournisseur', + 'CommandeFournisseur' + ); + } } /** diff --git a/htdocs/fourn/class/fournisseur.commande.class.php b/htdocs/fourn/class/fournisseur.commande.class.php index 8db0e2e7a82..e3e7124f374 100644 --- a/htdocs/fourn/class/fournisseur.commande.class.php +++ b/htdocs/fourn/class/fournisseur.commande.class.php @@ -2467,6 +2467,18 @@ class CommandeFournisseur extends CommonOrder } } + // Remove linked categories. + if (!$error) { + $sql = "DELETE FROM ".MAIN_DB_PREFIX."categorie_supplier_order"; + $sql .= " WHERE fk_order = ".((int) $this->id); + + $result = $this->db->query($sql); + if (!$result) { + $error++; + $this->errors[] = $this->db->lasterror(); + } + } + $main = $this->db->prefix().'commande_fournisseurdet'; if (!$error) { @@ -2969,6 +2981,23 @@ class CommandeFournisseur extends CommonOrder } } + /** + * Sets object to given categories. + * + * Adds it to non existing supplied categories. + * Deletes object from existing categories not supplied. + * Existing categories are left untouch. + * + * @param int[]|int $categories Category ID or array of Categories IDs + * + * @return int Return integer <0 if KO, >0 if OK + */ + public function setCategories($categories) + { + require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php'; + return parent::setCategoriesCommon($categories, Categorie::TYPE_SUPPLIER_ORDER); + } + /** * Update line * diff --git a/htdocs/fourn/commande/card.php b/htdocs/fourn/commande/card.php index 380224402da..766641934c2 100644 --- a/htdocs/fourn/commande/card.php +++ b/htdocs/fourn/commande/card.php @@ -1,33 +1,33 @@ - * Copyright (C) 2004-2015 Laurent Destailleur - * Copyright (C) 2005 Eric Seigne - * Copyright (C) 2005-2016 Regis Houssin - * Copyright (C) 2010-2015 Juanjo Menent - * Copyright (C) 2011-2022 Philippe Grand - * Copyright (C) 2012-2016 Marcos García - * Copyright (C) 2013 Florian Henry - * Copyright (C) 2014 Ion Agorria - * Copyright (C) 2018-2025 Frédéric France - * Copyright (C) 2022 Gauthier VERDOL - * Copyright (C) 2022 Charlene Benke - * Copyright (C) 2023 Joachim Kueter - * Copyright (C) 2024-2025 MDW - * Copyright (C) 2024 Nick Fragoulis +/* Copyright (C) 2004-2006 Rodolphe Quiedeville + * Copyright (C) 2004-2015 Laurent Destailleur + * Copyright (C) 2005 Eric Seigne + * Copyright (C) 2005-2016 Regis Houssin + * Copyright (C) 2010-2015 Juanjo Menent + * Copyright (C) 2011-2022 Philippe Grand + * Copyright (C) 2012-2016 Marcos García + * Copyright (C) 2013 Florian Henry + * Copyright (C) 2014 Ion Agorria + * Copyright (C) 2018-2025 Frédéric France + * Copyright (C) 2022 Gauthier VERDOL + * Copyright (C) 2022 Charlene Benke + * Copyright (C) 2023 Joachim Kueter + * Copyright (C) 2024-2025 MDW + * Copyright (C) 2024 Nick Fragoulis + * Copyright (C) 2025 Alexandre Spangaro * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * (at your option) any later version. * - * This program is distributed in the hope that it will be useful, + * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . - * or see https://www.gnu.org/ */ /** @@ -39,6 +39,7 @@ // Load Dolibarr environment require '../../main.inc.php'; +require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php'; require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php'; require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php'; require_once DOL_DOCUMENT_ROOT.'/core/class/html.formorder.class.php'; @@ -286,6 +287,14 @@ if (empty($reshook)) { } } + // Set tags + if ($action == 'settags' && isModEnabled('category') && $usercancreate) { + $result = $object->setCategories(GETPOST('categories', 'array')); + if ($result < 0) { + setEventMessages($object->error, $object->errors, 'errors'); + } + } + // Edit Thirdparty if (getDolGlobalString('MAIN_CAN_EDIT_SUPPLIER_ON_SUPPLIER_ORDER') && $action == 'set_thirdparty' && $usercancreate && $object->status == CommandeFournisseur::STATUS_DRAFT) { $new_socid = GETPOSTINT('new_socid'); @@ -1539,6 +1548,13 @@ if (empty($reshook)) { } } + if (isModEnabled('category')) { + $categories = GETPOST('categories', 'array'); + if (method_exists($object, 'setCategories')) { + $object->setCategories($categories); + } + } + if ($error) { $langs->load("errors"); $db->rollback(); @@ -1875,6 +1891,15 @@ if ($action == 'create') { print ''; } + // Categories + if (isModEnabled("category")) { + print ''.$langs->trans("Categories").''; + $cate_arbo = $form->select_all_categories(Categorie::TYPE_SUPPLIER_ORDER, '', 'parent', 64, 0, 1); + $arrayselected = GETPOST('categories', 'array'); + print img_picto('', 'category').$form->multiselectarray('categories', $cate_arbo, $arrayselected, 0, 0, 'quatrevingtpercent widthcentpercentminusx', 0, 0); + print ""; + } + print ''.$langs->trans('NotePublic').''; print ''; $doleditor = new DolEditor('note_public', isset($note_public) ? $note_public : GETPOST('note_public', 'restricthtml'), '', 80, 'dolibarr_notes', 'In', false, false, !getDolGlobalString('FCKEDITOR_ENABLE_NOTE_PUBLIC') ? 0 : 1, ROWS_3, '90%'); @@ -2384,6 +2409,40 @@ if ($action == 'create') { print ''; } + // Tags-Categories + if (isModEnabled('category')) { + print ''; + print '
'; + print $langs->trans("Categories"); + print ''; + if ($usercancreate) { + print ''.img_edit().''; + } else { + print ' '; + } + print '
'; + print ''; + print ''; + $cate_arbo = $form->select_all_categories(Categorie::TYPE_SUPPLIER_ORDER, '', 'parent', 64, 0, 1); + if ($action == 'edittags') { + print '
'; + print ''; + print ''; + $c = new Categorie($db); + $cats = $c->containing($object->id, Categorie::TYPE_SUPPLIER_ORDER); + $arrayselected=[]; + foreach ($cats as $cat) { + $arrayselected[] = $cat->id; + } + print img_picto('', 'category').$form->multiselectarray('categories', $cate_arbo, $arrayselected, 0, 0, 'quatrevingtpercent widthcentpercentminusx', 0, '0'); + print ''; + print '
'; + } else { + print $form->showCategories($object->id, Categorie::TYPE_SUPPLIER_ORDER, 1); + } + print ""; + } + // Other attributes include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php'; diff --git a/htdocs/langs/en_US/categories.lang b/htdocs/langs/en_US/categories.lang index d5a1d27cf16..7fbd047a400 100644 --- a/htdocs/langs/en_US/categories.lang +++ b/htdocs/langs/en_US/categories.lang @@ -17,6 +17,8 @@ ContactsCategoriesArea=Contact tags/categories area AccountsCategoriesArea=Bank account tags/categories area ProjectsCategoriesArea=Project tags/categories area UsersCategoriesArea=User tags/categories area +InvoicesCategoriesArea=Invoice tags/categories area +SuppliersOrdersCategoriesArea=Supplier order tags/categories area Bank_linesCategoriesArea==Bank lines tags/categories area SubCats=Sub-categories CatList=List of tags/categories @@ -80,6 +82,7 @@ CatProjectsList=List of projects tags/categories CatUsersList=List of users tags/categories CatOrdersLinks=Links between orders and tags/categories CatInvoicesLinks=Links between invoices and tags/categories +CatSupplierOrdersLinks=Links between supplier orders and tags/categories CatSupLinks=Links between vendors and tags/categories CatCusLinks=Links between customers/prospects and tags/categories CatContactsLinks=Links between contacts/addresses and tags/categories @@ -98,6 +101,7 @@ AddSupplierIntoCategory=Assign the category to the supplier AddFichinterIntoCategory=Assign the category to the intervention AddOrderIntoCategory=Assign the category to the order AddInvoiceIntoCategory=Assign the category to the invoice +AddSupplierOrderIntoCategory=Assign the category to the supplier order AssignCategoryTo=Assign the category to ShowCategory=Show tag/category ByDefaultInList=By default in list