commit de009a3fee7e0471c3e095ce92d8708ff2b42597
Author: Moritz Bunkus <m.bunkus@linet.de>
Date:   Tue Jun 7 13:30:46 2016 +0200

    Zahlungsbedingungen: Unterscheidung zwischen Angeboten/Aufträgen und Rechnungen
    
    Dies führt ein neues Attribut »payment_terms.description_long_invoice«
    und dazugehörige Übersetzungen in »generic_translation« ein.
    
    Die Druckvariable »payment_terms« wird nun in Abhängigkeit vom
    auszudruckenden Beleg gesetzt:
    
    1. Für Verkaufsrechnungen wird zuerst eine Übersetzung von
       »description_long_invoice« für die ausgewählte Sprache gesucht. Falls
       die leer ist oder keine Sprache ausgewählt, so wird die nicht
       übersetzte »description_long_invoice« genommen. Ist auch die leer, so
       erfolgt ein Fallback auf 2.
    
    2. Für alle anderen Belege oder falls bei 1. nichts heraus gekommen ist,
       wird wie vor dieser Änderung eine Übersetzung von »description_long«
       für die ausgewählte Sprache gesucht. Falls die leer ist oder keine
       Sprache ausgewählt, so wird die nicht übersetzte »description_long«
       genommen.

