# $Id: autosum.tcl,v 1.5 1998/10/25 22:32:09 cthulhu Exp $

proc FindEmptyRowOrCol {sel} {
    source "[xxl_library]/globalvars.tcl"

    if {[lindex $sel 1]==[lindex $sel 3]} {

	set j [expr [lindex $sel 2] + 1]
	while {[CellValue $activeSheet $j [lindex $sel 1]]!=""} {
	    incr j
	}
	return $j
    } else {
	set c [lindex $sel 0]
	set r [expr [lindex $sel 3] + 1]
	while {$c!=[lindex $sel 2] || [CellValue $activeSheet $c $r]!=""} {
	    if {[CellValue $activeSheet $c $r]!=""} {
		incr r
		set c [lindex $sel 0]
	    } else {
		incr c
	    }
	}
	return $r
    }
}
	       
proc DeltaRow {dir} {
    switch $dir {
	1 { return -1}
	2 { return 1}
	3 { return 0}
	4 { return 0}
    }
}

proc DeltaCol {dir} {
    switch $dir {
	1 { return 0}
	2 { return 0}
	3 { return -1}
	4 { return 1}
    }
}

proc HasData {dir} {
    if {$dir == ""} {
	return 0
    } else { 
	return 1
    }
}

proc DirLength {dir} {
    source "[xxl_library]/globalvars.tcl"
    set res 0
    set j 1
    
    while {[CellValue $activeSheet \
		[expr $activeCellCol + [expr [DeltaCol $dir]*$j]] \
		[expr $activeCellRow + [expr [DeltaRow $dir]*$j]]]!=""} {
	incr j}
    return [expr $j -1]
}

