Add excursion option

Change-Id: I70133582d92c3a6385fefb46a99743d47f68cd46
diff --git a/User.php b/User.php
index e7efc44..9fe4899 100644
--- a/User.php
+++ b/User.php
@@ -32,6 +32,7 @@
     public $lunch_day_1;
     public $lunch_day_2;
     public $lunch_day_3;
+    public bool $excursion;
     public float $total_due;
     public $invoice;
     public bool $presentation_confirmed;
@@ -66,6 +67,7 @@
         $this->lunch_day_1 = "";
         $this->lunch_day_2 = "";
         $this->lunch_day_3 = "";
+        $this->excursion = false;
         $this->total_due = 0.0;
         $this->invoice = "";
         $this->presentation_confirmed = false;
@@ -91,7 +93,8 @@
             if (array_key_exists($key, (array) $this))
                 $this->{$key} = $value;
         }
-        if (isset($data->password)) $this->set_password($data->password);
+        if (isset($data->password))
+            $this->set_password($data->password);
     }
 
     function init_from_object(object $data)
@@ -100,7 +103,8 @@
             if (array_key_exists($key, (array) $this))
                 $this->{$key} = $value;
         }
-        if (isset($data->password)) $this->set_password($data->password);
+        if (isset($data->password))
+            $this->set_password($data->password);
     }
 
     function init_from_array(array $data)
@@ -113,7 +117,8 @@
                     $this->{$key} = $value;
             }
         }
-        if (!empty($data["password"])) $this->set_password($data["password"]);
+        if (!empty($data["password"]))
+            $this->set_password($data["password"]);
     }
 
 
@@ -140,7 +145,7 @@
         $tmp_user->invoice = "";
         $tmp_user->password = "***";
         $tmp_user->user_hash = "***";
-        return  json_encode($tmp_user);
+        return json_encode($tmp_user);
     }
 
     function backup_in_session()
@@ -151,14 +156,17 @@
         }
     }
 
