package org.drools.games.wumpus.view

import org.drools.games.wumpus.Cell
import org.drools.games.wumpus.Direction
import org.drools.games.wumpus.Hero
import org.drools.games.wumpus.Gold
import org.drools.games.wumpus.Pit
import org.drools.games.wumpus.Wumpus
import org.drools.games.wumpus.Thing

import java.awt.image.BufferedImage
import java.awt.Color;
import java.awt.Graphics

import javax.imageio.ImageIO

import javax.swing.JPanel;

function void paintCaveCell(String image, Cell cell, GameView gv, GameUI gui) {
     int rowIndent = 20;
     int colIndent = 5;
     int rowPad = cell.getRow() * gv.getCellPadding();
     int colPad = cell.getCol() * gv.getCellPadding();
     int y = (4 - cell.getRow()) * 50 - rowPad + rowIndent;
     int x = cell.getCol() * 50 + colPad + colIndent;
     
     Graphics caveG = gui.getCavePanel().getCaveG();
     caveG.setColor( Color.WHITE ); // background
     caveG.fillRect( x, y,  gv.getCellWidth(), gv.getCellHeight() );
     caveG.drawImage( ImageIO.read( GameView.class.getResource( image ) ), x, y, gv.getCellHeight(), gv.getCellWidth(), gui.getCavePanel() );
}


dialect "mvel"

declare CompositeImageName
    @propertyReactive
    cell : Cell
    pit : String
    wumpus : String
    gold : String
    hero : String    
end 

declare CaveDirty
	@propertyReactive
    dirty : boolean
end   

rule "Init CaveDirty" when
    not CaveDirty()
then
    insert( new CaveDirty() );
end

rule "Create CompositeImage" when
    $c : Cell()
    not CompositeImageName( cell == $c )
then
    CompositeImageName cin = new CompositeImageName($c, "", "", "", "");
    insert( cin );
end  

rule "Reset CompositeImage" when
    $cin : CompositeImageName()
    not Cell( row == $cin.cell.row, col == $cin.cell.col)
then
    retract( $cin );
end    

rule "Base Paint" when
    $c : Cell()
    $cin : CompositeImageName( cell == $c )
then
end    

rule "Paint Gold" extends "Base Paint" when
    Gold(row == $c.row, col == $c.col)  
then
   modify( $cin ) { gold = "gold" };
end

rule "Paint Empty Gold" extends "Base Paint" when
    not Gold(row == $c.row, col == $c.col)  
then
   modify( $cin ) { gold = "" };
end

rule "Paint Pit" extends "Base Paint" when
    Pit(row == $c.row, col == $c.col)  
then
   modify( $cin ) { pit = "pit" };
end

rule "Paint Wumpus Alive" extends "Base Paint" when
    Wumpus(alive == true, row == $c.row, col == $c.col)  
then
   modify( $cin ) { wumpus = "wumpus_alive" };
end

rule "Paint Wumpus Dead" extends "Base Paint" when
    Wumpus(alive == false, row == $c.row, col == $c.col)  
then
   modify( $cin ) { wumpus = "wumpus_dead" }
end

rule "Paint Hero Direction Up" extends "Base Paint" when 
    $h : Hero( direction == Direction.UP, row == $c.row, col == $c.col )
then
     modify( $cin ) { hero = "hero_up" };
end    

rule "Paint Hero Direction Down" extends "Base Paint"  when
    $h : Hero( direction == Direction.DOWN, row == $c.row, col == $c.col  )
then
    modify( $cin ) { hero = "hero_down" };
end   

rule "Paint Hero Direction Left" extends "Base Paint"  when
    $h : Hero( direction == Direction.LEFT, row == $c.row, col == $c.col  )
then
    modify( $cin ) { hero = "hero_left" };
end    

rule "Paint Hero Direction Right" extends "Base Paint" when
    $h : Hero( direction == Direction.RIGHT, row == $c.row, col == $c.col  )
then
    modify( $cin ) { hero = "hero_right" };
end 

rule "Paint Empty Hero" extends "Base Paint" when
    not Hero( row == $c.row, col == $c.col  )
then
    modify( $cin ) { hero = "" };
end   

rule "Paint Hidden Room" when 
    $gui : GameUI( cavePanel != null && cavePanel.caveG != null  )
    $cd : CaveDirty()
    $gv : GameView(showAllCells == false)
    $c : Cell(hidden == true) 
then
   paintCaveCell( "hidden_room.png", $c, $gv, $gui);
   modify( $cd ) { dirty = true };
end


rule "Paint Empty Room" when 
   $gui : GameUI( cavePanel != null && cavePanel.caveG != null )
    $cd : CaveDirty()   
   ($gv : GameView(showAllCells == true) and $c : Cell() ) or
   ($gv : GameView(showAllCells == false) and $c : Cell(hidden == false) )      
   CompositeImageName( cell == $c, pit == "", wumpus == "", gold == "", hero == "" )
then
   paintCaveCell( "empty_room.png", $c, $gv, $gui );
   modify( $cd ) { dirty = true };
end 

rule "Paint Non Empty Room" when
   $gui : GameUI( cavePanel != null && cavePanel.caveG != null )
   $cd : CaveDirty()   
   ($gv : GameView(showAllCells == true) and $c : Cell() ) or
   ($gv : GameView(showAllCells == false) and $c : Cell(hidden == false) )    
   $cin : CompositeImageName( cell == $c, ( !(hero != "" && pit != "")  &&  // don't draw a hero on the same square as a pit or an alive wumpus, as the game is over
                                            !(hero != "" && wumpus == "wumpus_alive") && 
                                            !(pit == "" && wumpus == "" && gold == "" && hero == "") ) )
then
    paintCaveCell( $cin.pit + $cin.wumpus + $cin.gold +  $cin.hero + ".png", $cin.cell, $gv, $gui );
    modify( $cd ) { dirty = true };
end

rule "Redraw Cave" no-loop salience -100 when
   $gui : GameUI() 
   $cd : CaveDirty( dirty == true )
then
   $gui.updateCave();
   modify( $cd ) { dirty = false };
end