proc AutoSum {} {
    source "[xxl_library]/globalvars.tcl"

    if {$cols_selected!="" || $rows_selected!=""} {
	HelpMessage "Autosum not available for entire columns or rows" 1 1
    } elseif {$currentRange != ""} {
	if {[lindex $currentRange 1] == [lindex $currentRange 3]} {
	    set res "=@SUM("
	    append res [CellName [lindex $currentRange 0] \
			    [lindex $currentRange 1]] ":" \
		[CellName [lindex $currentRange 2] [lindex $currentRange 3]] \
		")"
	    set r [FindEmptyRowOrCol $currentRange]
	    CellSet $activeSheet $r [lindex $currentRange 1] $res
	    set activeCellCol $r
	    set activeCellRow [lindex $currentRange 1]
	    highlightActiveCell
	} else {
	    set c [lindex $currentRange 0]
	    set r [FindEmptyRowOrCol $currentRange]
	    while {$c != [expr [lindex $currentRange 2] + 1]} {
		set res "=@SUM("
		append res [CellName $c [lindex $currentRange 1]] ":" \
		    [CellName $c [lindex $currentRange 3]] ")"
		CellSet $activeSheet $c $r $res
		incr c
	    }
	    if {[lindex $currentRange 0]==[lindex $currentRange 2]} {
		set activeCellCol [lindex $currentRange 0]
		set activeCellRow $r
		highlightActiveCell
	    }
	}
    } else {
	set up [CellValue $activeSheet \
		    $activeCellCol [expr $activeCellRow - 1]]
	set down [CellValue $activeSheet \
		      $activeCellCol [expr $activeCellRow + 1]]
	set left [CellValue $activeSheet \
		      [expr $activeCellCol - 1] $activeCellRow]
	set right [CellValue $activeSheet \
		       [expr $activeCellCol + 1] $activeCellRow]
	set up [HasData $up]
	set down [HasData $down]
	set left [HasData $left]
	set right [HasData $right]
	if {[expr $up+$down+$left+$right] == 0} {
	    HelpMessage "Please pick a cell adjacent to nonempty cells or a cell range before using AutoSum" 1
	} elseif {[expr $up+$down+$left+$right] == 1} {
	    if {$up==1} {
		set res "=@SUM("
		append res [CellName $activeCellCol \
				[expr $activeCellRow - [DirLength 1]]] \
		    ":" [CellName $activeCellCol [expr $activeCellRow -1]] ")"
		set currentRange \
		    [list $activeCellCol [expr $activeCellRow - [DirLength 1]]\
			 $activeCellCol [expr $activeCellRow - 1]]
	    }
	    if {$down==1} {
		set res "=@SUM("
		append res [CellName $activeCellCol [expr $activeCellRow +1]] \
		    ":" [CellName $activeCellCol \
			     [expr $activeCellRow + [DirLength 2]]] ")"
		set currentRange \
		    [list $activeCellCol [expr $activeCellRow + 1] \
			 $activeCellCol [expr $activeCellRow + [DirLength 2]]]
	    }
	    if {$left==1} {
		set res "=@SUM("
		append res [CellName [expr $activeCellCol -  [DirLength 3]] \
				$activeCellRow] \
		    ":" [CellName [expr $activeCellCol -1] $activeCellRow] ")"
		set currentRange \
		    [list [expr $activeCellCol - [DirLength 3]] $activeCellRow\
			 [expr $activeCellCol - 1] $activeCellRow]
	    }
	    if {$right==1} {
		set res "=@SUM("
		append res [CellName [expr $activeCellCol +1] $activeCellRow] \
		    ":" [CellName [expr $activeCellCol + [DirLength 4]] \
			     $activeCellRow] ")"
		set currentRange \
		    [list [expr $activeCellCol + 1] $activeCellRow\
			 [expr $activeCellCol + [DirLength 4]] $activeCellRow]
	    }
	    CellSet $activeSheet $activeCellCol $activeCellRow $res	    
	    highlightActiveCell
	    highlightCurrentRange [canvasFromSheet $activeSheet]
	} else {
	    toplevel .autosum
	    wm title .autosum "AutoSum"

	    label .autosum.label -text "Where should sum data come from?:"
	    pack .autosum.label -side top

	    frame .autosum.box
 	    radiobutton .autosum.box.up -variable dir \
		-text "Above active cell" -value 1 
	    radiobutton .autosum.box.down -variable dir \
		-text "Below active cell"  -value 2
	    radiobutton .autosum.box.left -variable dir \
		-text "Left of active cell" -value 3
	    radiobutton .autosum.box.right -variable dir \
		-text "Right of active cell" -value 4
	    if {$up==1} {pack .autosum.box.up -anchor w}
	    if {$down==1} {pack .autosum.box.down -anchor w}
	    if {$left==1} {pack .autosum.box.left -anchor w}
	    if {$right==1} {pack .autosum.box.right -anchor w}

	    if {$up==1} {
		.autosum.box.up select
	    } elseif {$down==1} {
		.autosum.box.down select
	    } elseif {$left==1} {
		.autosum.box.left select
	    } else {
		.autosum.box.right select
	    }
	    
	    pack .autosum.box -side top
	    frame .autosum.endr
	    button .autosum.endr.ok -text Ok \
		-command {
		    destroy .autosum
		    switch $dir {
			1 { set res "=@SUM("
			    append res [CellName $activeCellCol \
					    [expr $activeCellRow - \
						 [DirLength 1]]] \
				":" [CellName $activeCellCol \
					 [expr $activeCellRow -1]] ")"
			    set currentRange \
				[list $activeCellCol \
				     [expr $activeCellRow - [DirLength 1]]\
				     $activeCellCol [expr $activeCellRow - 1]]
			} 
			2 { set res "=@SUM("
			    append res [CellName $activeCellCol \
					    [expr $activeCellRow +1]] \
				":" [CellName $activeCellCol \
					 [expr $activeCellRow + \
					      [DirLength 2]]] ")"
			    set currentRange \
				[list $activeCellCol [expr $activeCellRow + 1]\
				     $activeCellCol \
				     [expr $activeCellRow + [DirLength 2]]]
			}
			3 { set res "=@SUM("
			    append res [CellName [expr $activeCellCol - \
						      [DirLength 3]] \
					    $activeCellRow] \
				":" [CellName [expr $activeCellCol -1] \
					 $activeCellRow] ")"
			    set currentRange \
				[list [expr $activeCellCol - [DirLength 3]] \
				     $activeCellRow\
				     [expr $activeCellCol - 1] $activeCellRow]
			}
			4 { set res "=@SUM("
			    append res [CellName [expr $activeCellCol +1] \
					    $activeCellRow] \
				":" [CellName [expr $activeCellCol + \
						   [DirLength 4]] \
					 $activeCellRow] ")"
			    set currentRange \
				[list [expr $activeCellCol + 1] $activeCellRow\
				     [expr $activeCellCol + [DirLength 4]] \
				     $activeCellRow]
			}
		    }
		    CellSet $activeSheet $activeCellCol $activeCellRow $res
		    highlightActiveCell
		    highlightCurrentRange [canvasFromSheet $activeSheet]
		}
	    button .autosum.endr.abort -text Abort \
		-command {destroy .autosum}
	    pack .autosum.endr.ok .autosum.endr.abort -fill x -expand yes \
		-side bottom
	    pack .autosum.endr -side bottom -fill x -expand yes -side bottom
	    focus .autosum
	    grab .autosum
	    tkwait window .autosum
	}
    }
}

# $Log: autosum.tcl,v $
# Revision 1.5  1998/10/25 22:32:09  cthulhu
# Autosum disallows summing of entire columns or rows.
#
# Revision 1.4  1998/09/07 21:08:08  cthulhu
# Autosum now displays sum result in the edit box always and not just in a couple
# of cases like before.
#
# Revision 1.3  1998/08/22 22:11:40  cthulhu
# Minor bugs
#
# Revision 1.2  1998/08/22 22:07:31  cthulhu
# Warnings are displayed using HelpMessage instead of WarnUser
#
# Revision 1.1  1998/08/17 20:04:14  cthulhu
# Initial revision
#