-    function to_table() {
+    function to_table()
+    {
         $table = "<table  style='border: 1px solid #e1e4e8; border-collapse: collapse; width: 100%;'>";
         foreach ($this as $key => $value) {
             if ($key != "password" && $key != "user_hash" && !empty($value) && $key != "invoice") {
                 if (is_bool($value)) {
-                    if ($value) $value = "yes";
-                    else $value = "no";
-                } elseif(is_float($value)) {
+                    if ($value)
+                        $value = "yes";
+                    else
+                        $value = "no";
+                } elseif (is_float($value)) {
                     $key .= " €";
                     $value = number_format($value, 2, '.', ' ');
                 }
diff --git a/config.php.example b/config.php.example
index 722ed0f..4f67a19 100755
--- a/config.php.example
+++ b/config.php.example
@@ -24,6 +24,7 @@
 $EARLYBIRD_CONFERENCE_FEE = 240;
 $CONFERENCE_DINNER = 60;
 $STUDENT_DISCOUNT = 80;
+$EXCURSION = 20;
 $EARLYBIRD_DEADLINE = "15 May 2023"; // HAWAIAN TIME (HST) is used :)
 
 // Redis password
diff --git a/create_user_table.sql b/create_user_table.sql
index d5abe47..8559b27 100644
--- a/create_user_table.sql
+++ b/create_user_table.sql
@@ -26,6 +26,7 @@
     lunch_day_1 varchar(32) not null default '',
     lunch_day_2 varchar(32) not null default '',
     lunch_day_3 varchar(32) not null default '',
+    excursion boolean not null default false,
     total_due decimal(10,2) not null default 0.00,
     registered_at timestamp default '0000-00-00 00:00:00', 
     updated_at timestamp default now() on update now(),
diff --git a/invoice.php b/invoice.php
index 2892865..cbc45e6 100644
--- a/invoice.php
+++ b/invoice.php
@@ -12,7 +12,7 @@
 $FULL_VAT=0.19;
 function create_invoice(User $user)
 {
-    global $FULL_VAT, $SERVICE_ACRONYM, $SERVICE_NAME, $SERVICE_LOGO, $REGULAR_CONFERENCE_FEE, $EARLYBIRD_CONFERENCE_FEE, $STUDENT_DISCOUNT, $CONFERENCE_DINNER, $LUNCH;
+    global $FULL_VAT, $SERVICE_ACRONYM, $SERVICE_NAME, $SERVICE_LOGO, $REGULAR_CONFERENCE_FEE, $EARLYBIRD_CONFERENCE_FEE, $STUDENT_DISCOUNT, $CONFERENCE_DINNER, $LUNCH, $EXCURSION;
     $vat_sum = 0;
     $invoice = new InvoicePrinter("A4", "€", "en");
     $invoice->lang['product'] = "Item";
@@ -36,7 +36,7 @@
         $invoice->addItem( $SERVICE_ACRONYM . ' Registration', $SERVICE_NAME, 1, false, $REGULAR_CONFERENCE_FEE, false, $REGULAR_CONFERENCE_FEE);
     if($user->student) $invoice->addItem('Student Discount', 'Student discount', 1, false, - $STUDENT_DISCOUNT, false, -$STUDENT_DISCOUNT);
     if($user->conference_dinner)  {
-        $invoice->addItem('Conference Dinner' . ($user->vegetarian_dinner ? " (vegetarian option)" : ""), 'The conference dinner will take place on 20 July.', 1, false, $CONFERENCE_DINNER, $CONFERENCE_DINNER * $FULL_VAT, $CONFERENCE_DINNER);
+        $invoice->addItem('Conference Dinner' . ($user->vegetarian_dinner ? " (vegetarian option)" : ""), 'The conference dinner takes place on 20 July.', 1, false, $CONFERENCE_DINNER, $CONFERENCE_DINNER * $FULL_VAT, $CONFERENCE_DINNER);
         $vat_sum += $CONFERENCE_DINNER * $FULL_VAT;
     }
     $lunch_count = 0;
@@ -69,6 +69,11 @@
         $invoice->addItem('Lunch', $lunch_details, $lunch_count, false, $LUNCH, $lunch_count * $LUNCH * $FULL_VAT, $lunch_count * $LUNCH);
     // $invoice->addTotal('Discount', $STUDENT_DISCOUNT);
 
+    if ($user->excursion) {
+        $vat_sum += $EXCURSION * $FULL_VAT;
+        $invoice->addItem('Excursion', 'The excursion takes place on the afternoon 21 July.', 1, false, $EXCURSION, $EXCURSION * $FULL_VAT, $EXCURSION);
+    }
+
     /* Add totals */
     $invoice->addTotal('Gross', $user->total_due);
 
diff --git a/static/main.js b/static/main.js
index 3f8c7ac..ee19a8a 100644
--- a/static/main.js
+++ b/static/main.js
@@ -15,10 +15,14 @@
                     event.preventDefault();
                     event.stopPropagation();
                 }
+                update_total_due();
                 form.classList.add('was-validated');
             }, false);
         });
     }, false);
+    window.addEventListener('popstate', function(event) {
+        update_total_due();
+    }, false);
 })();
 
 function update_total_due() {
@@ -39,6 +43,9 @@
         if ($('#conference_dinner').is(":checked")) {
             costs += parseInt($("#conference_dinner_price").text(), 10);
         }
+        if ($('#excursion').is(":checked")) {
+            costs += parseInt($("#excursion_price").text(), 10);
+        }
         const lunches = ["lunch_day_1", "lunch_day_2", "lunch_day_3"];
         lunches.forEach(function(lunch) {
             if ($("input[name='" + lunch + "']:checked").val() != "--") {
diff --git a/templates/register.htm b/templates/register.htm
index ca8eeca..61cebea 100644
--- a/templates/register.htm
+++ b/templates/register.htm
@@ -604,6 +604,15 @@
     </div>
     <div id="lunchHelp2" class="form-text fs-4">Please note that lunch must be ordered and paid for in advance and unfortunately cannot be purchased spontaneously on site.</div>
 
+    <div class="form-outline mb-3">
+        <label class="form-label fw-bold" for="excursion">Excursion</label>
+        <div class="form-group form-check">
+            <input type="checkbox" class="form-check-input" name="excursion" id="excursion" <?php echo isset($_POST[ 'excursion']) ? 'checked' : '' ?> oninput="update_total_due()" value="excursion">
+            <label class="form-check-label fs-4" for="excursion">I would like to participate in the excursion on the afternoon of Friday, 21 July for the price of <strong>€&#160;<span id="excursion_price"><?php echo $EXCURSION; ?></span></strong>.
+            </label>
+        </div>
+    </div>
+
     <div class="form-outline col-md-12">
         <label class="form-label fw-bold" for="exampleInputAmount">Total Amount in Euro to be paid</label>
         <div class="input-group">