diff --git a/SL/Controller/PaymentTerm.pm b/SL/Controller/PaymentTerm.pm
index 5064f756d..f1eeb4477 100644
--- a/SL/Controller/PaymentTerm.pm
+++ b/SL/Controller/PaymentTerm.pm
@@ -110,6 +110,7 @@ sub create_or_update {
   $self->{payment_term}->save;
   foreach my $language (@{ $self->{languages} }) {
     $self->{payment_term}->save_attribute_translation('description_long', $language, $::form->{"translation_" . $language->id});
+    $self->{payment_term}->save_attribute_translation('description_long_invoice', $language, $::form->{"translation_invoice_" . $language->id});
   }
 
   flash_later('info', $is_new ? $::locale->text('The payment term has been created.') : $::locale->text('The payment term has been saved.'));
diff --git a/SL/DB/Manager/PaymentTerm.pm b/SL/DB/Manager/PaymentTerm.pm
index abe6837fa..895410a77 100644
--- a/SL/DB/Manager/PaymentTerm.pm
+++ b/SL/DB/Manager/PaymentTerm.pm
@@ -14,7 +14,7 @@ __PACKAGE__->make_manager_methods;
 sub _sort_spec {
   return ( default => [ 'sortkey', 1 ],
            columns => { SIMPLE => 'ALL',
-                        map { ( $_ => "lower(payment_terms.${_})" ) } qw(description description_long),
+                        map { ( $_ => "lower(payment_terms.${_})" ) } qw(description description_long description_long_invoice),
                       });
 }
 
diff --git a/SL/DB/MetaSetup/PaymentTerm.pm b/SL/DB/MetaSetup/PaymentTerm.pm
index bc0587e7c..ed52a9149 100644
--- a/SL/DB/MetaSetup/PaymentTerm.pm
+++ b/SL/DB/MetaSetup/PaymentTerm.pm
@@ -9,17 +9,18 @@ use parent qw(SL::DB::Object);
 __PACKAGE__->meta->table('payment_terms');
 
 __PACKAGE__->meta->columns(
-  auto_calculation => { type => 'boolean', not_null => 1 },
-  description      => { type => 'text' },
-  description_long => { type => 'text' },
-  id               => { type => 'integer', not_null => 1, sequence => 'id' },
-  itime            => { type => 'timestamp', default => 'now()' },
-  mtime            => { type => 'timestamp' },
-  percent_skonto   => { type => 'float', scale => 4 },
-  ranking          => { type => 'integer' },
-  sortkey          => { type => 'integer', not_null => 1 },
-  terms_netto      => { type => 'integer' },
-  terms_skonto     => { type => 'integer' },
+  auto_calculation         => { type => 'boolean', not_null => 1 },
+  description              => { type => 'text' },
+  description_long         => { type => 'text' },
+  description_long_invoice => { type => 'text' },
+  id                       => { type => 'integer', not_null => 1, sequence => 'id' },
+  itime                    => { type => 'timestamp', default => 'now()' },
+  mtime                    => { type => 'timestamp' },
+  percent_skonto           => { type => 'float', precision => 4, scale => 4 },
+  ranking                  => { type => 'integer' },
+  sortkey                  => { type => 'integer', not_null => 1 },
+  terms_netto              => { type => 'integer' },
+  terms_skonto             => { type => 'integer' },
 );
 
 __PACKAGE__->meta->primary_key_columns([ 'id' ]);
diff --git a/SL/DO.pm b/SL/DO.pm
index a012ddb13..c8ef14549 100644
--- a/SL/DO.pm
+++ b/SL/DO.pm
@@ -1055,7 +1055,11 @@ sub order_details {
   $h_bin_wh->finish();
 
   $form->{delivery_term} = SL::DB::Manager::DeliveryTerm->find_by(id => $form->{delivery_term_id} || undef);
-  $form->{delivery_term}->description_long($form->{delivery_term}->translated_attribute('description_long', $form->{language_id})) if $form->{delivery_term} && $form->{language_id};
+  if ($form->{delivery_term} && $form->{language_id}) {
+    $form->{delivery_term}->description_long(        $form->{delivery_term}->translated_attribute('description_long',         $form->{language_id}));
+    $form->{delivery_term}->description_long_invoice($form->{delivery_term}->translated_attribute('description_long_invoice', $form->{language_id}));
+  }
+
   $form->{department}    = SL::DB::Manager::Department->find_by(id => $form->{department_id})->description if $form->{department_id};
 
   $form->{username} = $myconfig->{name};
diff --git a/SL/Form.pm b/SL/Form.pm
index fbcbe56f3..b5af00359 100644
--- a/SL/Form.pm
+++ b/SL/Form.pm
@@ -1697,16 +1697,17 @@ sub get_default_currency {
 }
 
 sub set_payment_options {
-  my ($self, $myconfig, $transdate) = @_;
+  my ($self, $myconfig, $transdate, $type) = @_;
 
   my $terms = $self->{payment_id} ? SL::DB::PaymentTerm->new(id => $self->{payment_id})->load : undef;
   return if !$terms;
 
+  my $is_invoice                = $type =~ m{invoice}i;
+
   $transdate                  ||= $self->{invdate} || $self->{transdate};
   my $due_date                  = $self->{duedate} || $self->{reqdate};
 
   $self->{$_}                   = $terms->$_ for qw(terms_netto terms_skonto percent_skonto);
-  $self->{payment_terms}        = $terms->description_long;
   $self->{payment_description}  = $terms->description;
   $self->{netto_date}           = $terms->calc_date(reference_date => $transdate, due_date => $due_date, terms => 'net')->to_kivitendo;
   $self->{skonto_date}          = $terms->calc_date(reference_date => $transdate, due_date => $due_date, terms => 'discount')->to_kivitendo;
@@ -1739,39 +1740,26 @@ sub set_payment_options {
   }
 
   if ($self->{"language_id"}) {
-    my $dbh   = $self->get_standard_dbh($myconfig);
-    my $query =
-      qq|SELECT t.translation, l.output_numberformat, l.output_dateformat, l.output_longdates | .
-      qq|FROM generic_translations t | .
-      qq|LEFT JOIN language l ON t.language_id = l.id | .
-      qq|WHERE (t.language_id = ?)
-           AND (t.translation_id = ?)
-           AND (t.translation_type = 'SL::DB::PaymentTerm/description_long')|;
-    my ($description_long, $output_numberformat, $output_dateformat,
-      $output_longdates) =
-      selectrow_query($self, $dbh, $query,
-                      $self->{"language_id"}, $self->{"payment_id"});
-
-    $self->{payment_terms} = $description_long if ($description_long);
-
-    if ($output_dateformat) {
+    my $language             = SL::DB::Language->new(id => $self->{language_id})->load;
+
+    $self->{payment_terms}   = $type =~ m{invoice}i ? $terms->translated_attribute('description_long_invoice', $language->id) : undef;
+    $self->{payment_terms} ||= $terms->translated_attribute('description_long', $language->id);
+
+    if ($language->output_dateformat) {
       foreach my $key (qw(netto_date skonto_date)) {
-        $self->{$key} =
-          $main::locale->reformat_date($myconfig, $self->{$key},
-                                       $output_dateformat,
-                                       $output_longdates);
+        $self->{$key} = $::locale->reformat_date($myconfig, $self->{$key}, $language->output_dateformat, $language->output_longdates);
       }
     }
 
-    if ($output_numberformat &&
-        ($output_numberformat ne $myconfig->{"numberformat"})) {
-      my $saved_numberformat = $myconfig->{"numberformat"};
-      $myconfig->{"numberformat"} = $output_numberformat;
-      map { $formatted_amounts{$_} = $self->format_amount($myconfig, $amounts{$_}) } keys %amounts;
-      $myconfig->{"numberformat"} = $saved_numberformat;
+    if ($language->output_numberformat && ($language->output_numberformat ne $myconfig->{numberformat})) {
+      local $myconfig->{numberformat};
+      $myconfig->{"numberformat"} = $language->output_numberformat;
+      $formatted_amounts{$_} = $self->format_amount($myconfig, $amounts{$_}) for keys %amounts;
     }
   }
 
+  $self->{payment_terms} =  $self->{payment_terms} || ($is_invoice ? $terms->description_long_invoice : undef) || $terms->description_long;
+
   $self->{payment_terms} =~ s/<%netto_date%>/$self->{netto_date}/g;
   $self->{payment_terms} =~ s/<%skonto_date%>/$self->{skonto_date}/g;
   $self->{payment_terms} =~ s/<%currency%>/$self->{currency}/g;
diff --git a/SL/IS.pm b/SL/IS.pm
index 08846cb08..5b02041ba 100644
--- a/SL/IS.pm
+++ b/SL/IS.pm
@@ -525,10 +525,14 @@ sub invoice_details {
   $form->{invtotal} = $form->format_amount($myconfig, $form->{invtotal}, 2);
   $form->{paid}     = $form->format_amount($myconfig, $form->{paid}, 2);
 
-  $form->set_payment_options($myconfig, $form->{invdate});
+  $form->set_payment_options($myconfig, $form->{invdate}, 'sales_invoice');
 
   $form->{delivery_term} = SL::DB::Manager::DeliveryTerm->find_by(id => $form->{delivery_term_id} || undef);
-  $form->{delivery_term}->description_long($form->{delivery_term}->translated_attribute('description_long', $form->{language_id})) if $form->{delivery_term} && $form->{language_id};
+  if ($form->{delivery_term} && $form->{language_id}) {
+    $form->{delivery_term}->description_long(        $form->{delivery_term}->translated_attribute('description_long',         $form->{language_id}));
+    $form->{delivery_term}->description_long_invoice($form->{delivery_term}->translated_attribute('description_long_invoice', $form->{language_id}));
+  }
+
   $form->{department}    = SL::DB::Manager::Department->find_by(id => $form->{department_id})->description if $form->{department_id};
 
   $form->{username} = $myconfig->{name};
diff --git a/SL/OE.pm b/SL/OE.pm
index 61af6211c..2e28f71e4 100644
--- a/SL/OE.pm
+++ b/SL/OE.pm
@@ -1584,18 +1584,17 @@ sub order_details {
   # format amounts
   $form->{quototal} = $form->{ordtotal} = $form->format_amount($myconfig, $form->{ordtotal}, 2);
 
-  if ($form->{type} =~ /_quotation/) {
-    $form->set_payment_options($myconfig, $form->{quodate});
-  } else {
-    $form->set_payment_options($myconfig, $form->{orddate});
-  }
+  $form->set_payment_options($myconfig, $form->{$form->{type} =~ /_quotation/ ? 'quodate' : 'orddate'}, $form->{type});
 
   $form->{username} = $myconfig->{name};
 
   $dbh->disconnect;
 
   $form->{delivery_term} = SL::DB::Manager::DeliveryTerm->find_by(id => $form->{delivery_term_id} || undef);
-  $form->{delivery_term}->description_long($form->{delivery_term}->translated_attribute('description_long', $form->{language_id})) if $form->{delivery_term} && $form->{language_id};
+  if ($form->{delivery_term} && $form->{language_id}) {
+    $form->{delivery_term}->description_long(        $form->{delivery_term}->translated_attribute('description_long',         $form->{language_id}));
+    $form->{delivery_term}->description_long_invoice($form->{delivery_term}->translated_attribute('description_long_invoice', $form->{language_id}));
+  }
 
   $form->{order} = SL::DB::Manager::Order->find_by(id => $form->{id}) if $form->{id};
 
diff --git a/locale/de/all b/locale/de/all
index f04e7696c..f34d1b110 100755
--- a/locale/de/all
+++ b/locale/de/all
@@ -1633,6 +1633,8 @@ $self->{texts} = {
   'Logout now'                  => 'kivitendo jetzt verlassen',
   'Long Dates'                  => 'Lange Monatsnamen',
   'Long Description'            => 'Langtext',
+  'Long Description (invoices)' => 'Langtext (Rechnungen)',
+  'Long Description (quotations & orders)' => 'Langtext (Angebote & Aufträge)',
   'Luxembourg'                  => 'Luxemburg',
   'MAILED'                      => 'Gesendet',
   'MD'                          => 'PT',
@@ -2704,6 +2706,8 @@ $self->{texts} = {
   'Text field variables: \'WIDTH=w HEIGHT=h\' sets the width and height of the text field. They default to 30 and 5 respectively.' => 'Textfelder: \'WIDTH=w HEIGHT=h\' setzen die Breite und die H&ouml;he des Textfeldes. Wenn nicht anders angegeben, so werden sie 30 Zeichen breit und f&uuml;nf Zeichen hoch dargestellt.',
   'Text variables: \'MAXLENGTH=n\' sets the maximum entry length to \'n\'.' => 'Textzeilen: \'MAXLENGTH=n\' setzt eine Maximall&auml;nge von n Zeichen.',
   'Text, text field and number variables: The default value will be used as-is.' => 'Textzeilen, Textfelder und Zahlenvariablen: Der Standardwert wird so wie er ist &uuml;bernommen.',
+  'Texts for invoices'          => 'Texte für Rechnungen',
+  'Texts for quotations & orders' => 'Texte für Angebote & Aufträge',
   'That export does not exist.' => 'Dieser Export existiert nicht.',
   'That is why kivitendo could not find a default currency.' => 'Daher konnte kivitendo keine Standardwährung finden.',
   'The \'name\' is the field shown to the user during login.' => 'Der \'Name\' ist derjenige, der dem Benutzer beim Login angezeigt wird.',
diff --git a/sql/Pg-upgrade2/payment_terms_for_invoices.sql b/sql/Pg-upgrade2/payment_terms_for_invoices.sql
new file mode 100644
index 000000000..6b6653d41
--- /dev/null
+++ b/sql/Pg-upgrade2/payment_terms_for_invoices.sql
@@ -0,0 +1,20 @@
+-- @tag: payment_terms_for_invoices
+-- @description: Unterscheidung in Zahlungsbedingungen für Angebote/Aufträge und Rechnungen
+-- @depends: release_3_4_0
+ALTER TABLE payment_terms ADD COLUMN description_long_invoice TEXT;
+UPDATE payment_terms SET description_long_invoice = description_long;
+
+INSERT INTO generic_translations (translation_type, language_id, translation_id, translation)
+SELECT translation_type || '_invoice', language_id, translation_id, translation
+FROM generic_translations
+WHERE translation_type = 'SL::DB::PaymentTerm/description_long';
+
+CREATE OR REPLACE FUNCTION generic_translations_delete_on_payment_terms_delete_trigger()
+RETURNS TRIGGER AS $$
+  BEGIN
+    DELETE FROM generic_translations
+    WHERE (translation_id = OLD.id)
+      AND (translation_type IN ('SL::DB::PaymentTerm/description_long', 'SL::DB::PaymentTerm/description_long_invoice'));
+    RETURN OLD;
+  END;
+$$ LANGUAGE plpgsql;
diff --git a/templates/webpages/payment_term/form.html b/templates/webpages/payment_term/form.html
index c77e719f1..df09a0161 100755
--- a/templates/webpages/payment_term/form.html
+++ b/templates/webpages/payment_term/form.html
@@ -6,6 +6,11 @@
 [%- INCLUDE 'common/flash.html' %]
 
   <table>
+   <tr class="listheading">
+    <th></th>
+    <th>[% LxERP.t8("General settings") %]</th>
+   </tr>
+
    <tr>
     <td>[%- 'Description' | $T8 %]</td>
     <td>
@@ -13,22 +18,6 @@
     </td>
    </tr>
 
-   <tr>
-    <td>[%- 'Long Description' | $T8 %]</td>
-    <td>
-     <input name="payment_term.description_long" value="[%- HTML.escape(SELF.payment_term.description_long) %]" size="60">
-    </td>
-   </tr>
-
-   [%- FOREACH language = SELF.languages %]
-    <tr>
-     <td>[%- HTML.escape(language.description) %] ([%- LxERP.t8('Translation') %])</td>
-     <td>
-      <input name="translation_[% language.id %]" value="[%- HTML.escape(SELF.payment_term.translated_attribute('description_long', language, 1)) %]" size="60">
-     </td>
-    </tr>
-   [%- END %]
-
    <tr>
     <td>[% LxERP.t8("Calculate due date automatically") %]</td>
     <td>[% L.yes_no_tag("payment_term.auto_calculation", SELF.payment_term.auto_calculation, "data-auto-calculation-toggle"="1") %]</td>
@@ -54,6 +43,36 @@
      <input name="payment_term.percent_skonto_as_percent" value="[%- HTML.escape(SELF.payment_term.percent_skonto_as_percent) %]" size="6">%
     </td>
    </tr>
+
+   <tr class="listheading">
+    <th></th>
+    <th>[% LxERP.t8("Texts for quotations & orders") %]</th>
+    <th>[% LxERP.t8("Texts for invoices") %]</th>
+   </tr>
+
+   <tr>
+    <td>[%- 'Long Description' | $T8 %]</td>
+    <td>
+     <input name="payment_term.description_long" value="[%- HTML.escape(SELF.payment_term.description_long) %]" size="60">
+    </td>
+
+    <td>
+     <input name="payment_term.description_long_invoice" value="[%- HTML.escape(SELF.payment_term.description_long_invoice) %]" size="60">
+    </td>
+   </tr>
+
+   [%- FOREACH language = SELF.languages %]
+    <tr>
+     <td>[%- HTML.escape(language.description) %] ([%- LxERP.t8('Translation') %])</td>
+     <td>
+      <input name="translation_[% language.id %]" value="[%- HTML.escape(SELF.payment_term.translated_attribute('description_long', language, 1)) %]" size="60">
+     </td>
+
+     <td>
+      <input name="translation_invoice_[% language.id %]" value="[%- HTML.escape(SELF.payment_term.translated_attribute('description_long_invoice', language, 1)) %]" size="60">
+     </td>
+    </tr>
+   [%- END %]
   </table>
 
   <p>
diff --git a/templates/webpages/payment_term/list.html b/templates/webpages/payment_term/list.html
index d2f4748b1..782a06763 100644
--- a/templates/webpages/payment_term/list.html
+++ b/templates/webpages/payment_term/list.html
@@ -15,7 +15,8 @@
     <tr class="listheading">
      <th align="center"><img src="image/updown.png" alt="[%- LxERP.t8('reorder item') %]"></th>
      <th>[%- 'Description' | $T8 %]</th>
-     <th>[%- 'Long Description' | $T8 %]</th>
+     <th>[%- 'Long Description (quotations & orders)' | $T8 %]</th>
+     <th>[%- 'Long Description (invoices)' | $T8 %]</th>
      <th>[% 'Automatic date calculation' | $T8 %]</th>
      <th align="right">[%- 'Netto Terms' | $T8 %]</th>
      <th align="right">[%- 'Skonto Terms' | $T8 %]</th>
@@ -33,6 +34,7 @@
       </a>
      </td>
      <td>[%- HTML.escape(payment_term.description_long) %]</td>
+     <td>[%- HTML.escape(payment_term.description_long_invoice) %]</td>
      <td>[% IF payment_term.auto_calculation %][% LxERP.t8("yes") %][% ELSE %][% LxERP.t8("no") %][% END %]</td>
      <td align="right">[%- HTML.escape(payment_term.terms_netto_as_number) %]</td>
      <td align="right">[%- HTML.escape(payment_term.terms_skonto_as_number) %]</td>
