Merge branch 'develop' of github.com:Dolibarr/dolibarr into 12.0_new_allow_extrafields_on_pdf_extend_to_line_desc
This commit is contained in:
commit
0c2d08cdd9
2
.github/workflows/stale-issues.yml
vendored
2
.github/workflows/stale-issues.yml
vendored
@ -16,7 +16,7 @@ jobs:
|
||||
stale-issue-label: 'Issue Stale (automatic label)'
|
||||
exempt-issue-label: 'Priority High / Blocking'
|
||||
days-before-stale: 365
|
||||
days-before-close: 10
|
||||
days-before-close: 15
|
||||
#stale-pr-message: 'This PR is stale because it has been open 1 year with no activity. If this PR is still mergeable (no conflict, nor Continuous Integration errors), please comment to confirm this merge is still expected. Without comment, this issue will be closed automatically by stale bot in 15 days.'
|
||||
#stale-pr-label: 'PR Stale (automatic label)'
|
||||
#exempt-pr-label: 'Priority Top Strategic'
|
||||
|
||||
@ -75,7 +75,7 @@ if ($id)
|
||||
|
||||
$linkback = '<a href="'.DOL_URL_ROOT.'/adherents/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
|
||||
|
||||
dol_banner_tab($object, 'rowid', $linkback);
|
||||
dol_banner_tab($object, 'id', $linkback);
|
||||
|
||||
print '<div class="fichecenter">';
|
||||
|
||||
|
||||
@ -118,10 +118,10 @@ if (($action == "searchfiles" || $action == "dl")) {
|
||||
$error++;
|
||||
}
|
||||
|
||||
$sql = '';
|
||||
|
||||
if (!$error)
|
||||
{
|
||||
$sql = '';
|
||||
|
||||
$wheretail = " '".$db->idate($date_start)."' AND '".$db->idate($date_stop)."'";
|
||||
|
||||
// Customer invoices
|
||||
@ -178,152 +178,153 @@ if (($action == "searchfiles" || $action == "dl")) {
|
||||
$sql .= " AND t.entity IN (".($entity == 1 ? '0,1' : $entity).')';
|
||||
//$sql.=" AND fk_statut <> ".ChargeSociales::STATUS_DRAFT;
|
||||
}
|
||||
}
|
||||
|
||||
if ($sql) {
|
||||
$sql .= $db->order($sortfield, $sortorder);
|
||||
//print $sql;
|
||||
if ($sql) {
|
||||
$sql .= $db->order($sortfield, $sortorder);
|
||||
//print $sql;
|
||||
|
||||
$resd = $db->query($sql);
|
||||
$files = array();
|
||||
$link = '';
|
||||
$resd = $db->query($sql);
|
||||
$files = array();
|
||||
$link = '';
|
||||
|
||||
if ($resd)
|
||||
{
|
||||
$numd = $db->num_rows($resd);
|
||||
if ($resd)
|
||||
{
|
||||
$numd = $db->num_rows($resd);
|
||||
|
||||
$tmpinvoice = new Facture($db);
|
||||
$tmpinvoicesupplier = new FactureFournisseur($db);
|
||||
$tmpdonation = new Don($db);
|
||||
$tmpinvoice = new Facture($db);
|
||||
$tmpinvoicesupplier = new FactureFournisseur($db);
|
||||
$tmpdonation = new Don($db);
|
||||
|
||||
$upload_dir = '';
|
||||
$i = 0;
|
||||
while ($i < $numd)
|
||||
{
|
||||
$objd = $db->fetch_object($resd);
|
||||
$upload_dir = '';
|
||||
$i = 0;
|
||||
while ($i < $numd)
|
||||
{
|
||||
$objd = $db->fetch_object($resd);
|
||||
|
||||
switch ($objd->item)
|
||||
{
|
||||
case "Invoice":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->ref);
|
||||
$upload_dir = $conf->facture->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=facture&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "SupplierInvoice":
|
||||
$tmpinvoicesupplier->fetch($objd->id);
|
||||
$subdir = get_exdir($tmpinvoicesupplier->id, 2, 0, 1, $tmpinvoicesupplier, 'invoice_supplier'); // TODO Use first file
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->ref);
|
||||
$upload_dir = $conf->fournisseur->facture->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=facture_fournisseur&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "ExpenseReport":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->ref);
|
||||
$upload_dir = $conf->expensereport->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=expensereport&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "SalaryPayment":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->id);
|
||||
$upload_dir = $conf->salaries->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=salaries&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "Donation":
|
||||
$tmpdonation->fetch($objp->id);
|
||||
$subdir = get_exdir(0, 0, 0, 0, $tmpdonation, 'donation');
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->id);
|
||||
$upload_dir = $conf->don->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=don&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "SocialContributions":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->id);
|
||||
$upload_dir = $conf->tax->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=tax&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
default:
|
||||
$subdir = '';
|
||||
$upload_dir = '';
|
||||
$link = '';
|
||||
break;
|
||||
}
|
||||
switch ($objd->item)
|
||||
{
|
||||
case "Invoice":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->ref);
|
||||
$upload_dir = $conf->facture->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=facture&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "SupplierInvoice":
|
||||
$tmpinvoicesupplier->fetch($objd->id);
|
||||
$subdir = get_exdir($tmpinvoicesupplier->id, 2, 0, 1, $tmpinvoicesupplier, 'invoice_supplier'); // TODO Use first file
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->ref);
|
||||
$upload_dir = $conf->fournisseur->facture->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=facture_fournisseur&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "ExpenseReport":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->ref);
|
||||
$upload_dir = $conf->expensereport->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=expensereport&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "SalaryPayment":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->id);
|
||||
$upload_dir = $conf->salaries->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=salaries&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "Donation":
|
||||
$tmpdonation->fetch($objp->id);
|
||||
$subdir = get_exdir(0, 0, 0, 0, $tmpdonation, 'donation');
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->id);
|
||||
$upload_dir = $conf->don->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=don&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
case "SocialContributions":
|
||||
$subdir = '';
|
||||
$subdir .= ($subdir ? '/' : '').dol_sanitizeFileName($objd->id);
|
||||
$upload_dir = $conf->tax->dir_output.'/'.$subdir;
|
||||
$link = "document.php?modulepart=tax&file=".str_replace('/', '%2F', $subdir).'%2F';
|
||||
break;
|
||||
default:
|
||||
$subdir = '';
|
||||
$upload_dir = '';
|
||||
$link = '';
|
||||
break;
|
||||
}
|
||||
|
||||
if (!empty($upload_dir))
|
||||
{
|
||||
$result = true;
|
||||
if (!empty($upload_dir))
|
||||
{
|
||||
$result = true;
|
||||
|
||||
$files = dol_dir_list($upload_dir, "files", 0, '', '(\.meta|_preview\.png)$', '', SORT_ASC, 1);
|
||||
//var_dump($upload_dir);
|
||||
//var_dump($files);
|
||||
if (count($files) < 1)
|
||||
{
|
||||
$nofile = array();
|
||||
$nofile['id'] = $objd->id;
|
||||
$nofile['entity'] = $objd->entity;
|
||||
$nofile['date'] = $db->idate($objd->date);
|
||||
$nofile['paid'] = $objd->paid;
|
||||
$nofile['amount_ht'] = $objd->total_ht;
|
||||
$nofile['amount_ttc'] = $objd->total_ttc;
|
||||
$nofile['amount_vat'] = $objd->total_vat;
|
||||
$nofile['ref'] = ($objd->ref ? $objd->ref : $objd->id);
|
||||
$nofile['fk'] = $objd->fk_soc;
|
||||
$nofile['item'] = $objd->item;
|
||||
$nofile['thirdparty_name'] = $objd->thirdparty_name;
|
||||
$nofile['thirdparty_code'] = $objd->thirdparty_code;
|
||||
$nofile['country_code'] = $objd->country_code;
|
||||
$nofile['vatnum'] = $objd->vatnum;
|
||||
$files = dol_dir_list($upload_dir, "files", 0, '', '(\.meta|_preview\.png)$', '', SORT_ASC, 1);
|
||||
//var_dump($upload_dir);
|
||||
//var_dump($files);
|
||||
if (count($files) < 1)
|
||||
{
|
||||
$nofile = array();
|
||||
$nofile['id'] = $objd->id;
|
||||
$nofile['entity'] = $objd->entity;
|
||||
$nofile['date'] = $db->idate($objd->date);
|
||||
$nofile['paid'] = $objd->paid;
|
||||
$nofile['amount_ht'] = $objd->total_ht;
|
||||
$nofile['amount_ttc'] = $objd->total_ttc;
|
||||
$nofile['amount_vat'] = $objd->total_vat;
|
||||
$nofile['ref'] = ($objd->ref ? $objd->ref : $objd->id);
|
||||
$nofile['fk'] = $objd->fk_soc;
|
||||
$nofile['item'] = $objd->item;
|
||||
$nofile['thirdparty_name'] = $objd->thirdparty_name;
|
||||
$nofile['thirdparty_code'] = $objd->thirdparty_code;
|
||||
$nofile['country_code'] = $objd->country_code;
|
||||
$nofile['vatnum'] = $objd->vatnum;
|
||||
|
||||
$filesarray[$nofile['item'].'_'.$nofile['id']] = $nofile;
|
||||
}
|
||||
else
|
||||
{
|
||||
foreach ($files as $key => $file)
|
||||
{
|
||||
$file['id'] = $objd->id;
|
||||
$file['entity'] = $objd->entity;
|
||||
$file['date'] = $db->idate($objd->date);
|
||||
$file['paid'] = $objd->paid;
|
||||
$file['amount_ht'] = $objd->total_ht;
|
||||
$file['amount_ttc'] = $objd->total_ttc;
|
||||
$file['amount_vat'] = $objd->total_vat;
|
||||
$file['ref'] = ($objd->ref ? $objd->ref : $objd->id);
|
||||
$file['fk'] = $objd->fk_soc;
|
||||
$file['item'] = $objd->item;
|
||||
$filesarray[$nofile['item'].'_'.$nofile['id']] = $nofile;
|
||||
}
|
||||
else
|
||||
{
|
||||
foreach ($files as $key => $file)
|
||||
{
|
||||
$file['id'] = $objd->id;
|
||||
$file['entity'] = $objd->entity;
|
||||
$file['date'] = $db->idate($objd->date);
|
||||
$file['paid'] = $objd->paid;
|
||||
$file['amount_ht'] = $objd->total_ht;
|
||||
$file['amount_ttc'] = $objd->total_ttc;
|
||||
$file['amount_vat'] = $objd->total_vat;
|
||||
$file['ref'] = ($objd->ref ? $objd->ref : $objd->id);
|
||||
$file['fk'] = $objd->fk_soc;
|
||||
$file['item'] = $objd->item;
|
||||
|
||||
$file['thirdparty_name'] = $objd->thirdparty_name;
|
||||
$file['thirdparty_code'] = $objd->thirdparty_code;
|
||||
$file['country_code'] = $objd->country_code;
|
||||
$file['vatnum'] = $objd->vatnum;
|
||||
$file['thirdparty_name'] = $objd->thirdparty_name;
|
||||
$file['thirdparty_code'] = $objd->thirdparty_code;
|
||||
$file['country_code'] = $objd->country_code;
|
||||
$file['vatnum'] = $objd->vatnum;
|
||||
|
||||
// Save record into array (only the first time it is found)
|
||||
if (empty($filesarray[$file['item'].'_'.$file['id']])) {
|
||||
$filesarray[$file['item'].'_'.$file['id']] = $file;
|
||||
}
|
||||
// Save record into array (only the first time it is found)
|
||||
if (empty($filesarray[$file['item'].'_'.$file['id']])) {
|
||||
$filesarray[$file['item'].'_'.$file['id']] = $file;
|
||||
}
|
||||
|
||||
// Add or concat file
|
||||
if (empty($filesarray[$file['item'].'_'.$file['id']]['files'])) {
|
||||
$filesarray[$file['item'].'_'.$file['id']]['files'] = array();
|
||||
}
|
||||
$filesarray[$file['item'].'_'.$file['id']]['files'][] = array('link' => $link.$file['name'], 'name'=>$file['name'], 'ref'=>$file['ref'], 'fullname' => $file['fullname'], 'relpathnamelang' => $langs->trans($file['item']).'/'.$file['name']);
|
||||
//var_dump($file['item'].'_'.$file['id']);
|
||||
//var_dump($filesarray[$file['item'].'_'.$file['id']]['files']);
|
||||
}
|
||||
}
|
||||
}
|
||||
// Add or concat file
|
||||
if (empty($filesarray[$file['item'].'_'.$file['id']]['files'])) {
|
||||
$filesarray[$file['item'].'_'.$file['id']]['files'] = array();
|
||||
}
|
||||
$filesarray[$file['item'].'_'.$file['id']]['files'][] = array('link' => $link.$file['name'], 'name'=>$file['name'], 'ref'=>$file['ref'], 'fullname' => $file['fullname'], 'relpathnamelang' => $langs->trans($file['item']).'/'.$file['name']);
|
||||
//var_dump($file['item'].'_'.$file['id']);
|
||||
//var_dump($filesarray[$file['item'].'_'.$file['id']]['files']);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
dol_print_error($db);
|
||||
}
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
dol_print_error($db);
|
||||
}
|
||||
|
||||
$db->free($resd);
|
||||
}
|
||||
else {
|
||||
setEventMessages($langs->trans("ErrorAtLeastOneObjectMustBeSelected"), null, 'errors');
|
||||
$db->free($resd);
|
||||
}
|
||||
else {
|
||||
setEventMessages($langs->trans("ErrorSelectAtLeastOne"), null, 'errors');
|
||||
$error++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -452,7 +453,7 @@ print ' - '.$form->selectDate($date_stop, 'date_stop', 0, 0, 0, "", 1, 1, 0)."\n
|
||||
if (!empty($conf->multicompany->enabled) && is_object($mc))
|
||||
{
|
||||
$mc->getInfo($conf->entity);
|
||||
print '<span class="marginleftonly marginrightonly">('.$langs->trans("Entity").' : ';
|
||||
print '<span class="marginleftonly marginrightonly'.(empty($conf->global->MULTICOMPANY_ALLOW_EXPORT_ACCOUNTING_DOC_FOR_ALL_ENTITIES)?' opacitymedium':'').'">('.$langs->trans("Entity").' : ';
|
||||
print "<td>";
|
||||
if (!empty($conf->global->MULTICOMPANY_ALLOW_EXPORT_ACCOUNTING_DOC_FOR_ALL_ENTITIES)) {
|
||||
print $mc->select_entities(GETPOSTISSET('search_entity') ? GETPOST('search_entity', 'int') : $mc->id, 'search_entity', '', false, false, false, false, true);
|
||||
|
||||
@ -255,13 +255,14 @@ else
|
||||
$px1->draw($file, $fileurl);
|
||||
|
||||
$show1 = $px1->show();
|
||||
unset($graph_datas);
|
||||
unset($px1);
|
||||
unset($datas);
|
||||
unset($datamin);
|
||||
unset($dataall);
|
||||
unset($labels);
|
||||
unset($amounts);
|
||||
|
||||
$px1 = null;
|
||||
$graph_datas =null;
|
||||
$datas = null;
|
||||
$datamin = null;
|
||||
$dataall = null;
|
||||
$labels = null;
|
||||
$amounts = null;
|
||||
}
|
||||
|
||||
// Graph Balance for the year
|
||||
@ -392,13 +393,13 @@ else
|
||||
|
||||
$show2 = $px2->show();
|
||||
|
||||
unset($px2);
|
||||
unset($graph_datas);
|
||||
unset($datas);
|
||||
unset($datamin);
|
||||
unset($dataall);
|
||||
unset($labels);
|
||||
unset($amounts);
|
||||
$px2 = null;
|
||||
$graph_datas =null;
|
||||
$datas = null;
|
||||
$datamin = null;
|
||||
$dataall = null;
|
||||
$labels = null;
|
||||
$amounts = null;
|
||||
}
|
||||
|
||||
// Graph 3 - Balance for all time line
|
||||
@ -460,7 +461,7 @@ else
|
||||
}
|
||||
else
|
||||
{
|
||||
$datas[$i] = '' +$solde + $subtotal;
|
||||
$datas[$i] = 0 + $solde + $subtotal;
|
||||
}
|
||||
$datamin[$i] = $object->min_desired;
|
||||
$dataall[$i] = $object->min_allowed;
|
||||
@ -505,13 +506,13 @@ else
|
||||
|
||||
$show3 = $px3->show();
|
||||
|
||||
unset($px3);
|
||||
unset($graph_datas);
|
||||
unset($datas);
|
||||
unset($datamin);
|
||||
unset($dataall);
|
||||
unset($labels);
|
||||
unset($amounts);
|
||||
$px3 = null;
|
||||
$graph_datas =null;
|
||||
$datas = null;
|
||||
$datamin = null;
|
||||
$dataall = null;
|
||||
$labels = null;
|
||||
$amounts = null;
|
||||
}
|
||||
|
||||
// Tableau 4a - Credit/Debit
|
||||
@ -634,10 +635,10 @@ else
|
||||
|
||||
$show4 = $px4->show();
|
||||
|
||||
unset($graph_datas);
|
||||
unset($px4);
|
||||
unset($debits);
|
||||
unset($credits);
|
||||
$px4 = null;
|
||||
$graph_datas = null;
|
||||
$debits = null;
|
||||
$credits = null;
|
||||
}
|
||||
|
||||
// Tableau 4b - Credit/Debit
|
||||
@ -742,10 +743,10 @@ else
|
||||
|
||||
$show5 = $px5->show();
|
||||
|
||||
unset($graph_datas);
|
||||
unset($px5);
|
||||
unset($debits);
|
||||
unset($credits);
|
||||
$px5 = null;
|
||||
$graph_datas = null;
|
||||
$debits = null;
|
||||
$credits = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -2419,12 +2419,23 @@ class Facture extends CommonInvoice
|
||||
* @param string $force_number Reference to force on invoice
|
||||
* @param int $idwarehouse Id of warehouse to use for stock decrease if option to decreasenon stock is on (0=no decrease)
|
||||
* @param int $notrigger 1=Does not execute triggers, 0= execute triggers
|
||||
* @param int $batch_rule [=0] 0 not decrement batch, else batch rule to use
|
||||
* 1=take in batches ordered by sellby and eatby dates
|
||||
* @return int <0 if KO, 0=Nothing done because invoice is not a draft, >0 if OK
|
||||
*/
|
||||
public function validate($user, $force_number = '', $idwarehouse = 0, $notrigger = 0)
|
||||
public function validate($user, $force_number = '', $idwarehouse = 0, $notrigger = 0, $batch_rule = 0)
|
||||
{
|
||||
global $conf, $langs;
|
||||
require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
|
||||
$productStatic = null;
|
||||
$warehouseStatic = null;
|
||||
if ($batch_rule > 0) {
|
||||
require_once DOL_DOCUMENT_ROOT . '/product/class/product.class.php';
|
||||
require_once DOL_DOCUMENT_ROOT . '/product/class/productbatch.class.php';
|
||||
require_once DOL_DOCUMENT_ROOT . '/product/stock/class/entrepot.class.php';
|
||||
$productStatic = new Product($this->db);
|
||||
$warehouseStatic = new Entrepot($this->db);
|
||||
}
|
||||
|
||||
$now = dol_now();
|
||||
|
||||
@ -2566,11 +2577,94 @@ class Facture extends CommonInvoice
|
||||
$mouvP = new MouvementStock($this->db);
|
||||
$mouvP->origin = &$this;
|
||||
// We decrease stock for product
|
||||
if ($this->type == self::TYPE_CREDIT_NOTE) $result = $mouvP->reception($user, $this->lines[$i]->fk_product, $idwarehouse, $this->lines[$i]->qty, 0, $langs->trans("InvoiceValidatedInDolibarr", $num));
|
||||
else $result = $mouvP->livraison($user, $this->lines[$i]->fk_product, $idwarehouse, $this->lines[$i]->qty, $this->lines[$i]->subprice, $langs->trans("InvoiceValidatedInDolibarr", $num));
|
||||
if ($result < 0) {
|
||||
$error++;
|
||||
$this->error = $mouvP->error;
|
||||
if ($this->type == self::TYPE_CREDIT_NOTE) {
|
||||
$result = $mouvP->reception($user, $this->lines[$i]->fk_product, $idwarehouse, $this->lines[$i]->qty, 0, $langs->trans("InvoiceValidatedInDolibarr", $num));
|
||||
if ($result < 0) {
|
||||
$error++;
|
||||
$this->error = $mouvP->error;
|
||||
}
|
||||
} else {
|
||||
$is_batch_line = false;
|
||||
if ($batch_rule > 0) {
|
||||
$productStatic->fetch($this->lines[$i]->fk_product);
|
||||
if ($productStatic->hasbatch()) {
|
||||
$is_batch_line = true;
|
||||
$product_qty_remain = $this->lines[$i]->qty;
|
||||
|
||||
$sortfield = null;
|
||||
$sortorder = null;
|
||||
// find all batch order by sellby (DLC) and eatby dates (DLUO) first
|
||||
if ($batch_rule == Productbatch::BATCH_RULE_SELLBY_EATBY_DATES_FIRST) {
|
||||
$sortfield = 'pl.sellby,pl.eatby,pb.qty,pl.rowid';
|
||||
$sortorder = 'ASC,ASC,ASC,ASC';
|
||||
}
|
||||
|
||||
$resBatchList = Productbatch::findAllForProduct($this->db, $productStatic->id, $idwarehouse, (!empty($conf->global->STOCK_ALLOW_NEGATIVE_TRANSFER) ? null : 0), $sortfield, $sortorder);
|
||||
if (!is_array($resBatchList)) {
|
||||
$error++;
|
||||
$this->error = $this->db->lasterror();
|
||||
}
|
||||
|
||||
if (!$error) {
|
||||
$batchList = $resBatchList;
|
||||
if (empty($batchList)) {
|
||||
$error++;
|
||||
$langs->load('errors');
|
||||
$warehouseStatic->fetch($idwarehouse);
|
||||
$this->error = $langs->trans('ErrorBatchNoFoundForProductInWarehouse', $productStatic->label, $warehouseStatic->ref);
|
||||
dol_syslog(__METHOD__ . ' Error: ' . $langs->transnoentitiesnoconv('ErrorBatchNoFoundForProductInWarehouse', $productStatic->label, $warehouseStatic->ref), LOG_ERR);
|
||||
}
|
||||
|
||||
foreach ($batchList as $batch) {
|
||||
if ($batch->qty <= 0) continue; // try to decrement only batches have positive quantity first
|
||||
|
||||
// enough quantity in this batch
|
||||
if ($batch->qty >= $product_qty_remain) {
|
||||
$product_batch_qty = $product_qty_remain;
|
||||
} // not enough (take all in batch)
|
||||
else {
|
||||
$product_batch_qty = $batch->qty;
|
||||
}
|
||||
$result = $mouvP->livraison($user, $productStatic->id, $idwarehouse, $product_batch_qty, $this->lines[$i]->subprice, $langs->trans('InvoiceValidatedInDolibarr', $num), '', '', '', $batch->batch);
|
||||
if ($result < 0) {
|
||||
$error++;
|
||||
$this->error = $mouvP->error;
|
||||
break;
|
||||
}
|
||||
|
||||
$product_qty_remain -= $product_batch_qty;
|
||||
// all product quantity was decremented
|
||||
if ($product_qty_remain <= 0) break;
|
||||
}
|
||||
|
||||
if (!$error && $product_qty_remain > 0) {
|
||||
if ($conf->global->STOCK_ALLOW_NEGATIVE_TRANSFER) {
|
||||
// take in the first batch
|
||||
$batch = $batchList[0];
|
||||
$result = $mouvP->livraison($user, $productStatic->id, $idwarehouse, $product_qty_remain, $this->lines[$i]->subprice, $langs->trans('InvoiceValidatedInDolibarr', $num), '', '', '', $batch->batch);
|
||||
if ($result < 0) {
|
||||
$error++;
|
||||
$this->error = $mouvP->error;
|
||||
}
|
||||
} else {
|
||||
$error++;
|
||||
$langs->load('errors');
|
||||
$warehouseStatic->fetch($idwarehouse);
|
||||
$this->error = $langs->trans('ErrorBatchNoFoundEnoughQuantityForProductInWarehouse', $productStatic->label, $warehouseStatic->ref);
|
||||
dol_syslog(__METHOD__ . ' Error: ' . $langs->transnoentitiesnoconv('ErrorBatchNoFoundEnoughQuantityForProductInWarehouse', $productStatic->label, $warehouseStatic->ref), LOG_ERR);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!$is_batch_line) {
|
||||
$result = $mouvP->livraison($user, $this->lines[$i]->fk_product, $idwarehouse, $this->lines[$i]->qty, $this->lines[$i]->subprice, $langs->trans("InvoiceValidatedInDolibarr", $num));
|
||||
if ($result < 0) {
|
||||
$error++;
|
||||
$this->error = $mouvP->error;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -184,7 +184,7 @@ if ($action == 'add')
|
||||
GETPOST('langfile', 'alpha'),
|
||||
1,
|
||||
(GETPOST('totalizable', 'alpha')?1:0),
|
||||
GETPOST('documentpdf', 'alpha')
|
||||
GETPOST('printable', 'alpha')
|
||||
);
|
||||
if ($result > 0)
|
||||
{
|
||||
@ -354,7 +354,7 @@ if ($action == 'update')
|
||||
GETPOST('langfile'),
|
||||
1,
|
||||
(GETPOST('totalizable', 'alpha')?1:0),
|
||||
GETPOST('documentpdf', 'alpha')
|
||||
GETPOST('printable', 'alpha')
|
||||
);
|
||||
if ($result > 0)
|
||||
{
|
||||
|
||||
@ -1179,8 +1179,8 @@ abstract class CommonDocGenerator
|
||||
$defaultParams = array(
|
||||
'style' => '',
|
||||
'display' => 'auto', // auto, table, list
|
||||
'documentpdfEnable' => array(1),
|
||||
'documentpdfEnableNotEmpty' => array(2),
|
||||
'printableEnable' => array(1),
|
||||
'printableEnableNotEmpty' => array(2),
|
||||
|
||||
'table' => array(
|
||||
'maxItemsInRow' => 2,
|
||||
@ -1217,13 +1217,13 @@ abstract class CommonDocGenerator
|
||||
// Enable extrafield ?
|
||||
$enabled = 0;
|
||||
$disableOnEmpty = 0;
|
||||
if(!empty($extrafields->attributes[$object->table_element]['documentpdf'][$key])) {
|
||||
$documentpdf = intval($extrafields->attributes[$object->table_element]['documentpdf'][$key]);
|
||||
if(in_array($documentpdf,$params['documentpdfEnable']) || in_array($documentpdf,$params['documentpdfEnableNotEmpty']) ) {
|
||||
if(!empty($extrafields->attributes[$object->table_element]['printable'][$key])) {
|
||||
$printable = intval($extrafields->attributes[$object->table_element]['printable'][$key]);
|
||||
if(in_array($printable,$params['printableEnable']) || in_array($printable,$params['printableEnableNotEmpty']) ) {
|
||||
$enabled = 1;
|
||||
}
|
||||
|
||||
if (in_array($documentpdf,$params['documentpdfEnableNotEmpty'])) {
|
||||
if (in_array($printable,$params['printableEnableNotEmpty'])) {
|
||||
$disableOnEmpty = 1;
|
||||
}
|
||||
}
|
||||
@ -1443,12 +1443,12 @@ abstract class CommonDocGenerator
|
||||
|
||||
// Enable extrafield ?
|
||||
$enabled = 0;
|
||||
if(!empty($extrafields->attributes[$object->table_element]['documentpdf'][$key])) {
|
||||
$documentpdf = intval($extrafields->attributes[$object->table_element]['documentpdf'][$key]);
|
||||
if($documentpdf === 1 || $documentpdf === 2) {
|
||||
if(!empty($extrafields->attributes[$object->table_element]['printable'][$key])) {
|
||||
$printable = intval($extrafields->attributes[$object->table_element]['printable'][$key]);
|
||||
if($printable === 1 || $printable === 2) {
|
||||
$enabled = 1;
|
||||
}
|
||||
// Note : if $documentpdf === 3 or 4 so, it's displayed after line description not in cols
|
||||
// Note : if $printable === 3 or 4 so, it's displayed after line description not in cols
|
||||
}
|
||||
|
||||
if (!$enabled){ continue; } // don't wast resourses if we don't need them...
|
||||
|
||||
@ -49,6 +49,8 @@
|
||||
* <dol_print_object_tax> Print object total tax
|
||||
* <dol_print_object_local_tax> Print object local tax
|
||||
* <dol_print_object_total> Print object total
|
||||
* <dol_print_order_lines_printer1> Print order lines for Printer1
|
||||
* <dol_print_order_lines_printer2> Print order lines for Printer2
|
||||
* <dol_print_payment> Print payment method
|
||||
*
|
||||
* Code which can be placed everywhere
|
||||
@ -188,6 +190,8 @@ class dolReceiptPrinter extends Printer
|
||||
'dol_print_object_local_tax',
|
||||
'dol_print_object_total',
|
||||
'dol_print_object_number',
|
||||
'dol_print_order_lines_printer1',
|
||||
'dol_print_order_lines_printer2',
|
||||
'dol_value_customer_firstname',
|
||||
'dol_value_customer_lastname',
|
||||
'dol_value_customer_mail',
|
||||
@ -720,6 +724,28 @@ class dolReceiptPrinter extends Printer
|
||||
case 'DOL_BEEP':
|
||||
$this->printer->getPrintConnector() -> write("\x1e");
|
||||
break;
|
||||
case 'DOL_PRINT_ORDER_LINES_PRINTER1':
|
||||
foreach ($object->lines as $line) {
|
||||
if ($line->special_code==1)
|
||||
{
|
||||
$spacestoadd = $nbcharactbyline - strlen($line->ref) - strlen($line->qty) - 10 - 1;
|
||||
$spaces = str_repeat(' ', $spacestoadd);
|
||||
$this->printer->text($line->ref.$spaces.$line->qty.' '.str_pad(price($line->total_ttc), 10, ' ', STR_PAD_LEFT)."\n");
|
||||
$this->printer->text(strip_tags(htmlspecialchars_decode($line->desc))."\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'DOL_PRINT_ORDER_LINES_PRINTER2':
|
||||
foreach ($object->lines as $line) {
|
||||
if ($line->special_code==2)
|
||||
{
|
||||
$spacestoadd = $nbcharactbyline - strlen($line->ref) - strlen($line->qty) - 10 - 1;
|
||||
$spaces = str_repeat(' ', $spacestoadd);
|
||||
$this->printer->text($line->ref.$spaces.$line->qty.' '.str_pad(price($line->total_ttc), 10, ' ', STR_PAD_LEFT)."\n");
|
||||
$this->printer->text(strip_tags(htmlspecialchars_decode($line->desc))."\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
$this->printer->text($vals[$tplline]['tag']);
|
||||
$this->printer->text($vals[$tplline]['value']);
|
||||
|
||||
@ -225,10 +225,10 @@ class ExtraFields
|
||||
* @param string $langfile Language file
|
||||
* @param string $enabled Condition to have the field enabled or not
|
||||
* @param int $totalizable Is a measure. Must show a total on lists
|
||||
* @param int $documentpdf Is extrafield displayed on PDF
|
||||
* @param int $printable Is extrafield displayed on PDF
|
||||
* @return int <=0 if KO, >0 if OK
|
||||
*/
|
||||
public function addExtraField($attrname, $label, $type, $pos, $size, $elementtype, $unique = 0, $required = 0, $default_value = '', $param = '', $alwayseditable = 0, $perms = '', $list = '-1', $help = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $documentpdf = 0)
|
||||
public function addExtraField($attrname, $label, $type, $pos, $size, $elementtype, $unique = 0, $required = 0, $default_value = '', $param = '', $alwayseditable = 0, $perms = '', $list = '-1', $help = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $printable = 0)
|
||||
{
|
||||
if (empty($attrname)) return -1;
|
||||
if (empty($label)) return -1;
|
||||
@ -246,7 +246,7 @@ class ExtraFields
|
||||
if ($result > 0 || $err1 == 'DB_ERROR_COLUMN_ALREADY_EXISTS' || $type == 'separate')
|
||||
{
|
||||
// Add declaration of field into table
|
||||
$result2 = $this->create_label($attrname, $label, $type, $pos, $size, $elementtype, $unique, $required, $param, $alwayseditable, $perms, $list, $help, $default_value, $computed, $entity, $langfile, $enabled, $totalizable, $documentpdf);
|
||||
$result2 = $this->create_label($attrname, $label, $type, $pos, $size, $elementtype, $unique, $required, $param, $alwayseditable, $perms, $list, $help, $default_value, $computed, $entity, $langfile, $enabled, $totalizable, $printable);
|
||||
$err2 = $this->errno;
|
||||
if ($result2 > 0 || ($err1 == 'DB_ERROR_COLUMN_ALREADY_EXISTS' && $err2 == 'DB_ERROR_RECORD_ALREADY_EXISTS'))
|
||||
{
|
||||
@ -375,11 +375,11 @@ class ExtraFields
|
||||
* @param string $langfile Language file
|
||||
* @param string $enabled Condition to have the field enabled or not
|
||||
* @param int $totalizable Is a measure. Must show a total on lists
|
||||
* @param int $documentpdf Is extrafield displayed on PDF
|
||||
* @param int $printable Is extrafield displayed on PDF
|
||||
* @return int <=0 if KO, >0 if OK
|
||||
* @throws Exception
|
||||
*/
|
||||
private function create_label($attrname, $label = '', $type = '', $pos = 0, $size = 0, $elementtype = 'member', $unique = 0, $required = 0, $param = '', $alwayseditable = 0, $perms = '', $list = '-1', $help = '', $default = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $documentpdf = 0)
|
||||
private function create_label($attrname, $label = '', $type = '', $pos = 0, $size = 0, $elementtype = 'member', $unique = 0, $required = 0, $param = '', $alwayseditable = 0, $perms = '', $list = '-1', $help = '', $default = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $printable = 0)
|
||||
{
|
||||
// phpcs:enable
|
||||
global $conf, $user;
|
||||
@ -424,7 +424,7 @@ class ExtraFields
|
||||
$sql .= " perms,";
|
||||
$sql .= " langs,";
|
||||
$sql .= " list,";
|
||||
$sql .= " documentpdf,";
|
||||
$sql .= " printable,";
|
||||
$sql .= " fielddefault,";
|
||||
$sql .= " fieldcomputed,";
|
||||
$sql .= " fk_user_author,";
|
||||
@ -448,7 +448,7 @@ class ExtraFields
|
||||
$sql .= " ".($perms ? "'".$this->db->escape($perms)."'" : "null").",";
|
||||
$sql .= " ".($langfile ? "'".$this->db->escape($langfile)."'" : "null").",";
|
||||
$sql .= " '".$this->db->escape($list)."',";
|
||||
$sql .= " '".$this->db->escape($documentpdf)."',";
|
||||
$sql .= " '".$this->db->escape($printable)."',";
|
||||
$sql .= " ".($default ? "'".$this->db->escape($default)."'" : "null").",";
|
||||
$sql .= " ".($computed ? "'".$this->db->escape($computed)."'" : "null").",";
|
||||
$sql .= " ".(is_object($user) ? $user->id : 0).",";
|
||||
@ -595,11 +595,11 @@ class ExtraFields
|
||||
* @param string $langfile Language file
|
||||
* @param string $enabled Condition to have the field enabled or not
|
||||
* @param int $totalizable Is extrafield totalizable on list
|
||||
* @param int $documentpdf Is extrafield displayed on PDF
|
||||
* @param int $printable Is extrafield displayed on PDF
|
||||
* @return int >0 if OK, <=0 if KO
|
||||
* @throws Exception
|
||||
*/
|
||||
public function update($attrname, $label, $type, $length, $elementtype, $unique = 0, $required = 0, $pos = 0, $param = '', $alwayseditable = 0, $perms = '', $list = '', $help = '', $default = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $documentpdf = 0)
|
||||
public function update($attrname, $label, $type, $length, $elementtype, $unique = 0, $required = 0, $pos = 0, $param = '', $alwayseditable = 0, $perms = '', $list = '', $help = '', $default = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $printable = 0)
|
||||
{
|
||||
if ($elementtype == 'thirdparty') $elementtype = 'societe';
|
||||
if ($elementtype == 'contact') $elementtype = 'socpeople';
|
||||
@ -649,7 +649,7 @@ class ExtraFields
|
||||
{
|
||||
if ($label)
|
||||
{
|
||||
$result = $this->update_label($attrname, $label, $type, $length, $elementtype, $unique, $required, $pos, $param, $alwayseditable, $perms, $list, $help, $default, $computed, $entity, $langfile, $enabled, $totalizable, $documentpdf);
|
||||
$result = $this->update_label($attrname, $label, $type, $length, $elementtype, $unique, $required, $pos, $param, $alwayseditable, $perms, $list, $help, $default, $computed, $entity, $langfile, $enabled, $totalizable, $printable);
|
||||
}
|
||||
if ($result > 0)
|
||||
{
|
||||
@ -707,15 +707,15 @@ class ExtraFields
|
||||
* @param string $langfile Language file
|
||||
* @param string $enabled Condition to have the field enabled or not
|
||||
* @param int $totalizable Is extrafield totalizable on list
|
||||
* @param int $documentpdf Is extrafield displayed on PDF
|
||||
* @param int $printable Is extrafield displayed on PDF
|
||||
* @return int <=0 if KO, >0 if OK
|
||||
* @throws Exception
|
||||
*/
|
||||
private function update_label($attrname, $label, $type, $size, $elementtype, $unique = 0, $required = 0, $pos = 0, $param = '', $alwayseditable = 0, $perms = '', $list = '0', $help = '', $default = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $documentpdf = 0)
|
||||
private function update_label($attrname, $label, $type, $size, $elementtype, $unique = 0, $required = 0, $pos = 0, $param = '', $alwayseditable = 0, $perms = '', $list = '0', $help = '', $default = '', $computed = '', $entity = '', $langfile = '', $enabled = '1', $totalizable = 0, $printable = 0)
|
||||
{
|
||||
// phpcs:enable
|
||||
global $conf, $user;
|
||||
dol_syslog(get_class($this)."::update_label ".$attrname.", ".$label.", ".$type.", ".$size.", ".$elementtype.", ".$unique.", ".$required.", ".$pos.", ".$alwayseditable.", ".$perms.", ".$list.", ".$default.", ".$computed.", ".$entity.", ".$langfile.", ".$enabled.", ".$totalizable.", ".$documentpdf);
|
||||
dol_syslog(get_class($this)."::update_label ".$attrname.", ".$label.", ".$type.", ".$size.", ".$elementtype.", ".$unique.", ".$required.", ".$pos.", ".$alwayseditable.", ".$perms.", ".$list.", ".$default.", ".$computed.", ".$entity.", ".$langfile.", ".$enabled.", ".$totalizable.", ".$printable);
|
||||
|
||||
// Clean parameters
|
||||
if ($elementtype == 'thirdparty') $elementtype = 'societe';
|
||||
@ -780,7 +780,7 @@ class ExtraFields
|
||||
$sql .= " alwayseditable,";
|
||||
$sql .= " param,";
|
||||
$sql .= " list,";
|
||||
$sql .= " documentpdf,";
|
||||
$sql .= " printable,";
|
||||
$sql .= " totalizable,";
|
||||
$sql .= " fielddefault,";
|
||||
$sql .= " fieldcomputed,";
|
||||
@ -804,7 +804,7 @@ class ExtraFields
|
||||
$sql .= " '".$this->db->escape($alwayseditable)."',";
|
||||
$sql .= " '".$this->db->escape($params)."',";
|
||||
$sql .= " '".$this->db->escape($list)."', ";
|
||||
$sql .= " '".$this->db->escape($documentpdf)."', ";
|
||||
$sql .= " '".$this->db->escape($printable)."', ";
|
||||
$sql .= " ".$totalizable.",";
|
||||
$sql .= " ".(($default != '') ? "'".$this->db->escape($default)."'" : "null").",";
|
||||
$sql .= " ".($computed ? "'".$this->db->escape($computed)."'" : "null").",";
|
||||
@ -882,7 +882,7 @@ class ExtraFields
|
||||
}*/
|
||||
|
||||
// We should not have several time this request. If we have, there is some optimization to do by calling a simple $extrafields->fetch_optionals() in top of code and not into subcode
|
||||
$sql = "SELECT rowid,name,label,type,size,elementtype,fieldunique,fieldrequired,param,pos,alwayseditable,perms,langs,list,documentpdf,totalizable,fielddefault,fieldcomputed,entity,enabled,help";
|
||||
$sql = "SELECT rowid,name,label,type,size,elementtype,fieldunique,fieldrequired,param,pos,alwayseditable,perms,langs,list,printable,totalizable,fielddefault,fieldcomputed,entity,enabled,help";
|
||||
$sql .= " FROM ".MAIN_DB_PREFIX."extrafields";
|
||||
//$sql.= " WHERE entity IN (0,".$conf->entity.")"; // Filter is done later
|
||||
if ($elementtype) $sql .= " WHERE elementtype = '".$elementtype."'"; // Filed with object->table_element
|
||||
@ -944,7 +944,7 @@ class ExtraFields
|
||||
$this->attributes[$tab->elementtype]['perms'][$tab->name] = (strlen($tab->perms) == 0 ? 1 : $tab->perms);
|
||||
$this->attributes[$tab->elementtype]['langfile'][$tab->name] = $tab->langs;
|
||||
$this->attributes[$tab->elementtype]['list'][$tab->name] = $tab->list;
|
||||
$this->attributes[$tab->elementtype]['documentpdf'][$tab->name] = $tab->documentpdf;
|
||||
$this->attributes[$tab->elementtype]['printable'][$tab->name] = $tab->printable;
|
||||
$this->attributes[$tab->elementtype]['totalizable'][$tab->name] = $tab->totalizable;
|
||||
$this->attributes[$tab->elementtype]['entityid'][$tab->name] = $tab->entity;
|
||||
$this->attributes[$tab->elementtype]['enabled'][$tab->name] = $tab->enabled;
|
||||
|
||||
@ -6693,8 +6693,10 @@ class Form
|
||||
<script type="text/javascript">
|
||||
jQuery(document).ready(function () {
|
||||
$(\'.multiselectcheckbox'.$htmlname.' input[type="checkbox"]\').on(\'click\', function () {
|
||||
console.log("A new field was added/removed")
|
||||
$("input:hidden[name=formfilteraction]").val(\'listafterchangingselectedfields\')
|
||||
console.log("A new field was added/removed, we edit field input[name=formfilteraction]");
|
||||
|
||||
$("input:hidden[name=formfilteraction]").val(\'listafterchangingselectedfields\'); // Update field so we know we changed something on selected fields after POST
|
||||
|
||||
var title = $(this).val() + ",";
|
||||
if ($(this).is(\':checked\')) {
|
||||
$(\'.'.$htmlname.'\').val(title + $(\'.'.$htmlname.'\').val());
|
||||
@ -6703,8 +6705,10 @@ class Form
|
||||
$(\'.'.$htmlname.'\').val( $(\'.'.$htmlname.'\').val().replace(title, \'\') )
|
||||
}
|
||||
// Now, we submit page
|
||||
$(this).parents(\'form:first\').submit();
|
||||
//$(this).parents(\'form:first\').submit();
|
||||
});
|
||||
|
||||
|
||||
});
|
||||
</script>
|
||||
|
||||
@ -7070,7 +7074,6 @@ class Form
|
||||
jQuery(".linkto").click(function() {
|
||||
console.log("We choose to show/hide link for rel="+jQuery(this).attr(\'rel\'));
|
||||
jQuery("#"+jQuery(this).attr(\'rel\')+"list").toggle();
|
||||
jQuery(this).toggle();
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
@ -81,13 +81,31 @@ print "});\n";
|
||||
// Wrapper to manage dropdown
|
||||
if (! defined('JS_JQUERY_DISABLE_DROPDOWN'))
|
||||
{
|
||||
print "\n/* JS CODE TO ENABLE dropdown */\n";
|
||||
print "\n/* JS CODE TO ENABLE dropdown (hamburger, linkto, ...) */\n";
|
||||
print '
|
||||
jQuery(document).ready(function () {
|
||||
$(".dropdown dt a").on(\'click\', function () {
|
||||
console.log("We click on dropdown");
|
||||
//console.log($(this).parent().parent().find(\'dd ul\'));
|
||||
$(this).parent().parent().find(\'dd ul\').slideToggle(\'fast\');
|
||||
jQuery(document).ready(function () {
|
||||
var lastopendropdown = null;
|
||||
|
||||
// Click onto the link "link to" or "hamburger", toggle dropdown
|
||||
$(".dropdown dt a").on(\'click\', function () {
|
||||
console.log("toggle dropdown dt a");
|
||||
|
||||
//$(this).parent().parent().find(\'dd ul\').slideToggle(\'fast\');
|
||||
$(this).parent().parent().find(\'dd ul\').toggleClass("open");
|
||||
|
||||
if ($(this).parent().parent().find(\'dd ul\').hasClass("open")) {
|
||||
lastopendropdown = $(this).parent().parent().find(\'dd ul\');
|
||||
//console.log(lastopendropdown);
|
||||
} else {
|
||||
// We closed the dropdown for hamburger selectfields
|
||||
if ($("input:hidden[name=formfilteraction]").val() == "listafterchangingselectedfields") {
|
||||
console.log("resubmit the form saved into lastopendropdown after clicking on hamburger");
|
||||
//$(".dropdown dt a").parents(\'form:first\').submit();
|
||||
//$(".dropdown dt a").closest("form").submit();
|
||||
lastopendropdown.closest("form").submit();
|
||||
}
|
||||
}
|
||||
|
||||
// Note: Did not find a way to get exact height (value is update at exit) so i calculate a generic from nb of lines
|
||||
heigthofcontent = 21 * $(this).parent().parent().find(\'dd div ul li\').length;
|
||||
if (heigthofcontent > 300) heigthofcontent = 300; // limited by max-height on css .dropdown dd ul
|
||||
@ -101,19 +119,32 @@ if (! defined('JS_JQUERY_DISABLE_DROPDOWN'))
|
||||
console.log("We reposition top by "+pix);
|
||||
$(this).parent().parent().find(\'dd\').css("top", pix);
|
||||
}
|
||||
// $(".dropdown dd ul").slideToggle(\'fast\');
|
||||
});
|
||||
$(".dropdowncloseonclick").on(\'click\', function () {
|
||||
console.log("Link has class dropdowncloseonclick, so we close/hide the popup ul");
|
||||
$(this).parent().parent().hide();
|
||||
});
|
||||
|
||||
$(document).bind(\'click\', function (e) {
|
||||
//console.log("We click outside of dropdown, so we close it.");
|
||||
var $clicked = $(e.target);
|
||||
if (!$clicked.parents().hasClass("dropdown")) $(".dropdown dd ul").hide();
|
||||
// Click on a link into the popup "link to" or other dropdown that ask to close drop down on element click, so close dropdown
|
||||
$(".dropdowncloseonclick").on(\'click\', function () {
|
||||
console.log("Link has class dropdowncloseonclick, so we close/hide the popup ul");
|
||||
//$(this).parent().parent().hide(); // $(this).parent().parent() is ul
|
||||
$(this).parent().parent().removeClass("open"); // $(this).parent().parent() is ul
|
||||
});
|
||||
});
|
||||
|
||||
// Click outside of any dropdown
|
||||
$(document).bind(\'click\', function (e) {
|
||||
var $clicked = $(e.target); // This is element we click on
|
||||
if (!$clicked.parents().hasClass("dropdown")) {
|
||||
console.log("close dropdown dd ul - we click outside");
|
||||
//$(".dropdown dd ul").hide();
|
||||
$(".dropdown dd ul").removeClass("open");
|
||||
|
||||
if ($("input:hidden[name=formfilteraction]").val() == "listafterchangingselectedfields") {
|
||||
console.log("resubmit form saved into lastopendropdown after clicking outside of dropdown and having change selectlist from selectlist field of hamburger dropdown");
|
||||
//$(".dropdown dt a").parents(\'form:first\').submit();
|
||||
//$(".dropdown dt a").closest("form").submit();
|
||||
lastopendropdown.closest("form").submit();
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
';
|
||||
}
|
||||
|
||||
|
||||
@ -7618,15 +7618,12 @@ function printCommonFooter($zone = 'private')
|
||||
$micro_end_time = microtime(true);
|
||||
print ' - Build time: '.ceil(1000 * ($micro_end_time - $micro_start_time)).' ms';
|
||||
}
|
||||
if (function_exists("memory_get_usage"))
|
||||
{
|
||||
print ' - Mem: '.memory_get_usage();
|
||||
|
||||
if (function_exists("memory_get_usage")) {
|
||||
print ' - Mem: '.memory_get_usage(); // Do not use true here, it seems it takes the peak amount
|
||||
}
|
||||
if (function_exists("xdebug_memory_usage"))
|
||||
{
|
||||
print ' - XDebug time: '.ceil(1000 * xdebug_time_index()).' ms';
|
||||
print ' - XDebug mem: '.xdebug_memory_usage();
|
||||
print ' - XDebug mem peak: '.xdebug_peak_memory_usage();
|
||||
if (function_exists("memory_get_peak_usage")) {
|
||||
print ' - Real mem peak: '.memory_get_peak_usage(true);
|
||||
}
|
||||
if (function_exists("zend_loader_file_encoded"))
|
||||
{
|
||||
|
||||
@ -198,7 +198,7 @@ $langs->load("modulebuilder");
|
||||
</td><td class="valeur"><input id="list" class="minwidth100" type="text" name="list" value="<?php echo GETPOST('list', 'int')!='' ? GETPOST('list', 'int') : '1'; ?>"></td></tr>
|
||||
<!-- Visibility for PDF-->
|
||||
<tr><td class="extra_pdf"><?php echo $form->textwithpicto($langs->trans("DisplayOnPdf"), $langs->trans("DisplayOnPdfDesc")); ?>
|
||||
</td><td class="valeur"><input id="documentpdf" class="minwidth100" type="text" name="documentpdf" value="<?php echo dol_escape_htmltag(GETPOST('documentpdf', 'int')); ?>"></td></tr>
|
||||
</td><td class="valeur"><input id="printable" class="minwidth100" type="text" name="printable" value="<?php echo dol_escape_htmltag(GETPOST('printable', 'int')); ?>"></td></tr>
|
||||
<!-- Totalizable -->
|
||||
<tr class="extra_totalizable"><td><?php echo $langs->trans("Totalizable"); ?></td><td class="valeur"><input id="totalizable" type="checkbox" name="totalizable"<?php echo ((GETPOST('totalizable', 'alpha') || GETPOST('button', 'alpha'))?' checked':''); ?>></td></tr>
|
||||
<!-- Help tooltip -->
|
||||
|
||||
@ -165,7 +165,7 @@ $list=$extrafields->attributes[$elementtype]['list'][$attrname];
|
||||
$totalizable = $extrafields->attributes[$elementtype]['totalizable'][$attrname];
|
||||
$help=$extrafields->attributes[$elementtype]['help'][$attrname];
|
||||
$entitycurrentorall=$extrafields->attributes[$elementtype]['entityid'][$attrname];
|
||||
$documentpdf=$extrafields->attributes[$elementtype]['documentpdf'][$attrname];
|
||||
$printable=$extrafields->attributes[$elementtype]['printable'][$attrname];
|
||||
|
||||
if((($type == 'select') || ($type == 'checkbox') || ($type == 'radio')) && is_array($param))
|
||||
{
|
||||
@ -267,7 +267,7 @@ else
|
||||
</td><td class="valeur"><input id="list" class="minwidth100" type="text" name="list" value="<?php echo ($list!=''?$list:'1'); ?>"></td></tr>
|
||||
<!-- Visibility for PDF-->
|
||||
<tr><td class="extra_pdf"><?php echo $form->textwithpicto($langs->trans("DisplayOnPdf"), $langs->trans("DisplayOnPdfDesc")); ?>
|
||||
</td><td class="valeur"><input id="documentpdf" class="minwidth100" type="text" name="documentpdf" value="<?php echo dol_escape_htmltag($documentpdf); ?>"></td></tr>
|
||||
</td><td class="valeur"><input id="printable" class="minwidth100" type="text" name="printable" value="<?php echo dol_escape_htmltag($printable); ?>"></td></tr>
|
||||
<tr class="extra_totalizable"><td><?php echo $form->textwithpicto($langs->trans("Totalizable"), $langs->trans("TotalizableDesc")); ?></td><td class="valeur"><input id="totalizable" type="checkbox" name="totalizable"<?php echo ($totalizable?' checked':''); ?>></td></tr>
|
||||
<!-- Help tooltip -->
|
||||
<tr class="help"><td><?php echo $form->textwithpicto($langs->trans("HelpOnTooltip"), $langs->trans("HelpOnTooltipDesc")); ?></td><td class="valeur"><input id="help" class="quatrevingtpercent" type="text" name="help" value="<?php echo dol_escape_htmltag($help); ?>"></td></tr>
|
||||
|
||||
@ -93,7 +93,7 @@ if (is_array($extrafields->attributes[$elementtype]['type']) && count($extrafiel
|
||||
print '<td class="center">'.yn($extrafields->attributes[$elementtype]['required'][$key])."</td>\n";
|
||||
print '<td class="center">'.yn($extrafields->attributes[$elementtype]['alwayseditable'][$key])."</td>\n";
|
||||
print '<td class="center">'.$extrafields->attributes[$elementtype]['list'][$key]."</td>\n";
|
||||
print '<td class="center">'.$extrafields->attributes[$elementtype]['documentpdf'][$key]."</td>\n";
|
||||
print '<td class="center">'.$extrafields->attributes[$elementtype]['printable'][$key]."</td>\n";
|
||||
print '<td class="center">'.yn($extrafields->attributes[$elementtype]['totalizable'][$key])."</td>\n";
|
||||
if (! empty($conf->multicompany->enabled)) {
|
||||
print '<td class="center">';
|
||||
|
||||
@ -1094,7 +1094,7 @@ class Cronjob extends CommonObject
|
||||
|
||||
$errmsg = '';
|
||||
if (!is_array($object->errors) || !in_array($object->error, $object->errors)) $errmsg .= $object->error;
|
||||
if (is_array($object->errors) && count($object->errors)) $errmsg .= ($errmsg ? ', '.$errmsg : '').join(', ', $object->errors);
|
||||
if (is_array($object->errors) && count($object->errors)) $errmsg .= (($errmsg ? ', ' : '').join(', ', $object->errors));
|
||||
if (empty($errmsg)) $errmsg = $langs->trans('ErrorUnknown');
|
||||
|
||||
dol_syslog(get_class($this)."::run_jobs END result=".$result." error=".$errmsg, LOG_ERR);
|
||||
|
||||
@ -181,4 +181,7 @@ INSERT INTO llx_c_ticket_resolution (code, pos, label, active, use_default, desc
|
||||
|
||||
DELETE FROM llx_const WHERE name = __ENCRYPT('DONATION_ART885')__;
|
||||
|
||||
ALTER TABLE llx_extrafields ADD COLUMN documentpdf integer DEFAULT 0;
|
||||
ALTER TABLE llx_extrafields MODIFY COLUMN printable integer DEFAULT 0;
|
||||
ALTER TABLE llx_extrafields ADD COLUMN printable integer DEFAULT 0;
|
||||
|
||||
|
||||
|
||||
@ -36,7 +36,7 @@ create table llx_extrafields
|
||||
alwayseditable integer DEFAULT 0, -- 1 if field can be edited whatever is element status
|
||||
param text, -- extra parameters to define possible values of field
|
||||
list varchar(255) DEFAULT '1', -- visibility of field. 0=Never visible, 1=Visible on list and forms, 2=Visible on list only. Using a negative value means field is not shown by default on list but can be selected for viewing
|
||||
printable boolean DEFAULT FALSE, -- is the extrafield output on documents
|
||||
printable integer DEFAULT 0, -- is the extrafield output on documents
|
||||
totalizable boolean DEFAULT FALSE, -- is extrafield totalizable on list
|
||||
langs varchar(64), -- example: fileofmymodule@mymodule
|
||||
help text, -- to store help tooltip
|
||||
|
||||
@ -1686,6 +1686,8 @@ CashDeskIdWareHouse=Force and restrict warehouse to use for stock decrease
|
||||
StockDecreaseForPointOfSaleDisabled=Stock decrease from Point of Sale disabled
|
||||
StockDecreaseForPointOfSaleDisabledbyBatch=Stock decrease in POS is not compatible with module Serial/Lot management (currently active) so stock decrease is disabled.
|
||||
CashDeskYouDidNotDisableStockDecease=You did not disable stock decrease when making a sale from Point of Sale. Hence a warehouse is required.
|
||||
CashDeskForceDecreaseStockLabel=Stock decrease for batch products was forced.
|
||||
CashDeskForceDecreaseStockDesc=Decrease first by the oldest eatby and sellby dates.
|
||||
##### Bookmark #####
|
||||
BookmarkSetup=Bookmark module setup
|
||||
BookmarkDesc=This module allows you to manage bookmarks. You can also add shortcuts to any Dolibarr pages or external web sites on your left menu.
|
||||
|
||||
@ -96,7 +96,7 @@ ErrorBadMaskFailedToLocatePosOfSequence=Error, mask without sequence number
|
||||
ErrorBadMaskBadRazMonth=Error, bad reset value
|
||||
ErrorMaxNumberReachForThisMask=Maximum number reached for this mask
|
||||
ErrorCounterMustHaveMoreThan3Digits=Counter must have more than 3 digits
|
||||
ErrorSelectAtLeastOne=Error. Select at least one entry.
|
||||
ErrorSelectAtLeastOne=Error, select at least one entry.
|
||||
ErrorDeleteNotPossibleLineIsConsolidated=Delete not possible because record is linked to a bank transaction that is conciliated
|
||||
ErrorProdIdAlreadyExist=%s is assigned to another third
|
||||
ErrorFailedToSendPassword=Failed to send password
|
||||
@ -230,6 +230,8 @@ ErrorAddAtLeastOneLineFirst=Add at least one line first
|
||||
ErrorRecordAlreadyInAccountingDeletionNotPossible=Error, record is already transferred in accounting, deletion is not possible.
|
||||
ErrorLanguageMandatoryIfPageSetAsTranslationOfAnother=Error, language is mandatory if you set the page as a translation of another one.
|
||||
ErrorLanguageOfTranslatedPageIsSameThanThisPage=Error, language of translated page is same than this one.
|
||||
ErrorBatchNoFoundForProductInWarehouse=No lot/serial found for product "%s" in warehouse "%s".
|
||||
ErrorBatchNoFoundEnoughQuantityForProductInWarehouse=No enough quantity for this lot/serial for product "%s" in warehouse "%s".
|
||||
# Warnings
|
||||
WarningParamUploadMaxFileSizeHigherThanPostMaxSize=Your PHP parameter upload_max_filesize (%s) is higher than PHP parameter post_max_size (%s). This is not a consistent setup.
|
||||
WarningPasswordSetWithNoAccount=A password was set for this member. However, no user account was created. So this password is stored but can't be used to login to Dolibarr. It may be used by an external module/interface but if you don't need to define any login nor password for a member, you can disable option "Manage a login for each member" from Member module setup. If you need to manage a login but don't need any password, you can keep this field empty to avoid this warning. Note: Email can also be used as a login if the member is linked to a user.
|
||||
|
||||
@ -31,7 +31,7 @@ NextYearOfInvoice=Following year of invoice date
|
||||
DateNextInvoiceBeforeGen=Date of next invoice (before generation)
|
||||
DateNextInvoiceAfterGen=Date of next invoice (after generation)
|
||||
GraphInBarsAreLimitedTo3Measures=Grapics are limited to 3 measures in 'Bars' mode. The mode 'Lines' was automatically selected instead.
|
||||
OnlyOneFieldForXAxisIsPossible=Only 1 field is currently possible as X-Axis. Only the first selected field has been selected.
|
||||
OnlyOneFieldForXAxisIsPossible=Only 1 field is currently possible as X-Axis. Only the first selected field has been selected.
|
||||
AtLeastOneMeasureIsRequired=At least 1 field for measure is required
|
||||
AtLeastOneXAxisIsRequired=At least 1 field for X-Axis is required
|
||||
|
||||
@ -278,3 +278,7 @@ LinesToImport=Lines to import
|
||||
|
||||
MemoryUsage=Memory usage
|
||||
RequestDuration=Duration of request
|
||||
PopuProp=Products/Services by popularity in Proposals
|
||||
PopuCom=Products/Services by popularity in Orders
|
||||
ProductStatistics=Products/Services Statistics
|
||||
NbOfQtyInOrders=Qty in orders
|
||||
|
||||
@ -1683,6 +1683,8 @@ CashDeskIdWareHouse=Forcer et restreindre l'emplacement/entrepôt à utiliser po
|
||||
StockDecreaseForPointOfSaleDisabled=Réduction de stock lors de l'utilisation du Point de Vente désactivée
|
||||
StockDecreaseForPointOfSaleDisabledbyBatch=La décrémentation de stock depuis ce module Point de Vente n'est pas encore compatible avec la gestion des numéros de lots/série.
|
||||
CashDeskYouDidNotDisableStockDecease=Vous n'avez pas désactivé la réduction de stock lors d'une vente depuis le Point de vente. Par conséquent, un entrepôt est nécessaire.
|
||||
CashDeskForceDecreaseStockLabel=Décrémentation des stocks pour les lots a été forcé.
|
||||
CashDeskForceDecreaseStockDesc=Décrémentation des lots par DLC et DLUO les plus anciennes.
|
||||
##### Bookmark #####
|
||||
BookmarkSetup=Configuration du module Marque-pages
|
||||
BookmarkDesc=Ce module vous permet de gérer des liens et raccourcis. Il permet aussi d'ajouter n'importe quelle page de Dolibarr ou lien web dans le menu d'accès rapide sur la gauche.
|
||||
|
||||
@ -227,6 +227,8 @@ ErrorNoFieldWithAttributeShowoncombobox=Aucun champ n'a la propriété 'showonco
|
||||
ErrorFieldRequiredForProduct=Le champ '%s' est obligatoire pour le produit %s
|
||||
ProblemIsInSetupOfTerminal=Le problème est dans la configuration du terminal %s.
|
||||
ErrorAddAtLeastOneLineFirst=Ajouter d'abord au moins une ligne
|
||||
ErrorBatchNoFoundForProductInWarehouse=Aucun lot trouvé pour le produit "%s" dans l'entrepôt "%s".
|
||||
ErrorBatchNoFoundEnoughQuantityForProductInWarehouse=Quantité insuffisante dans les lots pour le produit "%s" dans l'entepôt "%s".
|
||||
# Warnings
|
||||
WarningParamUploadMaxFileSizeHigherThanPostMaxSize=Votre paramètre PHP upload_max_filesize (%s) est supérieur au paramètre PHP post_max_size (%s). Ceci n'est pas une configuration cohérente.
|
||||
WarningPasswordSetWithNoAccount=Un mot de passe a été fixé pour cet adhérent. Cependant, aucun compte d'utilisateur n'a été créé. Donc, ce mot de passe est stocké, mais ne peut être utilisé pour accéder à Dolibarr. Il peut être utilisé par un module/interface externe, mais si vous n'avez pas besoin de définir ni login ni mot de passe pour un adhérent, vous pouvez désactiver l'option «Gérer un login pour chaque adhérent" depuis la configuration du module Adhérents. Si vous avez besoin de gérer un login, mais pas de mot de passe, vous pouvez laisser ce champ vide pour éviter cet avertissement. Remarque: L'email peut également être utilisé comme login si l'adhérent est lié à un utilisateur.
|
||||
|
||||
@ -1898,13 +1898,15 @@ function top_menu_user()
|
||||
$( document ).ready(function() {
|
||||
$(document).on("click", function(event) {
|
||||
if (!$(event.target).closest("#topmenu-login-dropdown").length) {
|
||||
// Hide the menus.
|
||||
//console.log("close login dropdown");
|
||||
// Hide the menus.
|
||||
$("#topmenu-login-dropdown").removeClass("open");
|
||||
}
|
||||
});
|
||||
|
||||
$("#topmenu-login-dropdown .dropdown-toggle").on("click", function(event) {
|
||||
event.preventDefault();
|
||||
console.log("toggle login dropdown");
|
||||
event.preventDefault();
|
||||
$("#topmenu-login-dropdown").toggleClass("open");
|
||||
});
|
||||
|
||||
@ -1954,14 +1956,14 @@ function top_menu_bookmark()
|
||||
$( document ).ready(function() {
|
||||
$(document).on("click", function(event) {
|
||||
if (!$(event.target).closest("#topmenu-bookmark-dropdown").length) {
|
||||
console.log("close");
|
||||
//console.log("close bookmark dropdown - we click outside");
|
||||
// Hide the menus.
|
||||
$("#topmenu-bookmark-dropdown").removeClass("open");
|
||||
}
|
||||
});
|
||||
|
||||
$("#topmenu-bookmark-dropdown .dropdown-toggle").on("click", function(event) {
|
||||
console.log("toggle");
|
||||
console.log("toggle bookmark dropdown");
|
||||
openBookMarkDropDown();
|
||||
});
|
||||
|
||||
@ -2077,7 +2079,7 @@ function top_menu_search()
|
||||
// close drop down
|
||||
$(document).on("click", function(event) {
|
||||
if (!$(event.target).closest("#topmenu-global-search-dropdown").length) {
|
||||
console.log("click close");
|
||||
console.log("click close search - we click outside");
|
||||
// Hide the menus.
|
||||
$("#topmenu-global-search-dropdown").removeClass("open");
|
||||
}
|
||||
@ -2085,7 +2087,7 @@ function top_menu_search()
|
||||
|
||||
// Open drop down
|
||||
$("#topmenu-global-search-dropdown .dropdown-toggle").on("click", function(event) {
|
||||
console.log("click open");
|
||||
console.log("toggle search dropdown");
|
||||
openGlobalSearchDropDown();
|
||||
});
|
||||
|
||||
|
||||
@ -30,6 +30,11 @@ require_once DOL_DOCUMENT_ROOT."/core/class/commonobject.class.php";
|
||||
*/
|
||||
class Productbatch extends CommonObject
|
||||
{
|
||||
/**
|
||||
* Batches rules
|
||||
*/
|
||||
const BATCH_RULE_SELLBY_EATBY_DATES_FIRST = 1;
|
||||
|
||||
/**
|
||||
* @var string ID to identify managed object
|
||||
*/
|
||||
@ -540,4 +545,65 @@ class Productbatch extends CommonObject
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Return all batch for a product and a warehouse
|
||||
*
|
||||
* @param DoliDB $db Database object
|
||||
* @param int $fk_product Id of product
|
||||
* @param int $fk_warehouse Id of warehouse
|
||||
* @param int $qty_min [=NULL] Minimum quantity
|
||||
* @param string $sortfield [=NULL] List of sort fields, separated by comma. Example: 't1.fielda,t2.fieldb'
|
||||
* @param string $sortorder [=NULL] Sort order, separated by comma. Example: 'ASC,DESC';
|
||||
* @return int|array <0 if KO, array of batch
|
||||
*
|
||||
* @throws Exception
|
||||
*/
|
||||
public static function findAllForProduct($db, $fk_product, $fk_warehouse = 0, $qty_min = null, $sortfield = null, $sortorder = null)
|
||||
{
|
||||
$productBatchList = array();
|
||||
|
||||
dol_syslog(__METHOD__ . ' fk_product=' . $fk_product . ', fk_warehouse=' . $fk_warehouse . ', qty_min=' . $qty_min . ', sortfield=' . $sortfield . ', sortorder=' . $sortorder, LOG_DEBUG);
|
||||
|
||||
$sql = "SELECT";
|
||||
$sql .= " pl.rowid";
|
||||
$sql .= ", pl.fk_product";
|
||||
$sql .= ", pl.batch";
|
||||
$sql .= ", pl.sellby";
|
||||
$sql .= ", pl.eatby";
|
||||
$sql .= ", pb.qty";
|
||||
$sql .= " FROM " . MAIN_DB_PREFIX . "product_lot as pl";
|
||||
$sql .= " LEFT JOIN " . MAIN_DB_PREFIX . "product as p ON p.rowid = pl.fk_product";
|
||||
$sql .= " LEFT JOIN " . MAIN_DB_PREFIX . "product_batch AS pb ON pl.batch = pb.batch";
|
||||
$sql .= " LEFT JOIN " . MAIN_DB_PREFIX . "product_stock AS ps ON ps.rowid = pb.fk_product_stock";
|
||||
$sql .= " WHERE p.entity IN (" . getEntity('product') . ")";
|
||||
$sql .= " AND pl.fk_product = " . $fk_product;
|
||||
if ($fk_warehouse > 0) {
|
||||
$sql .= " AND ps.fk_entrepot = " . $fk_warehouse;
|
||||
}
|
||||
if ($qty_min !== null) {
|
||||
$sql .= " AND pb.qty > " . $qty_min;
|
||||
}
|
||||
$sql .= $db->order($sortfield, $sortorder);
|
||||
|
||||
$resql = $db->query($sql);
|
||||
if ($resql) {
|
||||
while ($obj = $db->fetch_object($resql)) {
|
||||
$productBatch = new self($db);
|
||||
$productBatch->id = $obj->rowid;
|
||||
$productBatch->fk_product = $obj->fk_product;
|
||||
$productBatch->batch = $obj->batch;
|
||||
$productBatch->eatby = $db->jdate($obj->eatby);
|
||||
$productBatch->sellby = $db->jdate($obj->sellby);
|
||||
$productBatch->qty = $obj->qty;
|
||||
$productBatchList[] = $productBatch;
|
||||
}
|
||||
$db->free($resql);
|
||||
|
||||
return $productBatchList;
|
||||
} else {
|
||||
dol_syslog(__METHOD__ . ' Error: ' . $db->lasterror(), LOG_ERR);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
217
htdocs/product/popucom.php
Normal file
217
htdocs/product/popucom.php
Normal file
@ -0,0 +1,217 @@
|
||||
<?php
|
||||
/* Copyright (C) 2001-2003 Rodolphe Quiedeville <rodolphe@quiedeville.org>
|
||||
* Copyright (C) 2004-2005 Laurent Destailleur <eldy@users.sourceforge.net>
|
||||
* Copyright (C) 2004 Eric Seigne <eric.seigne@ryxeo.com>
|
||||
* Copyright (C) 2005-2012 Regis Houssin <regis.houssin@inodbox.com>
|
||||
* Copyright (C) 2014 Marcos García <marcosgdf@gmail.com>
|
||||
* Copyright (C) 2015 Jean-François Ferry <jfefe@aternatik.fr>
|
||||
*
|
||||
* 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,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* 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 <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/**
|
||||
* \file htdocs/product/popucom.php
|
||||
* \ingroup commande, produit
|
||||
* \brief Liste des produits/services par popularite
|
||||
*/
|
||||
|
||||
require '../main.inc.php';
|
||||
require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
|
||||
|
||||
// Load translation files required by the page
|
||||
//Required to translate NbOfCommande
|
||||
$langs->load('commande');
|
||||
|
||||
$type=GETPOST("type", "int");
|
||||
|
||||
// Security check
|
||||
if (! empty($user->socid)) $socid=$user->socid;
|
||||
$result=restrictedArea($user, 'produit|service');
|
||||
|
||||
$limit = GETPOST('limit', 'int')?GETPOST('limit', 'int'):$conf->liste_limit;
|
||||
$sortfield = GETPOST("sortfield", 'alpha');
|
||||
$sortorder = GETPOST("sortorder", 'alpha');
|
||||
$page = GETPOST("page", 'int');
|
||||
if (empty($page) || $page == -1) { $page = 0; } // If $page is not defined, or '' or -1
|
||||
if (! $sortfield) $sortfield="c";
|
||||
if (! $sortorder) $sortorder="DESC";
|
||||
$offset = $limit * $page ;
|
||||
$pageprev = $page - 1;
|
||||
$pagenext = $page + 1;
|
||||
|
||||
|
||||
$staticproduct=new Product($db);
|
||||
|
||||
|
||||
/*
|
||||
* View
|
||||
*/
|
||||
|
||||
$helpurl='';
|
||||
if ($type == '0')
|
||||
{
|
||||
$helpurl='EN:Module_Products|FR:Module_Produits|ES:Módulo_Productos';
|
||||
}
|
||||
elseif ($type == '1')
|
||||
{
|
||||
$helpurl='EN:Module_Services_En|FR:Module_Services|ES:Módulo_Servicios';
|
||||
}
|
||||
else
|
||||
{
|
||||
$helpurl='EN:Module_Services_En|FR:Module_Services|ES:Módulo_Servicios';
|
||||
}
|
||||
$title=$langs->trans("Statistics");
|
||||
|
||||
|
||||
llxHeader('', $title, $helpurl);
|
||||
|
||||
print load_fiche_titre($title, $mesg, 'products');
|
||||
|
||||
|
||||
$param = '';
|
||||
$title = $langs->trans("ListProductServiceByPopularity");
|
||||
if ((string) $type == '1') {
|
||||
$title = $langs->trans("ListServiceByPopularity");
|
||||
}
|
||||
if ((string) $type == '0') {
|
||||
$title = $langs->trans("ListProductByPopularity");
|
||||
}
|
||||
|
||||
if ($type != '') $param .= '&type='.$type;
|
||||
|
||||
|
||||
$h=0;
|
||||
$head = array();
|
||||
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/stats/card.php?id=all';
|
||||
$head[$h][1] = $langs->trans("Chart");
|
||||
$head[$h][2] = 'chart';
|
||||
$h++;
|
||||
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/popuprop.php';
|
||||
$head[$h][1] = $langs->trans("PopuProp");
|
||||
$head[$h][2] = 'popularityprop';
|
||||
$h++;
|
||||
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/popucom.php';
|
||||
$head[$h][1] = $langs->trans("PopuCom");
|
||||
$head[$h][2] = 'popularitycommande';
|
||||
$h++;
|
||||
|
||||
dol_fiche_head($head, 'popularitycommande', $langs->trans("Statistics"), -1);
|
||||
|
||||
|
||||
// Array of liens to show
|
||||
$infoprod=array();
|
||||
|
||||
|
||||
// Add lines for commande
|
||||
$sql = "SELECT p.rowid, p.label, p.ref, p.fk_product_type as type, SUM(pd.qty) as c";
|
||||
$sql.= " FROM ".MAIN_DB_PREFIX."commandedet as pd";
|
||||
$sql.= ", ".MAIN_DB_PREFIX."product as p";
|
||||
$sql.= ' WHERE p.entity IN ('.getEntity('product').')';
|
||||
$sql.= " AND p.rowid = pd.fk_product";
|
||||
if ($type !== '') {
|
||||
$sql.= " AND fk_product_type = ".$type;
|
||||
}
|
||||
$sql.= " GROUP BY p.rowid, p.label, p.ref, p.fk_product_type";
|
||||
|
||||
$result=$db->query($sql);
|
||||
if ($result)
|
||||
{
|
||||
$totalnboflines = $db->num_rows($result);
|
||||
}
|
||||
|
||||
$sql.= $db->order($sortfield, $sortorder);
|
||||
$sql.= $db->plimit($limit+1, $offset);
|
||||
|
||||
$resql=$db->query($sql);
|
||||
if ($resql)
|
||||
{
|
||||
$num = $db->num_rows($resql);
|
||||
$i = 0;
|
||||
|
||||
while ($i < $num)
|
||||
{
|
||||
$objp = $db->fetch_object($resql);
|
||||
|
||||
$infoprod[$objp->rowid]=array('type'=>$objp->type, 'ref'=>$objp->ref, 'label'=>$objp->label);
|
||||
$infoprod[$objp->rowid]['nblinecommande']=$objp->c;
|
||||
|
||||
$i++;
|
||||
}
|
||||
$db->free($resql);
|
||||
}
|
||||
else
|
||||
{
|
||||
dol_print_error($db);
|
||||
}
|
||||
//var_dump($infoprod);
|
||||
|
||||
|
||||
print_barre_liste($title, $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, "", $num, $totalnboflines, '');
|
||||
|
||||
print '<table class="noborder centpercent">';
|
||||
|
||||
print "<tr class=\"liste_titre\">";
|
||||
print_liste_field_titre('Ref', $_SERVER["PHP_SELF"], 'p.ref', '', $param, '', $sortfield, $sortorder);
|
||||
print_liste_field_titre('Type', $_SERVER["PHP_SELF"], 'p.fk_product_type', '', $param, '', $sortfield, $sortorder);
|
||||
print_liste_field_titre('Label', $_SERVER["PHP_SELF"], 'p.label', '', $param, '', $sortfield, $sortorder);
|
||||
print_liste_field_titre('NbOfQtyInOrders', $_SERVER["PHP_SELF"], 'c', '', $param, '', $sortfield, $sortorder, 'right ');
|
||||
print "</tr>\n";
|
||||
|
||||
foreach($infoprod as $prodid => $vals)
|
||||
{
|
||||
// Multilangs
|
||||
if (! empty($conf->global->MAIN_MULTILANGS)) // si l'option est active
|
||||
{
|
||||
$sql = "SELECT label";
|
||||
$sql.= " FROM ".MAIN_DB_PREFIX."product_lang";
|
||||
$sql.= " WHERE fk_product=".$prodid;
|
||||
$sql.= " AND lang='". $langs->getDefaultLang() ."'";
|
||||
$sql.= " LIMIT 1";
|
||||
|
||||
$resultp = $db->query($sql);
|
||||
if ($resultp)
|
||||
{
|
||||
$objtp = $db->fetch_object($resultp);
|
||||
if (! empty($objtp->label)) $vals['label'] = $objtp->label;
|
||||
}
|
||||
}
|
||||
|
||||
print "<tr>";
|
||||
print '<td><a href="'.DOL_URL_ROOT.'/product/stats/card.php?id='.$prodid.'">';
|
||||
if ($vals['type'] == 1) print img_object($langs->trans("ShowService"), "service");
|
||||
else print img_object($langs->trans("ShowProduct"), "product");
|
||||
print " ";
|
||||
print $vals['ref'].'</a></td>';
|
||||
print '<td>';
|
||||
if ($vals['type'] == 1) print $langs->trans("Service");
|
||||
else print $langs->trans("Product");
|
||||
print '</td>';
|
||||
print '<td>'.$vals['label'].'</td>';
|
||||
print '<td class="right">'.$vals['nblinecommande'].'</td>';
|
||||
print "</tr>\n";
|
||||
$i++;
|
||||
}
|
||||
|
||||
print "</table>";
|
||||
|
||||
|
||||
|
||||
dol_fiche_end();
|
||||
|
||||
// End of page
|
||||
llxFooter();
|
||||
$db->close();
|
||||
@ -99,11 +99,16 @@ $head[$h][1] = $langs->trans("Chart");
|
||||
$head[$h][2] = 'chart';
|
||||
$h++;
|
||||
|
||||
$head[$h][0] = $_SERVER['PHP_SELF'];
|
||||
$head[$h][1] = $title;
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/popuprop.php';
|
||||
$head[$h][1] = $langs->trans("PopuProp");
|
||||
$head[$h][2] = 'popularityprop';
|
||||
$h++;
|
||||
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/popucom.php';
|
||||
$head[$h][1] = $langs->trans("PopuCom");
|
||||
$head[$h][2] = 'popularitycommande';
|
||||
$h++;
|
||||
|
||||
dol_fiche_head($head, 'popularityprop', $langs->trans("Statistics"), -1);
|
||||
|
||||
|
||||
|
||||
@ -161,10 +161,15 @@ if (empty($id) & empty($ref))
|
||||
}
|
||||
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/popuprop.php'.($type != '' ? '?type='.$type : '');
|
||||
$head[$h][1] = $title;
|
||||
$head[$h][1] = $langs->trans("PopuProp");
|
||||
$head[$h][2] = 'popularityprop';
|
||||
$h++;
|
||||
|
||||
$head[$h][0] = DOL_URL_ROOT.'/product/popucom.php'.($type != '' ? '?type='.$type : '');
|
||||
$head[$h][1] = $langs->trans("PopuCom");
|
||||
$head[$h][2] = 'popularitycommande';
|
||||
$h++;
|
||||
|
||||
dol_fiche_head($head, 'chart', $langs->trans("Statistics"), -1);
|
||||
}
|
||||
|
||||
|
||||
@ -179,7 +179,7 @@ if (!empty($conf->stock->enabled))
|
||||
{
|
||||
print '<tr class="oddeven"><td>'.$langs->trans("CashDeskDoNotDecreaseStock").'</td>'; // Force warehouse (this is not a default value)
|
||||
print '<td>';
|
||||
if (empty($conf->productbatch->enabled)) {
|
||||
if (empty($conf->productbatch->enabled) || !empty($conf->global->CASHDESK_FORCE_DECREASE_STOCK)) {
|
||||
print $form->selectyesno('CASHDESK_NO_DECREASE_STOCK'.$terminal, $conf->global->{'CASHDESK_NO_DECREASE_STOCK'.$terminal}, 1);
|
||||
}
|
||||
else
|
||||
@ -207,6 +207,13 @@ if (!empty($conf->stock->enabled))
|
||||
print '<span class="opacitymedium">'.$langs->trans("StockDecreaseForPointOfSaleDisabled").'</span>';
|
||||
}
|
||||
print '</td></tr>';
|
||||
|
||||
if (!empty($conf->productbatch->enabled) && !empty($conf->global->CASHDESK_FORCE_DECREASE_STOCK) && !$conf->global->{'CASHDESK_NO_DECREASE_STOCK'.$terminal}) {
|
||||
print '<tr class="oddeven"><td>' . $langs->trans('CashDeskForceDecreaseStockLabel') . '</td>';
|
||||
print '<td>';
|
||||
print '<span class="opacitymedium">' . $langs->trans('CashDeskForceDecreaseStockDesc') . '</span>';
|
||||
print '</td></tr>';
|
||||
}
|
||||
}
|
||||
|
||||
if ($conf->global->TAKEPOS_PRINT_METHOD == "receiptprinter") {
|
||||
|
||||
@ -190,7 +190,12 @@ if ($action == 'valid' && $user->rights->facture->creer)
|
||||
|
||||
$constantforkey = 'CASHDESK_ID_WAREHOUSE'.$_SESSION["takeposterminal"];
|
||||
dol_syslog("Validate invoice with stock change into warehouse defined into constant ".$constantforkey." = ".$conf->global->$constantforkey);
|
||||
$res = $invoice->validate($user, '', $conf->global->$constantforkey);
|
||||
$batch_rule = 0;
|
||||
if (!empty($conf->productbatch->enabled) && !empty($conf->global->CASHDESK_FORCE_DECREASE_STOCK)) {
|
||||
require_once DOL_DOCUMENT_ROOT . '/product/class/productbatch.class.php';
|
||||
$batch_rule = Productbatch::BATCH_RULE_SELLBY_EATBY_DATES_FIRST;
|
||||
}
|
||||
$res = $invoice->validate($user, '', $conf->global->$constantforkey, 0, $batch_rule);
|
||||
|
||||
$conf->global->STOCK_CALCULATE_ON_BILL = $savconst;
|
||||
}
|
||||
@ -441,6 +446,10 @@ if ($action == "updatereduction")
|
||||
if ($action == "order" and $placeid != 0)
|
||||
{
|
||||
include_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php';
|
||||
if ($conf->global->TAKEPOS_PRINT_METHOD == "receiptprinter"){
|
||||
require_once DOL_DOCUMENT_ROOT.'/core/class/dolreceiptprinter.class.php';
|
||||
$printer = new dolReceiptPrinter($db);
|
||||
}
|
||||
|
||||
$headerorder = '<html><br><b>'.$langs->trans('Place').' '.$place.'<br><table width="65%"><thead><tr><th class="left">'.$langs->trans("Label").'</th><th class="right">'.$langs->trans("Qty").'</th></tr></thead><tbody>';
|
||||
$footerorder = '</tbody></table>'.dol_print_date(dol_now(), 'dayhour').'<br></html>';
|
||||
@ -458,13 +467,20 @@ if ($action == "order" and $placeid != 0)
|
||||
$result = array_intersect($catsprinter1, $existing);
|
||||
$count = count($result);
|
||||
if ($count > 0) {
|
||||
$sql = "UPDATE ".MAIN_DB_PREFIX."facturedet set special_code='4' where rowid=".$line->id;
|
||||
$sql = "UPDATE ".MAIN_DB_PREFIX."facturedet set special_code='1' where rowid=".$line->id; //Set to print on printer 1
|
||||
$db->query($sql);
|
||||
$order_receipt_printer1 .= '<tr>'.$line->product_label.'<td class="right">'.$line->qty;
|
||||
if (!empty($line->array_options['options_order_notes'])) $order_receipt_printer1 .= "<br>(".$line->array_options['options_order_notes'].")";
|
||||
$order_receipt_printer1 .= '</td></tr>';
|
||||
}
|
||||
}
|
||||
if ($conf->global->TAKEPOS_PRINT_METHOD == "receiptprinter"){
|
||||
$invoice->fetch($placeid); //Reload object before send to printer
|
||||
$ret = $printer->sendToPrinter($invoice, $conf->global->{'TAKEPOS_TEMPLATE_TO_USE_FOR_ORDERS'.$_SESSION["takeposterminal"]}, $conf->global->{'TAKEPOS_PRINTER_TO_USE'.$_SESSION["takeposterminal"]}); // PRINT TO PRINTER 1
|
||||
}
|
||||
$sql = "UPDATE ".MAIN_DB_PREFIX."facturedet set special_code='4' where special_code='1' and fk_facture=".$invoice->id; // Set as printed
|
||||
$db->query($sql);
|
||||
$invoice->fetch($placeid); //Reload object after set lines as printed
|
||||
|
||||
foreach ($invoice->lines as $line)
|
||||
{
|
||||
@ -476,15 +492,20 @@ if ($action == "order" and $placeid != 0)
|
||||
$result = array_intersect($catsprinter2, $existing);
|
||||
$count = count($result);
|
||||
if ($count > 0) {
|
||||
$sql = "UPDATE ".MAIN_DB_PREFIX."facturedet set special_code='4' where rowid=".$line->id;
|
||||
$sql = "UPDATE ".MAIN_DB_PREFIX."facturedet set special_code='2' where rowid=".$line->id; //Set to print on printer 2
|
||||
$db->query($sql);
|
||||
$order_receipt_printer2 .= '<tr>'.$line->product_label.'<td class="right">'.$line->qty;
|
||||
if (!empty($line->array_options['options_order_notes'])) $order_receipt_printer2 .= "<br>(".$line->array_options['options_order_notes'].")";
|
||||
$order_receipt_printer2 .= '</td></tr>';
|
||||
}
|
||||
}
|
||||
|
||||
$invoice->fetch($placeid);
|
||||
if ($conf->global->TAKEPOS_PRINT_METHOD == "receiptprinter"){
|
||||
$invoice->fetch($placeid); //Reload object before send to printer
|
||||
$ret = $printer->sendToPrinter($invoice, $conf->global->{'TAKEPOS_TEMPLATE_TO_USE_FOR_ORDERS'.$_SESSION["takeposterminal"]}, $conf->global->{'TAKEPOS_PRINTER_TO_USE'.$_SESSION["takeposterminal"]}); // PRINT TO PRINTER 2
|
||||
}
|
||||
$sql = "UPDATE ".MAIN_DB_PREFIX."facturedet set special_code='4' where special_code='2' and fk_facture=".$invoice->id; // Set as printed
|
||||
$db->query($sql);
|
||||
$invoice->fetch($placeid); //Reload object after set lines as printed
|
||||
}
|
||||
|
||||
$sectionwithinvoicelink = '';
|
||||
|
||||
@ -9,7 +9,7 @@ button.dropdown-item.global-search-item {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
.open>.dropdown-search, .open>.dropdown-bookmark, .open>.dropdown-menu{
|
||||
.open>.dropdown-search, .open>.dropdown-bookmark, .open>.dropdown-menu, .dropdown dd ul.open {
|
||||
display: block;
|
||||
}
|
||||
|
||||
|
||||
@ -4983,7 +4983,7 @@ input.select2-input {
|
||||
}
|
||||
.select2-container--default .select2-selection--single .select2-selection__rendered {
|
||||
color: var(--colortext);
|
||||
background-color: var(--colorbackvmenu1);
|
||||
/* background-color: var(--colorbackvmenu1); */
|
||||
}
|
||||
.select2-default {
|
||||
color: #999 !important;
|
||||
@ -5079,8 +5079,8 @@ input.select2-input {
|
||||
box-shadow: none !important;
|
||||
}
|
||||
.select2-dropdown {
|
||||
background-color: var(--colorbackvmenu1);
|
||||
border: 1px solid var(--colorbackvmenu1);;
|
||||
/*background-color: var(--colorbackvmenu1);
|
||||
border: 1px solid var(--colorbackvmenu1); */
|
||||
box-shadow: 1px 2px 10px var(--colorbackvmenu1);
|
||||
}
|
||||
.select2-dropdown-open {
|
||||
@ -5405,9 +5405,9 @@ dl.dropdown {
|
||||
.dropdown dd ul li span {
|
||||
color: #888;
|
||||
}
|
||||
.dropdown dd ul li a:hover {
|
||||
/*.dropdown dd ul li a:hover {
|
||||
background-color: var(--inputbackgroundcolor);
|
||||
}
|
||||
}*/
|
||||
dd.dropdowndd ul li {
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
|
||||
Loading…
Reference in New Issue
Block a user