require "yaml"
require "sqlite3"

Shoes.app :title => "Dining Room", :width => 300, :height => 730, :resizable => false do
  background tan
  border darkred, :strokewidth => 8
  background darkred, :height => 45
  $tableWindow = self
  @@table_holder = []

  
  tables = YAML.load_file("Yaml/tables.yml")
  tables["tables"].each do |(key, value)|
    nostroke
    fill darkgreen
    table = rect value[0], value[1], value[2], value[3], value[4], :center => true
    para key, :top => value[1]-8, :left => value[0]-8, :stroke => white
    

      table.click do

        status = true unless @@table_holder.include?(key)
        status = confirm("This Table is Thinks it's Already Open\nHIT OK and Then HIT the CLOSE Button to Close It") if @@table_holder.include?(key)
        
        if status == true
          @@table_holder << key
      
          table.style(:fill => red)
        
          # ==================================
          # = New Shoes app for table number =
          # ==================================
          order_window = Shoes.app :title => "Table #{key}", :width => 800 do
            background darkgray, :height => 400
            $orderWindow = self
            RECTWIDTH = 110


            @sendToKitchen   = []     # => cleared every time 'send' button is clicked; used for kitchen printout
            @sendToDatabase  = []     # => cleared every time 'print' button is clicked; used for database record
            @howManySeparate = []     # => when length == 0 table.style(:fill => darkgreen)
       @@separateChecksArray = []     # => doesn't seem to be a danger if more than one table is open
            @sent = 0                 # => confirm data is entered into @sendToDatabase array; 1 == true
            @numberToPop = 0          # => empties @@separateChecksArray
            
            def showCategoryButtons(category, separateChecks)
              database = SQLite3::Database.open("Database/CSDB.db")
              @flowsy.clear if @flowsy != nil
              @flowsy = flow :left => 0, :top => 100, :margin => 20, :width => 600 do
                number = 1
                database.execute("SELECT item, salesPrice, foodCost, category FROM foodCosts WHERE category = '#{category}' ORDER BY item") do |item, price, foodCost, category|
                  my_button = button(item) do
                    @separateChecks.state = 'disabled'
                    addToCart(my_button.id,item,number,foodCost,category,price)
                    number += 1
                    @empty_flow.append do
                      myCartButton = button(item) {removeFromCart(my_button.id, myCartButton,separateChecks,item,price,foodCost)}
                    end
                  end
                end
              end
              database.close
            end
          
            def addToCart(buttonId, item, number,foodCost,category,price)
              @sendToKitchen  << [item, buttonId, number]
              @sendToDatabase << [item, buttonId, foodCost, category, price, number]
              @sent = 0
            end
          
            def removeFromCart(id, cart_button,separateChecks,item,price,foodCost)
              if separateChecks.checked?
                cart_button.state = 'disabled'
                @numberToPop += 1
                @@separateChecksArray << [item,1,foodCost,3, price,4]# the numbers are place holders for printCheckForGuest
              else
                @sendToKitchen.delete(@sendToKitchen.rassoc(id))
                @sendToDatabase.delete(@sendToDatabase.rassoc(id))
                cart_button.remove
              end
            end
          
            def printKitchenTicket(key, specialInstructions)
              @separateChecks.state = nil
              @@order = []         #class variable b/c window for alert is new app
              @@hash = Hash.new(0) #class variable b/c window sfor alert is new app
              @sendToKitchen.each { |e| @@hash[e[0]] += 1;@howManySeparate << [1] }
              File.open("Text/kitchenTicket.txt", "w") do |file|
                file.printf "%s\n", Time.now.asctime
                file.printf "Table %s\n\n", key
                @@hash.each_pair { |name, val| file.printf "%s %22s\n",val,name.rjust(22,'.') }#comment see below
                file.puts
                @sendToKitchen.each { |e| file.printf "%s\n", e[0] }
                file.printf "\nNotes:\n%s\n", specialInstructions
              end
              kitchen_window = window do
                subtitle "Order Sent\n"
                @@hash.each_pair { |name,val| caption "#{val} #{name}\n"  }
              end
              timer(2) do
                kitchen_window.close
              end
              @sendToKitchen.clear
              @sent = 1
            end
          
            def printBill(key, orderWindow,tabled)
              @@billToShowServer = []
              if @sent == 1 and @separateChecks.checked? == false
                recordDatabase(@sendToDatabase)
                printCheckForGuest(key,@sendToDatabase)
                @sendToDatabase.each do |e|
                  price = sprintf "%5.2f",e[4].to_f
                  @@billToShowServer << [e[0],price]
                end
                @sendToDatabase.clear
                tabled.style(:fill => darkgreen)
                @sent = 0
                bill_window = window do
                  subtitle "Bill Printed\n"
                  @@billToShowServer.each do |e|
                    para "#{e[0]}, #{e[1]}\n"
                  end
                end
                @@table_holder.delete(key)
                timer(2) do
                  bill_window.close
                  orderWindow.close
                end
              elsif @sent == 1 and @separateChecks.checked? == true
                recordDatabase(@@separateChecksArray)
                printCheckForGuest(key,@@separateChecksArray)
                @numberToPop.times {@howManySeparate.pop}
                @numberToPop = 0
                bill_window = window do
                  subtitle "Bill Printed\n\n"
                  @@separateChecksArray.each do |e|
                    price = sprintf "%5.2f",e[4].to_f
                    para "#{e[0]}, #{price}\n"
                  end
                  # $orderWindow.@sendToDatabase.each { |e| caption "#{e[0]}\n"  }
                end
                @@separateChecksArray.clear
                if @howManySeparate.length == 0
                  @@table_holder.delete(key)
                  timer(2) do
                    orderWindow.close
                    bill_window.close
                    tabled.style(:fill => darkgreen)
                  end
                end
                timer(2) do
                  bill_window.close
                end
              else
                alert("You Must SEND Order To Kitchen")
              end
            end
          
            def printCheckForGuest(key,arrayOfFood)
              @addIt = []
              File.open("Text/GuestCheck.txt", "w") do |file|
                file.printf "%s\n", Time.now.asctime
                file.printf "Table %s\n\n", key
                arrayOfFood.each do |item, id, noWorry, noWorry2, price, quantity|
                  @addIt << price.to_f
                  file.printf "%-22s %5.2f\n", item, price.to_f
                end
                if @addIt.length > 1
                  sT = @addIt.inject { |mem, var| mem.to_f + var.to_f }
                elsif @addIt.length == 1
                  sT = @addIt.to_s.to_f
                end
                tax = sT*0.07
                total = tax + sT
                file.printf "\n%-22s %5.2f\n", "Sub Total", sT
                file.printf "%-22s %5.2f\n", "Tax(7%)", tax
                file.printf "%-22s %5.2f\n", "Total", total
              end
            end
          
            def recordDatabase(arrayToRecord)
              database = SQLite3::Database.open("Database/CSDB.db")
                arrayToRecord.each do |item,id,foodCost,category,salesPrice|
                database.execute("INSERT INTO sales VALUES (1, '#{item}', '#{Time.now.strftime("%m/%d/%Y")}','#{category}',#{salesPrice},'#{foodCost}')")
                end
              database.close
            end
            
            @rectHolder = [[[],[]]]
            def changeColor(rect, id)
              rect.style(:fill => blue)
              @rectHolder << [[rect], [id]]
              oldRect = @rectHolder.shift
              unless oldRect[1][0] == nil or oldRect[1][0] == id
                oldRect[0][0].style(:fill => black)
              end
            end
            
          
            flow :margin => 20 do
              database = SQLite3::Database.open("Database/CSDB.db")
              @number_per_row = 5
              @number_of_categories = 0
              database.execute("SELECT category FROM foodCosts GROUP BY category").each_with_index do |category, index|
                @number_of_categories += 1
                if index < 5
                  my_top = 0
                else
                  my_top = 35
                end 
                catRect = rect(((index+@number_per_row) % @number_per_row)*RECTWIDTH,my_top,100,30,10)
                para category, :top => my_top+20, :left => ((index+@number_per_row) % @number_per_row)*RECTWIDTH+20, :stroke => white
                catRect.click do
                  changeColor(catRect, catRect.id)
                  showCategoryButtons(category, @separateChecks)
                end
              end
              database.close
            end
            
            @empty_flow = flow :margin => 20, :left => 0, :top => 400 do;end
            
            flow :margin => 20, :top => 0, :left => RECTWIDTH*@number_of_categories/2, :width => 300 do
              button("Close") {order_window.close;table.style(:fill => darkgreen);@@table_holder.delete(key)}
              button("Send") {printKitchenTicket(key, @specialInstructions.text);@specialInstructions.text = ''}
              button("Print") {printBill(key,order_window,table)}
              para "Separate Checks", :align => 'center'
              @separateChecks = check :left => 45, :top => 35, :state => 'disabled'
              @specialInstructions = edit_box :margin_left => 10
            end
            
          end#app

    
      end#table.click
    end#unless
  end#table.each
end