#! /usr/local/bin/wish4.2jp
#
#	GP ver. 2.5 patch level 2ja -- GUI Printer (Tcl/Tk Script File)
#
#       Copyright (C) 1998年 植田 裕之
#
#       作者：植田 裕之 (ueda@itbrain.co.jp)
#
#       本プログラムはフリー・ソフトウェアです．あなたは Free Software
#       Foundation が公表した GNU GNU Public License (GPL) のバージョン 2，
#       あるいはそれ以降の各バージョンの中からいずれかを選択し，その
#       バージョンが定める条項に従って本プログラムを再領布または変更する
#       ことができます．
#
#       本プログラムは有用とは思いますが，領布にあたっては，市場性及び特定
#       目的適合性についての暗黙の保証を含めて，いかなる保証も行ないません．
#       詳細については COPYING ファイル(GPL) をお読み下さい．
#
#       なお 同梱した COPYING.jp ファイルは COPYING ファイルの日本語訳で
#       あり，以下の URL で公開されています
#
#                 http://www.sra.co.jp/public/doc/gpl-2j
#

# 環境依存の変数です．各自のサイトに合わせて編集して下さい．

# GP の設定ファイルのパス
set PRINTER_LIST   "/usr/local/lib/GP/ja/printer"    ;# Path of Printer List
set FILETYPE_LIST  "/usr/local/lib/GP/ja/filetype"   ;# Path of File Type List
set FILTERS_DIR    "/usr/local/lib/GP/ja/filters"    ;# Path of Filter Def. Files
set ICONS_PATH     "/usr/local/lib/GP/ja/icons"      ;# Path of Icon files

# システムコマンドと作業用ディレクトリのパス
set PRINT_COM  "/usr/bin/lpr"                     ;# Print Command Path
set QUEUE_COM  "/usr/bin/lpq"                     ;# Queue Command Path
set REMOVE_COM "/usr/bin/lprm"                    ;# Queue Remove Command Path
set RM         "/bin/rm"                          ;# rm Command Path
set MV         "/bin/mv"                          ;# mv Command Path
set MKDIR      "/bin/mkdir"                       ;# mkdir Command Path
set TMPDIR     "/var/tmp"                         ;# TMP Directory

# ファイルプレビューのためのアプリケーションのパス
set PS_PREVIEWER    "/usr/X11R6/bin/gv"    ;# PS    File Previewer
set DVI_PREVIEWER   "/usr/X11R6/bin/xdvi"         ;# DVI   File Previewer
set IMAGE_PREVIEWER "/usr/X11R6/bin/xv"           ;# Image File Previewer
set PAGER           "/usr/local/bin/jless"        ;# Pager    Application
set TERM            "/usr/X11R6/bin/kterm -km euc" ;# Terminal Application

# ファイル変換アプリケーションのパス
set PS_UTILS_PATH     "/usr/local/bin/"           ;# Psutils Path

# 印刷用紙一覧
set PAPER_LIST "A4,Letter,A5,B5,A3,Legal,Tabloid,Statement,Executive,Folio,Quarto,10x14"

# 印刷用紙の初期値 (PAPER_LIST 変数を参照のこと)
set defaultPaper  "A4"

# デフォルトの用紙方向 (Portrait/Landscape)
set paperOrient "portrait"

# 複数部印刷する際の最大値
set MaxCopy     10

# 一枚の紙に組み込むページ数の最大値
set MaxNUP     16

# 印刷履歴（ヒストリ）の保持数の最大値
set history_Max 20

# デフォルトで印刷キューの自動チェックをするか否か (YES/NO)
set isAutoQueueCheck NO

# 自動キューチェックの間隔(秒)
set interval_QueueCheck 10

# ファイルタイプとファイル拡張子
set types {
    {"PS files"       {.ps} }
    {"DVI files"      {.dvi} }
    {"Text files"     {.txt .doc} }
    {"Image files"    {.gif .jpg .xbm} }
    {"All files"       * }
}

# 日本語フォントの設定
set kfont(1) -*-fixed-medium-r-normal--14-*-*-*-*-*-jisx0208.1983-*
set kfont(2) -*-fixed-medium-r-normal--16-*-*-*-*-*-jisx0208.1983-*
set kfont(5) -*-fixed-medium-r-normal--24-*-*-*-*-*-jisx0208.1983-*

####################################################
#                                                  #
# このコメント以降の行は編集しない方が良いでしょう #
#                                                  #
####################################################
# GP Version
set version "2.5p2ja"

# Setting paths of psutils
if {[info exists PS_UTILS_PATH] && $PS_UTILS_PATH != ""} {
    set PSBOOK    "$PS_UTILS_PATH/psbook"
    set PSNUP     "$PS_UTILS_PATH/psnup"
    set PSRESIZE  "$PS_UTILS_PATH/psresize"
    set PSSELECT  "$PS_UTILS_PATH/psselect"
    set PSTOPS    "$PS_UTILS_PATH/pstops"
    set isPSUTILS YES
} else {
    set isPSUTILS NO
}

# Procedure for showing Copyright 
proc Copyright {} {
    global version 
    puts "\n\t GP ver. $version (C) 1997-1998 植田 裕之\n"
}

# Check Tcl/Tk version
if {$tk_version < 4.2} {
    Copyright
    puts "\t GP ver. $version は *Tcl7.6p2/Tk4.2p2* が必要です\n" ; exit
}

# Check the arguments
set button_direc "left"
if {$argc > 1} {
    Copyright
    puts "\t\t 使い方 : GP \[-geometry +X+Y\] \[-vertical|-horizontal\]\n"
    exit
} elseif {[lindex $argv 0] == "-vertical"} {
    set button_direc "top"
}

# Initialize certain values
set Printer ""  ; set Comment "" ; set FileType ""
set isNUP NO    ; set isLNUM NO  ; set isREV NO
set maxTP 0     ; set maxDP 0    ; set maxIP 0
set history_max $history_Max     ; set history_num [expr $history_Max + 1] 
set USER [exec whoami]           ; set ext "ps"
set numTP 0     ; set numDP 0    ; set numIP 0


# Check Printer List
if {![file exists $PRINTER_LIST]} {
    Copyright ; puts "\t\t プリンタリストがありません\n" ; exit
}

# Check File Type List
if {![file exists $FILETYPE_LIST]} {
    Copyright ; puts "\t\t ファイルタイプリストがありません\n" ; exit
}

# Check whether ~/.GP directory exists
if {![file exists $env(HOME)/.GP]} {
    exec $MKDIR $env(HOME)/.GP
}

# Check history files and set them if they exist.
for {set i 1} {$i < [expr $history_max + 1]} {incr i} {
    set history($i) ""
}
if {[file exists $env(HOME)/.GP/history]} {
    set in_fd [open $env(HOME)/.GP/history r] ; set i 1
    while {![eof $in_fd]} {
	set line [gets $in_fd]
	if {[file isfile $line]} {
	    set history($i) $line ; set history_max $i ; incr i
	}
    }
} else {
    set history_max 1 ; set history_num 1
}

# WM Commands
wm title . "GP ver. $version"
wm protocol . WM_DELETE_WINDOW { quit }

# Message Fonts
set font(1) -*-Times-bold-r-Normal--14-*-*-*-*-*-*-*
set font(2) -*-Times-bold-r-Normal--16-*-*-*-*-*-*-*
set font(3) -*-Times-bold-r-Normal--18-*-*-*-*-*-*-*
set font(4) -*-Times-bold-r-Normal--24-*-*-*-*-*-*-*
set font(5) -*-Times-bold-r-Normal--34-*-*-*-*-*-*-*

# Message Colors
set afcolor blue

# Comment Arrays for Paper Size
set paperInfo(A3) "(297mm x 420mm)" ; set paperInfo(A4) "(210mm x 297mm)"
set paperInfo(A5) "(148mm x 210mm)" ; set paperInfo(B5) "(182mm x 257mm)"
set paperInfo(Letter)    "(8.5inch x 11inch)"
set paperInfo(Legal)     "(8.5inch x 14inch)"
set paperInfo(Tabloid)   "(11inch x 17inch)"
set paperInfo(Statement) "(5.5inch x 8.5inch)"
set paperInfo(Executive) "(7.6inch x 10inch)"
set paperInfo(Folio)     "(8.5inch x 13inch)"
set paperInfo(Quarto)    "(8.5inch x 10.83inch)"
set paperInfo(10x14)     "(10inch x 14inch)"

# Check TERM & PAGER variables
if {![info exists TERM] || ![info exists PAGER]} {
    if {[info exists env(TERM)] && [info exists env(PAGER)]} {
	set TERM $env(TERM) ; set PAGER $env(PAGER)
    }
}

# Widgets
frame  .frame   -bd 3 -relief groove ; frame  .printF  -bd 0 -relief flat
frame  .statusF -bd 0 -relief flat   ; frame  .quitF   -bd 0 -relief flat

button .printB -bitmap @$ICONS_PATH/printer.xbm -font $font(3) -bd 3 \
	-width 30 -height 30 -activeforeground $afcolor -command {print . }
button .statusB -bitmap question -font $font(3) -bd 3 -width 30 -height 30 \
	-activeforeground $afcolor -command {status . }
button .quitB -bitmap @$ICONS_PATH/exit.xbm -font $font(3) -bd 3 -width 30 \
	-height 30 -activeforeground red -command {save_history ; quit}

label .printL  -text "印刷" -kanjifont $kfont(2)
label .statusL -text "印刷状況" -kanjifont $kfont(2)
label .quitL   -text "終了"  -kanjifont $kfont(2)


# Packing
pack .printB  .printL  -in .printF  -side top
pack .statusB .statusL -in .statusF -side top
pack .quitB   .quitL   -in .quitF   -side top
pack .printF .statusF .quitF -side $button_direc -in .frame ; pack .frame 


# Bindings
bind all <Control-q> {exec $RM -rf $TMPDIR ; save_history ; exit}

# Balloon Help for Main Window
set message(.printB)  "ファイルを印刷します"
set message(.statusB) "印刷状況をチェックします"
set message(.quitB)   "GPを終了します"

foreach i {.printB .statusB .quitB} {
    bind $i <Enter> {
	if {![winfo exists .ballon]} {
	    exec sleep 0.5 ; toplevel .balloon -bg black
	    wm overrideredirect .balloon true
	    label .balloon.l -text $message(%W) -fg black -bg yellow \
		    -font $font(2) -kanjifont $kfont(2)
	    pack .balloon.l -in .balloon
	    wm geometry .balloon +[expr %X+5]+[expr %Y+5]
	}
    }
    bind $i <Leave> {
	if {[winfo exists .balloon]} { destroy .balloon	}
    }
}

#
# Procedures
#

# read_list -- Read PrinterName List
#
# Argument     : PrinterName List Filename
# Return Value : 0 ... Normal
#
proc read_list {filename} {
    global printers comments version

    if {[file isfile $filename] == 0} {
	Copyright ; puts "\t  $file ファイルがありません\n" ; exit
    }

    set fd_in [open $filename r] ; set i 0
    while {![eof $fd_in]} {
	set line [gets $fd_in]
	if {$line == "" || [regexp {^\#} $line] == 1} {continue}
	set list_print [split $line "#"]

	set printers($i) [lindex $line 0]
	set comments($printers($i)) [lrange $line 2 end] ; incr i
    }
    if {$i == 0} {
	Copyright
	puts "\t\t $filename の中にプリンタが定義されていません.\n" ; exit
    }
    set printers($i) END ; close $fd_in ; return 0
}


# read_types -- Reading File Type List
#
# Argument     : File Type List
# Return Value : 0 ... Normal
#
proc read_types { filename } {
    global filetype filelist defaultprn

    if {[file isfile $filename] == 0} {
	Copyright ; puts "\t  $file ファイルがありません\n" ; exit
    }

    set fd_in [open $filename r] ; set i 0
    while {![eof $fd_in]} {
	set line [gets $fd_in]
	if {$line == "" || [regexp {^\#} $line] == 1} {continue}
	set filelist($i) [lindex $line 0]
	set PRN  [lindex $line 1]
	set defaultprn($filelist($i)) $PRN
	set EXTS [lrange $line 2 end]
	foreach j [split $EXTS { }] {
	    if {[string index $j 0] == "."} { set filetype($j) $filelist($i) }
	}
	incr i
    }
    set filelist($i) END ; close $fd_in ; return 0
}


# read_filters -- Read filters information
#
# Argument     : Fiter Definition Filename 
# Return Value : None
#
proc read_filters {file} {
    global COMMAND numTP numDP numIP maxTP maxDP maxIP version

    if {![file isfile $file]} { return 1 }

    set tmp 1 ; set TYPE "" ; set NUM "" ; set in_fd [open $file r]

    while {![eof $in_fd]} {
	set line [gets $in_fd]

	if {[regexp {^\#} $line] == 1 || [llength $line] == 0} { continue }
	if {$tmp == 1 || $tmp == 2} {
	    if {$tmp == 1} {
                set tmpTYPE [lindex $line 2]
                if {[string range $tmpTYPE 0 3] == "TEXT"} {
                    set TYPE TEXT
                } elseif {[string range $tmpTYPE 0 2] == "DVI"} {
                    set TYPE DVI
                } elseif {[string range $tmpTYPE 0 4] == "Image"} {
                    set TYPE Image
                } else {
		    Copyright
		    puts "\t  \"[file tail $file]\" ファイルには\
			    認識でない\n\t\t ファイルタイプがあります．\
			    \n\t\t (TEXT, DVI, Image のいずれかのみが\
			    使えます)\n" ; exit
		}
	    } else {
		set NUM [lindex $line 2]
		set COMMAND($TYPE,$NUM,TYPE) $tmpTYPE

		if {$TYPE == "TEXT" && ($numTP == 0 || $numTP > $NUM)} {
		    set numTP $NUM
		} elseif {$TYPE == "DVI" && ($numDP == 0 || $numDP > $NUM)} {
		    set numDP $NUM
		} elseif {$TYPE == "Image" && ($numIP == 0 || $numIP > $NUM)} {
		    set numIP $NUM
		}
	    }
	    incr tmp
	} else {
	    set COMMAND($TYPE,$NUM,[lindex $line 0])\
		    [string trim [lrange $line 2 end] "\""]
	}
    }

    if {$TYPE == "TEXT"} {
	if {$maxTP < $NUM} { set maxTP $NUM }
    } elseif {$TYPE == "DVI"} {
	if {$maxDP < $NUM} { set maxDP $NUM }
    } else {
	if {$maxIP < $NUM} { set maxIP $NUM }
    } ;  return 0
}


# quit -- Exit Execution
#
# Argument     : None
# Return Value : None
#
proc quit {} {
    global TMPDIR RM

    set result [ tk_dialog .err "GP の終了" "GP を終了します" \
	    question 1 はい いいえ]
    if {$result == "0"} {exec $RM -rf $TMPDIR ; exit}
}


# disp_ver -- Display version of GP, etc...
#
# Argument     : Top Path
# Return Value : None
#
proc disp_ver {w} {
    if {[winfo exist .top]} { return }

    global font kfont version ; toplevel .top ; wm group .top $w
    wm title .top "Version of GP" ; grab set .top

    set web_add      "http://www.itbrain.co.jp/~ueda"
    set appli_info   "GUI Printer"
    set appli_info2  "$version"
    set copyright    "Copyright 1997-1998"
    set copyright2   "UEDA Hiroyuki"
    set fontI        "*-Times-Bold-I-Normal--24-*-*-*-*-*-*-*"
    set fontI2       "*-Times-Medium-I-Normal--20-*-*-*-*-*-*-*"

    canvas .top.disp_ver -width 300 -height 160 -borderwidth 10 -relief groove
    .top.disp_ver create text 151 42 -text $appli_info -fill white \
	    -font $fontI
    .top.disp_ver create text 150 40 -text $appli_info -fill midnightblue \
	    -font $fontI
    .top.disp_ver create text 220 65 -text "ver. $appli_info2" \
	    -fill midnightblue -font $fontI2
    .top.disp_ver create text 25 100 -fill black -font $font(2)\
	    -anchor w -text $copyright
    .top.disp_ver create text 185 100 -fill black -font $font(2)\
	    -anchor w -text $copyright2
    .top.disp_ver create text 90 120 -fill black -font $font(2) \
	    -anchor w -text "All rights reserved."
    .top.disp_ver create text 42 155 -fill white -font $font(2) \
	    -anchor w -text $web_add
    .top.disp_ver create text 40 153 -fill midnightblue -font $font(2) \
	    -anchor w -text $web_add

    button .top.close -text "閉じる" -bd 3 -width 10 -command {
	if {[winfo exist .top]} {destroy .top ; grab release .top ; return}
    } -kanjifont $kfont(2)

    pack .top.disp_ver .top.close -side top
}

# Read the Printer and File Type Lists
read_list $PRINTER_LIST ; read_types $FILETYPE_LIST

# Read the Filter Definition Files 
if {[file exists $env(HOME)/.GP/filters]} {
    foreach i [exec ls $env(HOME)/.GP/filters] {
	read_filters $env(HOME)/.GP/filters/$i
    }
} elseif {[info exists env(GP_FILTERS)] && [file exists $env(GP_FILTERS)]} {
    foreach i [exec ls $env(GP_FILTERS)] {
	read_filters $env(GP_FILTERS)/$i
    }
} elseif {[file exists $FILTERS_DIR]} {
    foreach i [exec ls $FILTERS_DIR] { read_filters $FILTERS_DIR/$i }
} else {
    Copyright ; puts "\t フィルタ定義ファイルが一つもありません\n" ; exit
}


# Initialize Temporary Variables
for {set i 1} {$i <= $maxTP} {incr i} {
    if {[info exists COMMAND(TEXT,$i,DEFAULT_OPTIONS)]} {
	set Opt(TEXT,$i)    $COMMAND(TEXT,$i,DEFAULT_OPTIONS)
	set tmpOpt(TEXT,$i) $COMMAND(TEXT,$i,DEFAULT_OPTIONS)
    } else {
	set Opt(TEXT,$i) "" ; set tmpOpt(TEXT,$i) ""
    }
}
for {set i 1} {$i <= $maxDP} {incr i} {
    if {[info exists COMMAND(DVI,$i,DEFAULT_OPTIONS)]} {
	set Opt(DVI,$i)    $COMMAND(DVI,$i,DEFAULT_OPTIONS)
	set tmpOpt(DVI,$i) $COMMAND(DVI,$i,DEFAULT_OPTIONS)
    } else {
	set Opt(DVI,$i) "" ; set tmpOpt(DVI,$i) ""
    }
}
for {set i 1} {$i <= $maxIP} {incr i} {
    if {[info exists COMMAND(Image,$i,DEFAULT_OPTIONS)]} {
	set Opt(Image,$i)    $COMMAND(Image,$i,DEFAULT_OPTIONS)
	set tmpOpt(Image,$i) $COMMAND(Image,$i,DEFAULT_OPTIONS)
    } else {
	set Opt(Image,$i) "" ; set tmpOpt(Image,$i) ""
    }
}

# Make Temporary Directory
exec $RM -rf $TMPDIR/$USER ; exec $MKDIR $TMPDIR/$USER
set TMPDIR "$TMPDIR/$USER"


# change_orient -- Changing Orientation Sample
#
# Argument     : Widget Path and points
# Return Value : None
#
proc change_orient {w x1 y1 x2 y2 x3 y3 x4 y4 x5 y5 xT yT} {
    global kfont
    
    $w delete sample 
    $w create polygon $x1 $y1 $x2 $y2 $x3 $y3 $x4 $y4 $x5 $y5 \
	    -fill white -outline black -width 2 -tags sample
    $w create line $x2 $y2 $x2 $y3 $x3 $y3 -width 2 -tags sample
    $w create text $xT $yT -text "あ" -kanjifont $kfont(5) -tags sample
}


# change_printOption -- Changing the Status of Print Options
#
# Argument     : Widget Path and File Type
# Return Value : None
#
proc change_printOption {w type} {
    global tmpRange tmpisNUP selectColor numTP numDP numIP COMMAND isPSUTILS

    # Variables for changing widget properties
    set opt_nor_1 "-state normal   -fg black"
    set opt_nor_2 "-state normal   -fg black -selectcolor $selectColor"
    set opt_dis_1 "-state disabled -fg gray50"
    set opt_dis_2 "-state disabled -fg gray50 -selectcolor gray80"

    # Checking the file type and direction for sending
    set tmpNum NO_Number
    if {$type == "TEXT"} {
	set tmpNum $numTP
    } elseif {$type == "DVI"} {
	set tmpNum $numDP
    } elseif {$type == "Image"} {
	set tmpNum $numIP
    }

    set sendType ""
    if {$tmpNum != "NO_Number"} {
	set sendType [lindex [split $COMMAND($type,$tmpNum,TYPE) "to"] 2]
    }

    # If filetype is PS and you don't have psutils,
    # or you send a file to a printer directly, all print options except
    # print number will be disabled. And if filetype is Image, all 
    # except print number and preview are disabled.
    if {$type == "Image" || ( $type == "PS" && $isPSUTILS != "YES")\
	    || $sendType == "DIRECT"} {
	
	foreach j {portrait landscape all specified num rev nupNO\
		nupYES scale} {
	    eval $w.$j conf $opt_dis_2
	}
	foreach j {from to nup paper} {
	    eval $w.$j conf $opt_dis_1
	}
	$w.canvas itemconf pagerange -fill gray50
	$w.canvas itemconf persheet -fill gray50
    } else {
	# If filetype is Text, DVI, PS(when with psutils), many options
	# are selectable. 
	set isPS_OK [expr {$type == "PS" || $sendType == "PS"} &&\
		{$isPSUTILS == "YES"}]

	# Paper Orientation
	if {[info exists COMMAND($type,$tmpNum,ORIENT_PORT)]} {
	    eval $w.portrait  conf $opt_nor_2
	    eval $w.landscape conf $opt_nor_2
	} else {
	    eval $w.portrait  conf $opt_dis_2
	    eval $w.landscape conf $opt_dis_2
	}

	# Print Range
	if {$isPS_OK || [info exists COMMAND($type,$tmpNum,PAGE_FROM)]} {
	    if {$tmpRange == "All"} {
		eval $w.from conf $opt_dis_1
		eval $w.to   conf $opt_dis_1
		$w.canvas itemconf pagerange -fill gray50
	    } else {
		eval $w.from conf $opt_nor_1
		eval $w.to   conf $opt_nor_1
		$w.canvas itemconf pagerange -fill black
	    }
	    eval $w.all conf $opt_nor_2
	    eval $w.specified conf $opt_nor_2
	} else {
	    eval $w.from conf $opt_dis_1 ; eval $w.to conf $opt_dis_1
	    eval $w.all  conf $opt_dis_2 ; eval $w.specified conf $opt_dis_2
	}

	# Multiple Page
	if {$isPS_OK || [info exists COMMAND($type,$tmpNum,MULTI_PAGE)] || \
		[info exists COMMAND($type,$tmpNum,TWOinONE)]} {
	    eval $w.nupNO conf $opt_nor_2 ; eval $w.nupYES conf $opt_nor_2
	} else {
	    eval $w.nupNO conf $opt_dis_2 ; eval $w.nupYES conf $opt_dis_2
	}
	if {$tmpisNUP == "YES"} {
	    eval $w.num conf $opt_nor_2
	    $w.canvas itemconf persheet -fill black
	}

	# Numbering Checkbutton
	if {$type == "TEXT" && [info exist COMMAND($type,$tmpNum,NUMBERING)]} {
	    eval $w.num conf $opt_nor_2
	} else {
	    eval $w.num conf $opt_dis_2
	}

	# Reverse Page Order
	if {$isPS_OK ||	[info exists COMMAND($type,$tmpNum,REVERSE_ORDER)]} {
	    eval $w.rev conf $opt_nor_2
	} else {
	    eval $w.rev conf $opt_nor_2
	}

	$w.paper     conf -state normal -fg black
	if {$sendType == "PS" || $type == "PS"} {
	    eval $w.scale conf $opt_nor_2
	} else {
	    eval $w.scale conf $opt_nor_2
	}
    }

    # PS Preview Button
    if {$sendType == "PS" || $type == "PS"} {
	eval $w.prev conf $opt_nor_1
    } else {
	eval $w.prev conf $opt_dis_1
    }

    # Printer Selection Button
    if {$sendType == "DIRECT2"} {
	$w.printer conf -state disabled
    } else {
	$w.printer conf -state normal
    }

    # Check a viwer for the file
    check_viewer $w $type
}


# check_viewer -- Check the Viewer for the file
#
# Argument     : Widget Path and File Type
# Return Value : None
#
proc check_viewer {w filetype} {
    global PS_PREVIEWER DVI_PREVIEWER IMAGE_PREVIEWER PAGER TERM

    set isVIEWER YES
    if {$filetype == "TEXT"} {
	if {![info exists TERM] || ![info exists PAGER]} {
	    set isVIEWER NO
	}
    } elseif {$filetype == "PS" && ![info exists PS_PREVIEWER]} {
	set isVIEWER NO
    } elseif {$filetype == "DVI" && ![info exists DVI_PREVIEWER]} {
	set isVIEWER NO
    } elseif {$filetype == "Image" && ![info exists IMAGE_PREVIEWER]} {
	set isVIEWER NO
    }

    if {$isVIEWER == "NO"} {
	$w.view conf -state disabled -fg gray50
    } else {
	$w.view conf -state normal -fg black
    }

    # Paper Selection Menu
    create_paperMenu $w $filetype
}


# create_paperMenu -- Changing Paper Selection Menu
#
# Argument     : Widget Path and File Type
# Return Value : None
#
proc create_paperMenu {w filetype } {
    global numTP numDP numIP Scale PAPER_LIST paperInfo defaultPaper font
    global tmpPaper COMMAND kfont

    if {$filetype == "TEXT"} {
	set tmpNum $numTP
    } elseif {$filetype == "DVI"} {
	set tmpNum $numDP
    } else {
	set tmpNum $numIP
    }

    destroy $w.paper.m ; menu $w.paper.m -tearoff 0

    if {$Scale == "YES"} {
	foreach j [split $PAPER_LIST ","] {
	    $w.paper.m add command -font $font(2) -label \
		    [format "%-12s\t%-s" $j $paperInfo($j)] \
		    -command "set tmpPaper $j ;\
		    set isPaperChanged YES ; $w.paper conf -text \
		    {[format "%-10s %-s" $j $paperInfo($j)]}"
	}
	set tmpPaper [lindex [split $PAPER_LIST ","] 0]
	$w.paper conf -text [format "%-10s %-s" $tmpPaper \
		$paperInfo($tmpPaper)]
    } else {
	if {$filetype == "PS"} {
	    $w.paper conf -text [format "%-10s %-s" $defaultPaper \
		    $paperInfo($defaultPaper)]
	    $w.paper.m add command -label "他の用紙は選択できません" \
		    -kanjifont $kfont(2)
	    set tmpPaper $defaultPaper ; return 0
	}

	set isPaper NO
	foreach j [split $PAPER_LIST ","] {
	    if {[info exists COMMAND($filetype,$tmpNum,$j)]} {
		if {$isPaper == "NO"} {
		    $w.paper conf -text [format "%-10s %-s" $j \
			    $paperInfo($j)]
		    set tmpPaper $j
		}
		$w.paper.m add command -font $font(2) -label \
			[format "%-12s\t%-s" $j $paperInfo($j)] \
			-command "set tmpPaper $j ;\
			set isPaperChanged YES ; $w.paper conf -text \
			{[format "%-10s %-s" $j $paperInfo($j)]}"
		set isPaper YES
	    }
	}
	if {$isPaper == "NO"} {
	    $w.paper.m add command  -label "他の用紙は選択できません" \
		    -kanjifont $kfont(2)
	}
    }
}


# draw_demibox -- Draw Surrounding Box which is discontinuous somewhere
#
# Argument     : Widget Path and 6 Points for drawing line
# Return Value : None
#
proc draw_demibox {w x1 y1 x2 y2 x3 y3 x4 y4 x5 y5 x6 y6} {
    $w create line $x1 $y1 $x2 $y2 $x3 $y3 $x4 $y4 $x5 $y5 $x6 $y6
}


# make_file -- Making a file for print/preview from specified file
#
# Argument     : File type and Options for printing the file
# Return Value : 0 if this procedure finishes normally
#
proc make_file {filetype filename orient paper range isNUP numNUP \
	isNUM isREV} {
    global TMPDIR RM MV COMMAND Opt isPSUTILS numTP numDP numIP
    global PSNUP PSRESIZE PSSELECT PSTOPS Scale tmpFrom tmpTo

    # A variable for cheking making a temporary file
    set isMakeTMP NO

    # Variables for Execution of Print Option
    set finPAPER "" ; set finORIENT  "" ; set finRANGE ""
    set finMULTI "" ; set finLINENUM "" ; set finREV   ""

    set sendType "PS" ; set type $filetype
    # Conversion a file if it is not PS file
    if {$type != "PS"} {
	set addOPTION ""

	# Set Filter Number 
	if {$type == "TEXT"} {
	    set numF $numTP
	} elseif {$type == "DVI"} {
	    set numF $numDP
	} elseif {$type == "Image"} {
	    set numF $numIP
	} else {
	    return
	}
	set sendType [lindex [split $COMMAND($type,$numF,TYPE) "to"] 2]

	# Paper Selection
	if {[info exists COMMAND($type,$numF,PAPER_OPTION)] && \
		[info exists COMMAND($type,$numF,$paper)]} {
	    set addOPTION "$COMMAND($type,$numF,PAPER_OPTION) \
		    $COMMAND($type,$numF,$paper)"
	    set finPAPER YES
	}

	# Paper Orientation
	set orientOPTION ""
	if {$orient == "portrait" && \
		[info exists COMMAND($type,$numF,ORIENT_PORT)]} {
	    set orientOPTION $COMMAND($type,$numF,ORIENT_PORT)
	    set finORIENT YES
	} elseif {$orient == "landscape" && \
		[info exists COMMAND($type,$numF,ORIENT_LAND)]} {
	    set orientOPTION $COMMAND($type,$numF,ORIENT_LAND)
	    set finORIENT YES
	}

	# Multiple Pages
	set multiOPTION ""
	if {$isNUP == "YES" && \
		[info exists COMMAND($type,$numF,MULTI_PAGE)]} {
	    set multiOPTION $COMMAND($type,$numF,MULTI_PAGE)
	    set finMULTI YES
	} elseif {$isNUP == "YES" && $type == "TEXT" && $numNUP == 2 && \
		[info exists COMMAND($type,$numF,TWOinONE)]} {
	    set multiOPTION $COMMAND($type,$numF,TWOinONE)
	    set finMULTI YES
	}

	# Set Option of Paper Orinentation and Multi Pages 
	if {$type == "TEXT" && \
		[info exists COMMAND($type,$numF,OPTION_REVERSE)] && \
		$COMMAND($type,$numF,OPTION_REVERSE) == "YES"} {
	    set addOPTION "$addOPTION $orientOPTION $multiOPTION"
	} else {
	    set addOPTION "$addOPTION $multiOPTION $orientOPTION"
	}

	# Print Range
	if {$range == "Specified" && \
		[info exists COMMAND($type,$numF,PAGE_FROM)]} {
	    set addOPTION "$addOPTION \
		    $COMMAND($type,$numF,PAGE_FROM) $tmpFrom \
		    $COMMAND($type,$numF,PAGE_TO) $tmpTo"
	    set finRANGE YES
	}

	# Numbering
	if {$isNUM == "YES" && $type == "TEXT" && \
		[info exists COMMAND($type,$numF,NUMBERING)]} {
	    set addOPTION "$addOPTION $COMMAND($type,$numF,NUMBERING)"
	    set finLINENUM YES
	}

	# Reverse Order
	if {$isREV == "YES" && \
		[info exists COMMAND($type,$numF,REVERSE_ORDER)] } {
	    set addOPTION "$addOPTION $COMMAND($type,$numF,REVERSE_ORDER)"
	    set finREV YES
	}

	# File Label
	if {[info exists COMMAND($type,$numF,FILE_LABEL)]} {
	    set addOPTION "$addOPTION $COMMAND($type,$numF,FILE_LABEL)\
		     [file tail $filename]"
	}

	if {$sendType != "DIRECT2"} {
	    catch {eval exec $COMMAND($type,$numF,PATH) \
		    $Opt($type,$numF) $addOPTION\
		    $COMMAND($type,$numF,INPUT_FROM) $filename \
		    $COMMAND($type,$numF,OUTPUT_TO) $TMPDIR/tmpfile.ps}
	} else {
	    catch {eval exec $COMMAND($type,$numF,PATH) \
		    $Opt($type,$numF) $addOPTION\
		    $COMMAND($type,$numF,INPUT_FROM) $filename}
	    return 0
	}

	if {[file exists $TMPDIR/tmpfile.ps] == 0 || \
		[file size $TMPDIR/tmpfile.ps] == 0} {
	    tk_dialog .err "変換失敗" \
		    "指定されているフィルタは [file tail $filename]\
		    を変換できませんでした" error 0 OK
	    return 1
	}
    }

    # If you have psutils, you can change file properties.
    if {$isPSUTILS == "YES" && $sendType == "PS"} {
	# A variable for original filename executed by Psutils
	if {$filetype == "PS"} {
	    set origFile $filename
	} else {
	    set origFile $TMPDIR/tmpfile.ps
	}

	# Execution without Image files
	if {$filetype != "Image"} {
	    # Execution of Selecting pages
	    if {$range == "Specified" && $finRANGE != "YES"} {
		if {$finMULTI == "YES"} {
		    set tempFrom [expr int(ceil(double($tmpFrom)/$numNUP))]
		    set tempTo   [expr int(ceil(double($tmpTo)/$numNUP))]
		} else {
		    set tempFrom $tmpFrom ; set tempTo $tmpTo
		}

		catch {eval exec $PSSELECT -p$tempFrom-$tempTo $origFile \
			> $TMPDIR/tmpfile2}
		catch {exec $MV $TMPDIR/tmpfile2 $TMPDIR/tmpfile.ps}
		set isMakeTMP YES
	    }

	    # Execution of Multiple pages/sheet
	    if {$isNUP == "YES" && $finMULTI != "YES"} {
		if {$isMakeTMP == "YES"} {
		    catch {exec $PSNUP -$numNUP $TMPDIR/tmpfile.ps > \
			    $TMPDIR/tmpfile2}
		} else {
		    catch {exec $PSNUP -$numNUP $origFile > $TMPDIR/tmpfile2}
		    set isMakeTMP YES
		}
		catch {exec $MV $TMPDIR/tmpfile2 $TMPDIR/tmpfile.ps}
	    }

	    # Execution of Reverse Order
	    if {$isREV == "YES" && $finREV != "YES"} {
		if {$isMakeTMP == "YES"} {
		    catch {exec $PSSELECT -r $TMPDIR/tmpfile.ps > \
			    $TMPDIR/tmpfile2}
		} else {
		    catch {exec $PSSELECT -r $origFile > $TMPDIR/tmpfile2}
		    set isMakeTMP YES
		}
		catch {exec $MV $TMPDIR/tmpfile2 $TMPDIR/tmpfile.ps}	    
	    }

	    # Changing Output Paper Size
	    set ps_paper [string tolower $paper]
	    if {$isMakeTMP == "NO" && $finPAPER != "YES" \
		    && $finMULTI != "YES"} {
		catch {exec $PSRESIZE -p$ps_paper $origFile > $TMPDIR/tmpfile2}
		catch {eval exec $MV $TMPDIR/tmpfile2 $TMPDIR/tmpfile.ps}
	    } elseif {$finPAPER != "YES"} {
		catch {exec $PSRESIZE -p$ps_paper $TMPDIR/tmpfile.ps > \
			$TMPDIR/tmpfile2}
		catch {eval exec $MV $TMPDIR/tmpfile2 $TMPDIR/tmpfile.ps}
	    }
	}
    }
    catch {exec $MV $TMPDIR/tmpfile.ps $TMPDIR/[file tail $filename]}

    # Check filesize for judge whether the file was created correctly
    if {[file size $TMPDIR/[file tail $filename]] == 0} {
	set tmp [tk_dialog .err "エラー(GP)" \
		"プレビューあるいは印刷用のファイルを作成できませんでした \n\
		(指定したオプションなどを確認して下さい)" error 0 OK]
	return 1 ;# Then never preview/print the file(Failure)
    } else {
	return 0 ;# Then preview/print the file
    }
}


# print -- Select and Print a File
#
# Argument     : Top Path
# Return Value : None
#
proc print { w } {
    if {[winfo exist .print]} { return 1 }
    toplevel .print -bd 5 -relief flat ; wm group .print $w 

    wm title .print "Print"

    global font kfont afcolor printers comments printfile filetype filelist 
    global defaultprn Printer Comment FileType PAPER_LIST paperInfo
    global defaultPaper paperOrient MaxCopy MaxNUP isNUP isLNUM isREV
    global isPaperChanged selectColor PS_UTILS_PATH
    global tmpRange tmpFrom tmpTo tmpOrient tmpisNUP tmpNUP tmpCopy
    global tmpLNUM tmpREV tmpPaper Scale numTP


    set tmpRange "All"   ; set tmpFrom 1 ; set tmpTo 999 ; set tmpNUP  2
    set tmpisNUP $isNUP  ; set tmpOrient $paperOrient    ; set tmpCopy 1
    set tmpLNUM  $isLNUM ; set tmpREV $isREV  ; set isPaperChanged NO
    set tmpPaper [format "%-10s %-s" $defaultPaper $paperInfo($defaultPaper)]


    if {$Printer == ""} {
	set Printer $printers(0) ; set Comment $comments($printers(0))
    }
    if {$FileType == ""} {set FileType $filelist(0)}

    # Setting the height and width of a canvas and several regions
    set cHeight 650 ; set cWidth 500

    # Canvas for many widgets
    canvas .print.canvas -width $cWidth -height $cHeight -relief groove -bd 2


    #
    # Widgets which will be on the canvas
    #
    # Buttons
    button .print.prev -text "PS ファイルプレビュー" -font $font(2) -bd 3 \
	    -kanjifont $kfont(2) -width 20 -activeforeground #00C4A6 \
	    -command {preview $printfile $FileType $tmpOrient $tmpPaper \
	    $tmpRange $tmpisNUP $tmpNUP $tmpLNUM $tmpREV}
    button .print.save -text "変換して保存する" -kanjifont $kfont(2) -bd 3 \
	    -width 24 -activeforeground midnightblue \
	    -command {save $printfile $FileType $tmpOrient $tmpPaper \
	    $tmpRange $tmpisNUP $tmpNUP $tmpLNUM $tmpREV}
    button .print.view -text "ファイルを見る" -kanjifont $kfont(2) \
	    -font $font(2) -bd 3 -width 20 -activeforeground #f200A6 \
	    -command {view_file $printfile $FileType }
    button .print.ok -text "印刷する"  -kanjifont $kfont(2) -bd 3 -width 24 \
	    -activeforeground $afcolor -command {
	if {$printfile != ""} {
	    set print_result [printing $printfile $FileType $tmpOrient \
		    $tmpPaper $tmpRange $tmpisNUP $tmpNUP $tmpLNUM $tmpREV \
		    $tmpCopy]
	    if {$print_result == 0} { record_history $printfile }
	}
    }
    button .print.close -text "閉じる" -kanjifont $kfont(2) -bd 3 -width 8\
	    -activeforeground red \
	    -command {if {[winfo exist .print]} {destroy .print} ; return 1 } 
    button .print.options -text "オプション" -kanjifont $kfont(2) -bd 3 \
	    -width 10 -activeforeground #3EE26A \
	    -command {option_conf .print $FileType}
    button .print.brw  -text "一覧" -kanjifont $kfont(2) -bd 3\
	    -activeforeground $afcolor  -command { 
	set printfile [set_printFile .print]
    }

    # Entries
    entry .print.file -font $font(2) -width 30 -textvariable printfile 
    entry .print.from -width 3 -font $font(2) -bd 3 -textvariable tmpFrom \
	    -fg gray50 -state disabled
    entry .print.to   -width 3 -font $font(2) -bd 3 -textvariable tmpTo \
	    -fg gray50 -state disabled
    entry .print.nup  -width 3 -font $font(2) -bd 3 -textvariable tmpNUP \
	    -fg gray50 -state disabled
    entry .print.copy  -width 3 -font $font(2) -bd 3 -textvariable tmpCopy \
	    -fg black -state normal

    # Radiobuttons
    radiobutton .print.all  -text "全ページ" -kanjifont $kfont(2) -width 14 \
	    -anchor w -variable tmpRange -value "All" -command { \
	    .print.canvas itemconf pagerange -fill gray50 ; \
	    .print.from conf -state disabled -fg gray50 ; \
	    .print.to   conf -state disabled -fg gray50 ; \
	    .print.canvas focus .print.rAll }
    set selectColor [.print.all cget -selectcolor]
    radiobutton .print.specified -text "指定範囲のみ" -kanjifont $kfont(2) \
	    -width 14 -anchor w -variable tmpRange -value "Specified" \
	    -command { .print.canvas itemconf pagerange -fill black ; \
	    .print.from conf -state normal -fg black ; \
	    .print.to   conf -state normal -fg black }
    radiobutton .print.portrait  -text "縦方向" -kanjifont $kfont(2) \
	    -width 10 -anchor w -variable tmpOrient -value "portrait"
    radiobutton .print.landscape -text "横方向" -kanjifont $kfont(2) \
	    -width 10 -anchor w -variable tmpOrient -value "landscape"
    radiobutton .print.nupNO  -text "いいえ" -kanjifont $kfont(2) -width 6 \
	    -anchor w -variable tmpisNUP -value NO  -command { \
	    .print.nup conf -state disabled -fg gray50 ; \
	    .print.canvas itemconf persheet -fill gray50
    }
    radiobutton .print.nupYES -text "はい" -kanjifont $kfont(2) -width 6 \
	    -anchor w -variable tmpisNUP -value YES -command { \
	    .print.nup conf -state normal -fg black ; \
	    .print.canvas itemconf persheet -fill black
    }

    # Checkbuttons
    checkbutton .print.num -text "行番号の付加" -kanjifont $kfont(2) -bd 3 \
	    -variable tmpLNUM -onvalue YES -offvalue NO
    checkbutton .print.scale -text "はい" -kanjifont $kfont(2) -bd 3 \
	    -variable Scale -onvalue YES -offvalue NO \
	    -command {create_paperMenu .print $FileType}
    checkbutton .print.rev -text "逆順印刷" -kanjifont $kfont(2) -bd 3 \
	    -variable tmpREV -onvalue YES -offvalue NO

    # Menus
    menubutton .print.printer -text "$Printer" -font $font(3) -width 10 \
	    -bd 3 -relief raised -anchor c -menu .print.printer.m \
	    -activeforeground $afcolor
    menu .print.printer.m -activeforeground $afcolor -tearoff 0 \
	    -font $font(2) -kanjifont $kfont(2)
    for {set i 0} {$printers($i) != "END"} {incr i} {
	.print.printer.m add command -font $font(2) \
		-label "[format "%-12s\t%-s" $printers($i) \
		$comments($printers($i))]" \
		-command "set Printer $printers($i) ; \
		.print.printer conf -text $printers($i) ; \
		.print.canvas itemconf printercomment \
		-text {$comments($printers($i))} -font $font(2) \
		-kanjifont $kfont(2)"
    }
    menubutton .print.filetype -text "$FileType" -font $font(3) -width 6 \
	    -bd 2 -relief raised -anchor c -menu .print.filetype.m \
	    -activeforeground $afcolor
    menu .print.filetype.m -activeforeground $afcolor -tearoff 0
    for {set i 0} {$filelist($i) != "END"} {incr i} {
	if {$defaultprn($filelist($i)) == "UNUSE"} {continue}
	.print.filetype.m add command -font $font(2) \
		-label "$filelist($i)" -command "set FileType $filelist($i) ;\
		.print.filetype conf -text $filelist($i) ;\
		.print.printer conf  -text $defaultprn($filelist($i)) ;\
		set Printer $defaultprn($filelist($i)) ;\
		change_printOption .print $filelist($i)"
    }
    menubutton .print.paper -text "$tmpPaper" -font $font(1) -width 28 \
	    -bd 2 -relief raised -anchor w -menu .print.paper.m \
	    -activeforeground $afcolor
    if {[winfo exists .print.paper.m]} {destroy .print.paper.m}
    menu .print.paper.m -activeforeground $afcolor -tearoff 0


    # Creating Windows on the Canvas
    #
    # For selecting a file
    set nameX 20 ; set nameY 30
    .print.canvas create text $nameX $nameY -text "ファイル" \
	    -kanjifont $kfont(2) -anchor w
    .print.canvas create text [expr $nameX + 20] [expr $nameY + 30] \
	    -text "ファイル名 : " -kanjifont $kfont(2) -anchor w
    .print.canvas create window [expr $nameX + 120] [expr $nameY + 30] \
	    -window .print.file -anchor w
    .print.canvas create window [expr $cWidth - 20] [expr $nameY + 30] \
	    -window .print.brw -anchor e
    .print.canvas create text [expr $nameX + 20] [expr $nameY + 60] \
	    -text "ファイルのタイプ : " -kanjifont $kfont(2) -anchor w
    .print.canvas create window [expr $nameX + 180] [expr $nameY + 65] \
	    -window .print.filetype -anchor w
    draw_demibox .print.canvas 15 $nameY 10 $nameY 10 [expr $nameY + 90]\
	    [expr $cWidth - ($nameX - 15)] [expr $nameY + 90] \
	    [expr $cWidth - ($nameX - 15)] $nameY 90 $nameY

    # For Selecting a printer
    set printerX 20 ; set printerY 140
    .print.canvas create text $printerX $printerY -text "プリンタ" \
            -kanjifont $kfont(2) -anchor w
    .print.canvas create text [expr $printerX+20] [expr $printerY+30] \
	    -text "プリンタ名" -kanjifont $kfont(2) -anchor w
    .print.canvas create window [expr $printerX+110] [expr $printerY+30] \
	    -window .print.printer -anchor w 
    .print.canvas create text [expr $printerX+20]  [expr $printerY+60] \
            -text "コメント" -kanjifont $kfont(2) -anchor w
    .print.canvas create text [expr $printerX+115] [expr $printerY+60] \
	    -text $Comment -font $font(1) -kanjifont $kfont(1) \
	    -anchor w -tags printercomment
    .print.canvas create text [expr $printerX+20]  [expr $printerY+90] \
            -text "用紙" -kanjifont $kfont(2) -anchor w
    .print.canvas create window [expr $printerX+110] [expr $printerY+90]\
	    -window .print.paper -anchor w
    draw_demibox .print.canvas 15 $printerY 10 $printerY \
	    10 [expr $printerY + 110] \
	    [expr $cWidth - ($printerX-15)] [expr $printerY + 110] \
	    [expr $cWidth - ($printerX-15)] $printerY 90 $printerY
    if {[info exists PS_UTILS_PATH] && $PS_UTILS_PATH != ""} {
	.print.canvas create text [expr $printerX+345] [expr $printerY+30] \
		-text "用紙の\nスケーリング" -kanjifont $kfont(2) -anchor w
	.print.canvas create window [expr $printerX+420] [expr $printerY+70] \
		-window .print.scale -anchor e
	draw_demibox .print.canvas [expr $printerX+340] [expr $printerY+30]\
		[expr $printerX+335] [expr $printerY+30] \
		[expr $printerX+335] [expr $printerY+90] \
		[expr $printerX+450] [expr $printerY+90] \
		[expr $printerX+450] [expr $printerY+30] \
		[expr $printerX+445] [expr $printerY+30] 
    }

    # For selecting print pages
    set pageX 280 ; set pageY 270
    .print.canvas create text $pageX $pageY -text "印刷範囲" \
	    -anchor w -kanjifont $kfont(2) -anchor w
    .print.canvas create window [expr $pageX + 20] [expr $pageY + 35]\
	    -window .print.all -anchor w
    .print.canvas create window [expr $pageX + 20] [expr $pageY + 65]\
	    -window .print.specified -anchor w
    .print.canvas create text [expr $pageX + 30] [expr $pageY + 85] \
	    -text "開始\nページ" -fill gray50 -anchor nw -kanjifont $kfont(2) \
	    -tags pagerange
    .print.canvas create window [expr $pageX + 80] [expr $pageY + 95] \
	    -window .print.from -anchor w
    .print.canvas create text [expr $pageX + 121] [expr $pageY + 85] \
	    -text "終了\nページ" -fill gray50 -anchor nw -kanjifont $kfont(2) \
	    -tags pagerange
    .print.canvas create window [expr $pageX + 170] [expr $pageY + 95] \
	    -window .print.to -anchor w
    draw_demibox .print.canvas [expr $pageX - 5] $pageY \
	    [expr $pageX - 10]  $pageY \
	    [expr $pageX - 10]  [expr $pageY + 130] \
	    [expr $cWidth - 5] [expr $pageY + 130] \
	    [expr $cWidth - 5] $pageY [expr $pageX + 75 ] $pageY

    # For selecting Paper Orientation
    set orientX 20 ; set orientY 270
    set sPSx [expr $orientX + 20]    ;  set sPSy [expr $orientY + 20]
    set ePSx [expr $sPSx + 50]       ;  set ePSy [expr $sPSy + 80]
    set sLSx [expr $orientX + 10]    ;  set sLSy [expr $orientY + 30]
    set eLSx [expr $sLSx + 75]       ;  set eLSy [expr $sLSy + 60]
    .print.canvas create text $orientX $orientY  -text "用紙方向" \
	    -anchor w -kanjifont $kfont(2)
    draw_demibox .print.canvas [expr $orientX - 5] $orientY \
	    [expr $orientX - 10]  $orientY \
	    [expr $orientX - 10]  [expr $orientY + 130] \
	    [expr $orientX + 230] [expr $orientY + 130] \
	    [expr $orientX + 230] $orientY [expr $orientX + 75] $orientY
    # Orientation Sample
    if {$tmpOrient == "portrait"} {
	change_orient .print.canvas $sPSx $sPSy [expr $ePSx - 10] $sPSy \
		$ePSx [expr $sPSy + 10] $ePSx $ePSy $sPSx $ePSy \
		[expr $orientX + 45] [expr $orientY + 60]
    } else {
	change_orient .print.canvas $sLSx $sLSy [expr $eLSx - 10] $sLSy \
		$eLSx [expr $sLSy + 10] $eLSx $eLSy $sLSx $eLSy  \
		[expr $orientX + 45] [expr $orientY + 60]
    }
    .print.portrait conf  -command "change_orient .print.canvas \
	    $sPSx $sPSy [expr $ePSx - 10] $sPSy $ePSx [expr $sPSy + 10] \
	    $ePSx $ePSy $sPSx $ePSy \
	    [expr $orientX + 45] [expr $orientY + 60]"
    .print.landscape conf -command "change_orient .print.canvas \
	    $sLSx $sLSy [expr $eLSx - 10] $sLSy $eLSx [expr $sLSy + 10] \
	    $eLSx $eLSy $sLSx $eLSy \
	    [expr $orientX + 45] [expr $orientY + 60]"
    .print.canvas create window [expr $orientX + 100] [expr $orientY + 50] \
	    -window .print.portrait  -anchor w
    .print.canvas create window [expr $orientX + 100] [expr $orientY + 80] \
	    -window .print.landscape -anchor w

    # For selecting multiple pages on one sheet
    set nupX 20 ; set nupY 420
    .print.canvas create text $nupX $nupY -text "段組み印刷" -anchor w \
	    -kanjifont $kfont(2)
    .print.canvas create window [expr $nupX + 10] [expr $nupY + 30] \
	    -window .print.nupNO -anchor w
    .print.canvas create window [expr $nupX + 10] [expr $nupY + 60] \
	    -window .print.nupYES -anchor w
    .print.canvas create window [expr $nupX + 90] [expr $nupY + 60] \
	    -window .print.nup -anchor w
    .print.canvas create text  [expr $nupX + 130] [expr $nupY + 65] \
	    -text "ページ/枚" -anchor w -kanjifont $kfont(2) -fill gray50 \
	    -tags persheet
    draw_demibox .print.canvas 15 $nupY 10 $nupY 10 [expr $nupY + 90]\
	    [expr $nupX + 230] [expr $nupY + 90] \
	    [expr $nupX + 230] $nupY 110 $nupY

    # For setting the number of copies
    set copyX 280 ; set copyY 420
    .print.canvas create text $copyX $copyY -text "コピー枚数" \
	    -anchor w -kanjifont $kfont(2)
    .print.canvas create window [expr $copyX + 10] [expr $copyY + 35] \
	    -window .print.copy -anchor w
    .print.canvas create text [expr $copyX + 55] [expr $copyY + 40] \
	    -text "枚" -anchor w -kanjifont $kfont(2)
    draw_demibox .print.canvas [expr $copyX - 5]  $copyY \
	    [expr $copyX - 10] $copyY [expr $copyX - 10] [expr $copyY + 65]\
	    [expr $copyX + 120] [expr $copyY + 65] \
	    [expr $copyX + 120] $copyY [expr $copyX + 90] $copyY

    set checksY 530
    .print.canvas create window 20 $checksY -window .print.rev -anchor w
    .print.canvas create window 20 [expr $checksY + 25]\
	    -window .print.num -anchor w
    

    # Buttons for "Preview", "Print", "Close", "Options", and "Make a file"
    set buttonsY [expr $cHeight - 20]
    .print.canvas create window [expr $cWidth - 480] [expr $buttonsY - 40] \
	    -window .print.view -anchor w
    .print.canvas create window [expr $cWidth - 480] $buttonsY \
	    -window .print.prev -anchor w
    .print.canvas create window [expr $cWidth - 230] [expr $buttonsY - 80] \
	    -window .print.save -anchor w
    .print.canvas create window [expr $cWidth - 230] [expr $buttonsY - 40] \
	    -window .print.ok -anchor w
    .print.canvas create window [expr $cWidth - 120] $buttonsY \
	    -window .print.close -anchor w
    .print.canvas create window [expr $cWidth - 230] $buttonsY \
	    -window .print.options -anchor w

    # Packing
    pack .print.canvas 


    # Bindings 
    event add <<Ctrl+p_Or_Up>>     <Control-p> <Up>
    event add <<Ctrl+n_Or_Down>>   <Control-n> <Down>
    event add <<Ctrl+d_Or_Escape>> <Control-d> <Escape>
    event add <<Return_Or_Leave>>  <Return> <Leave>
    bind .print <<Ctrl+p_Or_Up>> \
	    {put_history pre ; check_filetype $printfile .print}
    bind .print <<Ctrl+n_Or_Down>> \
	    {put_history next ; check_filetype $printfile .print}
    bind .print.file <<Ctrl+d_Or_Escape>> {
	set printfile [complete $printfile] ; .print.file icursor end
	focus .print.file
    }
    bind .print.file <<Return_Or_Leave>> {
	if {[file isfile $printfile]} {
	    check_filetype $printfile .print ; focus .print.ok
	} else { set printfile "" }
    }
    bind .print.from <<Return_Or_Leave>> {
	if [catch {expr int($tmpFrom)}] {
	    set tmpFrom 1
	} else {
	    if {int($tmpFrom) < 0} {
		set tmpFrom 1
		tk_dialog .err "数字がマイナスです" "負数は指定できません" \
			error 0 OK
	    } else {
		set tmpFrom [expr int($tmpFrom)] ; focus .print
	    }
	}
    }
    bind .print.to <<Return_Or_Leave>> {
	if [catch {expr int($tmpTo)}] {
	    set tmpTo 999
	} else {
	    if {$tmpTo < $tmpFrom || $tmpTo < 0} {
		set tmpTo $tmpFrom
		tk_dialog .err "不正な数字" \
			"\"開始ページ\" よりも小さな数字は許可されません" \
			error 0 OK
	    } else {
		set tmpTo [expr int($tmpTo)] ; focus .print 
	    }
	}
    }
    bind .print.nup <<Return_Or_Leave>> {
	if [catch {expr int($tmpNUP)}] {
	    set tmpNUP 2
	} else {
	    if {int($tmpNUP) > $MaxNUP} {
		set tmpNUP $MaxNUP
		tk_dialog .err "多過ぎる段組み" \
			"$MaxNUP ページ/枚が最大数です.\n\
			(あなたのサイトの管理者に相談して下さい)" error 0 OK
	    } else {
		set tmpNUP [expr int($tmpNUP)] ; focus .print
	    }
	}
    }
    bind .print.copy <<Return_Or_Leave>> {
	if [catch {expr int($tmpCopy)}] {
	    set tmpCopy 1
	} else {
	    if {$tmpCopy > $MaxCopy} {
		set tmpCopy $MaxCopy
		tk_dialog .err "多過ぎる印刷部数" "$MaxCopy 部以上は\
			印刷できません\
			(あなたのサイトの管理者に相談して下さい)"\
			error 0 OK ; focus .print
	    } else {
		set tmpCopy [expr int($tmpCopy)] ; focus .print
	    }
	}
    }


    # Changing Print Option Status
    change_printOption .print PS

    # Check the Viewer for the file
    check_viewer .print $FileType

    # Make the Paper Menu
    create_paperMenu .print $FileType
}


# view_file -- View the File
# 
# Argument     : Filename and Filetype
# Return Value : None
#
proc view_file {filename filetype} {
    global PS_PREVIEWER DVI_PREVIEWER IMAGE_PREVIEWER PAGER TERM

    if {$filename == ""} { return 1 }

    if {[file size $filename] == 0} {
	tk_dialog .err "空ファイル" "$filename は空ファイルです" \
		error 0 OK
	return 1
    }

    if {$filetype == "PS"} {
	catch {eval exec $PS_PREVIEWER $filename} ; return 0
    } elseif {$filetype == "DVI"} {
	catch {eval exec $DVI_PREVIEWER $filename} ; return 0
    } elseif {$filetype == "Image"} {
	catch {eval exec $IMAGE_PREVIEWER $filename} ; return 0
    } else {
	catch {eval exec $TERM -e $PAGER $filename} ; return 0
    }
}


# preview -- Preivew Print File
# 
# Argument     : PrintFile and Options
# Return Value : None
#
proc preview {filename filetype orient paper range isNUP numNUP isNUM isREV} {
    global PS_PREVIEWER RM TMPDIR PSNUP isPaperChanged


    if {$filename == ""} { return 1 }

    if {[file size $filename] == 0} {
	tk_dialog .err "空ファイル" "$filename は空ファイルです" \
		error 0 OK
	return 1
    }


    # Output Paper Size 
    set paperSize [lindex [split $paper { }] 0]

    # Make a preview file and Preview
    if {$filetype == "TEXT"} {
	if {[make_file TEXT $filename $orient $paperSize \
		$range $isNUP $numNUP $isNUM $isREV ] == 0} {
	    catch {exec $PS_PREVIEWER $TMPDIR/[file tail $filename]}
	}
    } elseif {$filetype == "DVI"} {
	if {[make_file DVI $filename $orient $paperSize \
		$range $isNUP $numNUP "" $isREV ] == 0} {
	    catch {exec $PS_PREVIEWER $TMPDIR/[file tail $filename]}
	}
    } elseif {$filetype == "PS"} {
	if {$isNUP == "YES" || $isREV == "YES" || \
		$range == "Specified" || $isPaperChanged == "YES"} {
	    if {[make_file PS $filename $orient $paperSize \
		    $range $isNUP $numNUP "" $isREV ] == 0} {
		catch {exec $PS_PREVIEWER $TMPDIR/[file tail $filename]}
	    }
	} else {
	    catch {exec $PS_PREVIEWER $filename}
	}
    } elseif {$filetype == "Image"} {
	if {[make_file Image $filename $orient $paperSize $range $isNUP \
		$numNUP $isNUM $isREV ] == 0} {
	    catch {exec $PS_PREVIEWER $TMPDIR/[file tail $filename]}
	}
    } else {
	tk_dialog .err "失礼..." "そのファイルは印刷できません" info 0 OK
    }
}


# set_printFile -- Set Print File and Check Extension 
#
# Argument     : Path of Print Window
# Return Value : Print File Name
#
proc set_printFile { w } {
    global types Printer FileType filetype filelist defaultprn printfile
    global printers

    set printfile [tk_getOpenFile -title "Print File" -filetypes $types]
    if {$printfile == ""} {
	wm title $w "Print" ; return ""
    } else {
	wm title $w "Print - $printfile" ; cd [file dirname $printfile]
    }

    check_filetype $printfile $w ; return $printfile
}


# printing -- Print File
#
# Argument     : Options for printing
# Return Value : 0 ... Normal
#
proc printing {filename filetype orient paper range isNUP numNUP isNUM isREV copy} { 
    global PRINT_COM RM TMPDIR Printer COMMAND numTP numDP numIP
    global isPaperChanged isPSUTILS version

    if {[file size $filename] == 0} {
	set tmp [tk_dialog .err "空ファイル" "$filename は空ファイルです" \
		error 0 OK]
	return 1
    }

    set type $filetype

    # Checking the file type and direction for sending
    if {$type == "TEXT"} {
	set tmpNum $numTP
    } elseif {$type == "DVI"} {
	set tmpNum $numDP
    } elseif {$type == "Image"} {
	set tmpNum $numIP
    }
    set sendType ""
    if {[info exist tmpNum]} {
	set sendType [lindex [split $COMMAND($type,$tmpNum,TYPE) "to"] 2]
    }

    # Print with lpr command or spcified command depending on
    # the file type and the filter with or without making temporary files.
    #
    # Case of Print without making temporary file
    if {( $type == "PS" && $isPSUTILS != "YES") || $sendType == "DIRECT"} {
	catch {eval exec $PRINT_COM -P$Printer -#$copy [file tail $filename]}
	return 0
    }

    # Case of Print with making temporary file or of Print by the Filter
    #
    # A variable for checking whether there is a printable file or not
    set isPrintOK NO

    # Output Paper Size 
    set paperSize [lindex [split $paper { }] 0]

    # Making a file for print and printing
    if {$type == "TEXT"} {
	if {[make_file TEXT $filename $orient $paperSize $range $isNUP \
		$numNUP $isNUM $isREV ] == 0} {
	    set isPrintOK YES
	}
    } elseif {$type == "DVI"} {
	if {[make_file DVI $filename $orient $paperSize $range $isNUP \
		$numNUP "" $isREV ] == 0} {
	    set isPrintOK YES
	}
    } elseif {$type == "PS"} {
	if {$isNUP == "YES" || $isREV == "YES" || $range == "Specified" || \
		$isPaperChanged == "YES"} {
	    if {[make_file PS $filename $orient $paperSize \
		    $range $isNUP $numNUP "" $isREV ] == 0} {
		set isPrintOK YES
	    }
	} else {
	    catch {eval exec $PRINT_COM -P$Printer -#$copy \
		    [file tail $filename]} ; return 0
	}
    } elseif {$type == "Image"} {
	if {[make_file Image $filename $orient $paperSize $range $isNUP \
		$numNUP $isNUM $isREV ] == 0} {
	    set isPrintOK YES
	}
    } else {
	puts "GP ver. $version ではそのファイルは印刷できません…" ; return 1
    }

    # Printing if there is a printable file
    if {$isPrintOK == "YES"} {
	catch {eval exec $PRINT_COM -P$Printer -#$copy \
		$TMPDIR/[file tail $filename]} ; return 0
    } else { return 1 }
}


# option_conf -- Option Configuration
#
# Argument     : Window Path and File Type
# Return Value : None
#
proc option_conf {w type} {
    if {[winfo exist .option]} { return 1 }
    toplevel .option -bd 5 -relief flat ; wm group .option $w
    grab set .option

    global font kfont COMMAND numTP numDP numIP maxTP maxDP maxIP
    global tmpTP tmpDP tmpIP Opt afcolor tmpOpt FileType 

    wm title .option "フィルタ設定"

    set tmpTP $numTP ; set tmpDP $numDP ; set tmpIP $numIP
    for {set i 1} {$i <= $maxTP} {incr i} {set tmpOpt(TEXT,$i) $Opt(TEXT,$i)}
    for {set i 1} {$i <= $maxDP} {incr i} {set tmpOpt(DVI,$i)  $Opt(DVI,$i) }
    for {set i 1} {$i <= $maxIP} {incr i} {set tmpOpt(Image$i) $Opt(Image,$i)}

    # Widgets
    canvas .option.selectC  -width 400 -height  95 -bd 1 -relief flat
    canvas .option.mainC    -width 400 -height 270 -bd 3 -relief groove
    canvas .option.buttonsC -width 400 -height  50 -bd 3 -relief groove

    entry .option.default -font $font(3) -width 42 -bd 3 \
	    -textvariable tmpOpt(TEXT,$numTP)

    menubutton .option.num -menu .option.num.menu -text $tmpTP -font $font(3) \
	    -width 3 -bd 3 -relief raised -activeforeground $afcolor
    menu   .option.num.menu -tearoff 0
    for {set i 1} {$i <= $maxTP} {incr i} {
	if {[info exists COMMAND(TEXT,$i,COMMENT)]} {
	    .option.num.menu add radiobutton -label $i -variable tmpTP \
		    -value $i -font $font(3) -command "set tmpTP $i
	    .option.num conf -text $i ; filter_char .option TEXT"
	}
    }

    button .option.textB -text "TEXT" -font $font(3) -bd 4 -width 7\
	    -command {filter_char .option TEXT}
    button .option.dviB   -text "DVI" -font $font(3) -bd 4 -width 7\
	    -command {filter_char .option DVI}
    button .option.imageB -text "Image" -font $font(3) -bd 4 -width 7\
	    -command {filter_char .option Image}
    button .option.defaultB -text "システムデフォルト値" -kanjifont $kfont(2) \
	    -bd 3 -activeforeground darkgreen
    button .option.info -text "GP に関して" -font $font(2) \
	    -kanjifont $kfont(2) -bd 3 -width 10\
	    -activeforeground midnightblue -command {disp_ver .option}
    button .option.cancel -text "キャンセル" -kanjifont $kfont(2) \
	    -width 10 -bd 3\
	    -activeforeground blue -command {if {[winfo exist .option]} \
	    {destroy .option} ; grab release .option ; return 1}
    button .option.ok -text "閉じる" -kanjifont $kfont(2) -bd 3 -width 10\
	    -activeforeground red -command {if {[winfo exist .option]} \
	    {destroy .option} ; set numTP $tmpTP ; set numDP $tmpDP ; \
	    set numIP $tmpIP ; 
    for {set i 1} {$i <= $maxTP} {incr i} {set Opt(TEXT,$i)  $tmpOpt(TEXT,$i)}
    for {set i 1} {$i <= $maxDP} {incr i} {set Opt(DVI,$i)   $tmpOpt(DVI,$i)}
    for {set i 1} {$i <= $maxIP} {incr i} {set Opt(Image,$i) $tmpOpt(Image$i)}

    change_printOption .print $FileType
    grab release .option ; return 0}

    event add <<Return_Or_Leave>> <Return> <Leave>
    bind .option.default <<Return_Or_Leave>> { }

    
    .option.mainC create text 10  20 -text "フィルタタイプ : " \
	    -kanjifont $kfont(2) -anchor w
    .option.mainC create text 10  70 -text "フィルタ番号 : "\
	    -kanjifont $kfont(2) -anchor w
    .option.mainC create text 10 120 -text "コマンド : " \
	    -kanjifont $kfont(2) -anchor w
    .option.mainC create text 10 170 -text "コメント : " \
	    -kanjifont $kfont(2) -anchor w
    .option.mainC create text 10 220 -text "デフォルトオプション : " \
	    -kanjifont $kfont(2) -anchor w
    .option.mainC create window 10  250 -window .option.default  -anchor w
    .option.mainC create window 210 215 -window .option.defaultB -anchor w
    .option.mainC create window 130  70 -window .option.num      -anchor w


    # Widgets for File Type Selection
    .option.selectC create text 20 20 -text "ファイルタイプ" -anchor w\
	    -kanjifont $kfont(2)
    .option.selectC create window  80 60 -window .option.textB
    .option.selectC create window 200 60 -window .option.dviB
    .option.selectC create window 320 60 -window .option.imageB
    draw_demibox .option.selectC 15 20 3 20 3 90 404 90 404 20 140 20

    # Widgets for Filters Characteristics Selection
    .option.mainC create text 150  20 -text "" -font $font(3) \
	    -anchor w -tags filter_type
    .option.mainC create text  97 120 -text "" -font $font(3) -anchor w \
	    -tags filter_command
    .option.mainC create text  95 170 -text "" -font $font(3) -anchor w \
	    -tags filter_comment -kanjifont $kfont(2)

    # Widgets for Buttons
    .option.buttonsC create window 80  30 -window .option.info
    .option.buttonsC create window 210 30 -window .option.cancel
    .option.buttonsC create window 340 30 -window .option.ok

    pack .option.selectC .option.mainC .option.buttonsC -side top -expand yes \
	    -fill x -pady 2

    if {$type == "PS" || $type == "UNUSE"} {
	filter_char .option TEXT
    } else {
	filter_char .option $type
    }
}


# filter_char -- Set Select Menues for Filter Characteristics
#
# Argument     : Widget Path and File Type
# Return Value : None
#
proc filter_char {w type} {
    global font kfont COMMAND maxTP maxDP maxIP tmpTP tmpDP tmpIP Opt tmpOpt

    if {$type == "TEXT"} {
	set tmpNUM  $tmpTP ; set maxNUM $maxTP ; set tmpName tmpTP
    } elseif {$type == "DVI"} {
	set tmpNUM $tmpDP ; set maxNUM $maxDP ; set tmpName tmpDP
    } else {
	set tmpNUM $tmpIP ; set maxNUM $maxIP ; set tmpName tmpIP
    }

    if {[info exists COMMAND($type,$tmpNUM,PATH)]} {
	set commandName $COMMAND($type,$tmpNUM,PATH)
    } else {
	set commandName ""
    }

    set sendType [lindex [split $COMMAND($type,$tmpNUM,TYPE) "to"] 2]
    if {$sendType == "DIRECT2"} {
	set sendType "DIRECT by this Filter"
    }

    set commandType "[lindex [split $COMMAND($type,$tmpNUM,TYPE) "to"] 0]\
	    -> $sendType"
    if {[info exists COMMAND($type,$tmpNUM,COMMENT)]} {
	set commandComment $COMMAND($type,$tmpNUM,COMMENT)
    } else {
	set commandComment ""
    }

    $w.mainC itemconf filter_type    -text $commandType
    $w.mainC itemconf filter_command -text $commandName
    $w.mainC itemconf filter_comment -text $commandComment

    if {[info exists COMMAND($type,$tmpNUM,DEFAULT_OPTIONS)]} {
	$w.defaultB conf -command [list set tmpOpt($type,$tmpNUM) \
		$COMMAND($type,$tmpNUM,DEFAULT_OPTIONS)]
	$w.default conf -state normal -fg black \
		-textvariable tmpOpt($type,$tmpNUM)
    } else {
	$w.defaultB conf -command "set tmpOpt($type,$tmpNUM) \"\""
	$w.default conf -state disabled	-textvariable tmpOpt($type,$tmpNUM)
    }
    $w.num conf -text $tmpNUM

    destroy $w.num.menu ; menu $w.num.menu -tearoff 0
    for {set i 1} {$i <= $maxNUM} {incr i} {
	if {[info exists COMMAND($type,$i,COMMENT)]} {
	    $w.num.menu add radiobutton \
		    -label "$i  $COMMAND($type,$i,COMMENT)" -variable $tmpName\
		    -value $i -font $font(2) -kanjifont $kfont(2)\
		    -command "set $tmpName $i ; filter_char $w $type"
	}
    }

    return 0
}


# save -- Save the file as...
# 
# Argument     : PrintFile and Options
# Return Value : None
#
proc save {filename filetype orient paper range isNUP numNUP isNUM isREV} {
    global PS_PREVIEWER RM MV TMPDIR PSNUP isPaperChanged types

    if {$filename == ""} { return 1 }

    if {[file size $filename] == 0} {
	tk_dialog .err "空ファイル" "$filename は空ファイルです" \
		error 0 OK ; return 1
    }

    # Set a filename for saving
    set savefile [tk_getSaveFile -filetypes $types]
    if {$savefile == ""} {
	return 1
    } elseif {[file exists $savefile] && ![file writable $savefile]} {
	tk_dialog .err "エラー" "ファイルを出力することができません" info 0 OK
	return 1
    } elseif {![file writable [file dirname $savefile]]} {
	tk_dialog .err "エラー" "ファイルを出力することができません" \
		info 0 OK ; return 1
    }

    # Output Paper Size 
    set paperSize [lindex [split $paper { }] 0]

    # Make a file and Save
    if {$filetype == "TEXT"} {
	if {[make_file TEXT $filename $orient $paperSize $range $isNUP \
		$numNUP $isNUM $isREV] == 0} {
	    catch {exec $MV $TMPDIR/[file tail $filename] $savefile}
	}
    } elseif {$filetype == "DVI"} {
	if {[make_file DVI $filename $orient $paperSize $range $isNUP \
		$numNUP "" $isREV] == 0} {
	    catch {exec $MV $TMPDIR/[file tail $filename] $savefile}
	}
    } elseif {$filetype == "PS"} {
	set result_makePS notEXEC
	if {$isNUP == "YES" || $isREV == "YES" || \
		$range == "Specified" || $isPaperChanged == "YES"} {
	    if {[make_file PS $filename $orient $paperSize $range $isNUP \
		    $numNUP "" $isREV] == 0} {
		catch {exec $MV $TMPDIR/[file tail $filename] $savefile}
	    }
	}
    } elseif {$filetype == "Image"} {
	if {[make_file Image $filename $orient $paperSize $range $isNUP \
		$numNUP $isNUM $isREV ] == 0} {
	    catch {exec $MV $TMPDIR/[file tail $filename] $savefile}
	}
    } else {
	tk_dialog .err "失礼..." "このファイルは扱えません" \
		info 0 OK ; return 1
    }

    if {[file exists $savefile] && [file size $savefile] != 0} {
	tk_dialog .info "保存成功" "ファイルを保存しました" info 0 OK
	return 0
    }
}


# status -- Status of Printers for GP
#
# Argument     : None
# Return Value : None
#
proc status {w} {
    if {[winfo exist .status]} { return }
    toplevel .status -bd 5 -relief flat
    wm group .status $w ; wm title .status "プリンタの状況"

    global font kfont afcolor filetype filelist printers s_prn
    global QUEUE_COM REMOVE_COM isUserQueue isAutoQueueCheck 
    global interval_QueueCheck

    set isUserQueue NO

    # Widgets
    #
    # Frames
    frame .status.top ; frame .status.middle ; frame .status.bottom
    frame .status.buttons   -bd 2 -relief groove

    # Widgets for Status Comment
    label .status.p -text "プリンタ" -width 12 -bd 2 -kanjifont $kfont(2)
    label .status.s -text "印刷状況  印刷者  サイズ  ファイル" \
            -width 42 -bd 2 -justify left -anchor w -kanjifont $kfont(2)
    pack .status.p .status.s -side left -in .status.top

    # Widgets for Each Printer
    for {set i 0} {$printers($i) != "END"} {incr i} {
	set s_prn($i) [exec $QUEUE_COM -P$printers($i)]
	if {[string compare $s_prn($i) "no entries"] == 0} {
	    set s_prn($i) "\t\t$s_prn($i)"
	} else {
	    set s_prn($i) [refine $s_prn($i)]
	}
	frame .status.$printers($i) -bd 1
	label .status.$printers($i).printer -text $printers($i) \
		-font $font(3) -bd 2 -relief groove -width 10
	label .status.$printers($i).status -text "" -font $font(2) \
		-kanjifont $kfont(2) -anchor w -justify left -bd 2 \
		-relief groove -width 40
	pack .status.$printers($i).printer .status.$printers($i).status \
		-side left -in .status.$printers($i) -fill y -expand yes
	pack .status.$printers($i) -side top -in .status.middle
    }

    # checkbutton
    checkbutton .status.autocheck -text "自動キューチェック" \
	    -kanjifont $kfont(2) -variable isAutoQueueCheck -onvalue YES -bd 3\
	    -command {
	if {$isAutoQueueCheck == "YES"} {
	    .status.check conf -state disabled -fg gray50
	    AutoQueueCheck [expr $interval_QueueCheck * 1000]
	} else {
	    .status.check conf -state normal -fg black
	}
    }
    pack .status.autocheck -in .status.bottom

    # Buttons
    button .status.check -text "チェック" -kanjifont $kfont(2) -bd 3\
	    -activeforeground $afcolor -command {re_check .status}
    button .status.close -text "閉じる" -kanjifont $kfont(2) -bd 3\
	    -activeforeground red -command {
	if {[winfo exist .status]} { destroy .status }
	set AutoQueueCheck NO ;	return
    }
    button .status.remove -text "キューの削除" -kanjifont $kfont(2) -bd 3\
	    -activeforeground $afcolor -command { queue_removal .status }

    # If Auto Queue-Check, change the state of check button disabled.
    if {$isAutoQueueCheck == "YES"} {
	.status.check conf -state disabled -fg gray50
    }

    # Packing All Widgets
    pack .status.check .status.remove .status.close -side left \
	    -in .status.buttons -fill x -expand yes
    pack .status.top .status.middle .status.bottom .status.buttons -fill x \
	    -expand yes -anchor w -pady 1

    if {$isUserQueue == "NO"} {
	.status.remove conf -state disabled
    }
    re_check .status
}


# re_check -- Recheck Printer Status 
#
# Argument     : Status Window Top Path
# Return Value : None
#
proc re_check {w} {
    global printers QUEUE_COM s_prn isUserQueue

    if {![winfo exist $w]} { return }
    
    set isUserQueue NO
    for {set i 0} {$printers($i) != "END"} {incr i} {
	set s_prn($i) [exec $QUEUE_COM -P$printers($i)]
	if {[string compare $s_prn($i) "no entries"] == 0} {
	    set s_prn($i) "\t\tキューなし"
	} else {
	    set s_prn($i) [refine $s_prn($i)]
	}
	$w.$printers($i).status conf -text $s_prn($i)
    }

    # Whether Remove button is to be normal or disabled
    if {$isUserQueue == "YES"} {
	$w.remove conf -state normal
    } else {
	$w.remove conf -state disabled
    }
}


# refine -- Refine Printer Status
#
# Argument     : Printer Status
# Return Value : Refined Printer Status
#
proc refine {p_status} {
    global isUserQueue USER

    set Status ""
    set offset 0 ;# for comment with "Priority" Information

    # Eliminate Needless Keywords
    foreach status_line  [split $p_status \n] {
	if {[lindex $status_line end] != "bytes"} { continue }

	set State [lindex $status_line 0] ; set Length [llength $status_line]
	if {[scan [lindex $status_line 1] %d tmp] == 1} {
	    set Owner [lindex $status_line 2] ; set offset 1
	} else {
	    set Owner [lindex $status_line 1]
	}
	if {$Owner == $USER} { set isUserQueue "YES" }
	if {[string length $Owner] > 8} {
	    set Owner [string range $Owner 0 7]
	}

	set File [file tail [lrange $status_line [expr 3+$offset]\
		[expr $Length - 3]]]
	if {[string trim $File "()"] == "standard input"} {
	    set File "標準入力"
	} else {
	    if {[llength $File] > 1} {
		set File "[string range [lindex $File 0] 0 12] etc."
	    } elseif {[string length $File] > 15} {
		set File "[string range $File 0 12]..."
	    }
	}
	set Size [FileSize [lindex $status_line [expr $Length - 2]]]
	set tmpStatus [format "%-7s \t%-9s %-5s \t%-15s\t" \
		$State $Owner $Size $File]
	set Status [concat $Status\n$tmpStatus]
    }

    # Return Refined Status
    return $Status
}


# FileSize -- Return File Size with Unit(k or M)
#
# Argument     : File Size (bytes)
# Retrun Value : File Size (kbytes or Mbytes)
#
proc FileSize {size} {
    if {$size > 999} {
	set size [expr int(double($size)/1024)]
	if {$size > 999} {
	    set size "[expr int(double($size)/1024)]M"
	} else {set size "[expr $size]k"}
    }
    return $size
}


# AutoQueueCheck -- Auto Print-Queue Check Routine
#
# Argument     : Sleep Time
# Retrun Value : None
#
proc AutoQueueCheck {time} {
    global isAutoQueueCheck

    # Check AutoQueueu Check Variable
    if {$isAutoQueueCheck != "YES"} { return }

    # Recheck Print Queues and ...
    re_check .status ; after $time AutoQueueCheck $time
}


# queue_removal -- Remove Print Queue
#
# Argument     : Status Window Path 
# Return Value : None
#
proc queue_removal {w} {
    if {[winfo exist .remove]} { return }
    toplevel .remove -bd 5 -relief flat
    wm group .remove $w ; grab set .remove
    wm title .remove "印刷キューの削除"

    global font kfont afcolor filetype filelist printers s_prn
    global QUEUE_COM REMOVE_COM USER

    # Check Print Que
    for {set i 0} {$printers($i) != "END"} {incr i} {
	set s_prn($i) [exec $QUEUE_COM -P$printers($i)]	
    }

    set j 0
    # Check Que for Removal Buttons
    for {set i 0} {$printers($i) != "END"} {incr i} {
	foreach list [split $s_prn($i) \n] {
	    if {[lindex $list end] != "bytes"} { continue }

	    set State [lindex $list 0] ; set Length [llength $list]
	    if {[scan [lindex $list 1] %d tmp] == 1} {
		set Owner [lindex $list 2] ; set offset 1
	    } else {
		set Owner [lindex $list 1] ; set offset 0
	    }
	    if {$Owner != $USER} { continue }
	    set Job   [lindex $list [expr 2+$offset]]
	    set File  [file tail [lrange $list [expr 3+$offset] \
		    [expr $Length-3]]]

	    if {[string trim $File "()"] == "standard input"} {
		set File "標準入力"
	    } else {
		if {[llength $File] > 1} {
		    set File "[string range [lindex $File 0] 0 12] etc."
		} elseif {[string length $File] > 15} {
		    set File "[string range $File 0 12]..."
		}
	    }
	    set Size  [FileSize [lindex $list [expr $Length-2]]]

	    set states [concat $i $Job $Owner \t$State]
	    set status($j) [concat $states\t$Size\t$File]
	    incr j ; set status($j) ""
	}
    }
    set isQUE "NO"

    #
    # Widgets for Queue Removing Buttons etc...
    #
    frame .remove.top ; frame .remove.body
    label .remove.label -text "プリンタ" -kanjifont $kfont(2) -width 12
    label .remove.label2 -text "印刷状況  サイズ  ファイル" \
	    -kanjifont $kfont(2) -justify left -anchor w -width 40
    pack .remove.label .remove.label2 -side left -in .remove.top \
	    -anchor w -fill x
    pack .remove.top -side top
    for {set i 0} {$printers($i) != "END"} {incr i} {
	frame .remove.body.$i -bd 2 -relief groove
	frame .remove.body.$i.left
	label .remove.prn_name$i -font $font(3) -anchor c \
		-text "$printers($i)" -width 10

	set isQUE_PRN "NO"
	# Loop by the Number of Status
	for {set j 0} {[info exists status($j)]} {incr j} {
	    set prn_Num [lindex $status($j) 0]
	    if {$prn_Num != $i || $status($j) == ""} { continue }

	    set queue_Num [lindex $status($j) 1]
	    set Status2($j) [lrange $status($j) 3 end]

	    button .remove.body.$i.left.cb$j -font $font(2) \
		    -kanjifont $kfont(2) -text $Status2($j) -anchor w \
		    -activeforeground red -bd 3 -relief raise -width 30 \
		    -command "exec $REMOVE_COM \
		    -P$printers($prn_Num) $queue_Num 2> /dev/null ; \
		    destroy .remove.body.$i.left.cb$j ; \
		    destroy_frame .remove $i" 

	    pack .remove.body.$i.left.cb$j -in .remove.body.$i.left \
		    -side top -fill x
	    set isQUE "YES" ; set isQUE_PRN "YES"
	}
	if {$isQUE_PRN == "YES"} {
	    pack .remove.prn_name$i .remove.body.$i.left -side left \
		    -in .remove.body.$i -fill y -expand yes
	    pack .remove.body.$i -in .remove.body -side top -fill x \
		    -expand yes 
	}
	if {[winfo children .remove.body.$i.left] == ""} { 
	    destroy .remove.body.$i
	}
    }
    pack .remove.body -side top

    #
    # Case of no printing queue
    #
    if {$isQUE == "NO"} {
	set result [tk_dialog .err "キューなし" "あなたのキューはありません" \
		info 0 了解]
	if {[winfo exist .remove]} { destroy .remove }
	grab release .remove ; return
    }
    button .remove.close -text "閉じる" -kanjifont $kfont(2) -width 8 -bd 2 \
	    -activeforeground red -command { \
	    if {[winfo exist .remove]} { destroy .remove }; \
	    grab release .remove ; re_check .status }
    pack .remove.close -side right
}


# destroy_frame -- Destroy Frames on Removal Buttons
#
# Argument     : Path of the Frame on which buttons are and Number
# Return Value : None
#
proc destroy_frame {w num} {
    if {[winfo children $w.body.$num.left] == ""} { destroy $w.body.$num }
    if {[winfo children $w.body] == ""} {
	grab release $w ; destroy $w ; re_check .status
    }
}


# complete -- Complete file name
#
# Argument     : Incomplete File Name/Directory Name
# Return Value : Complete Name or Incomplete Name
# 
proc complete {incomp_name} {
    # Check whthter there is any candidacy or not
    if {[catch {set candidacy [glob $incomp_name*]}] != 0} {
	set candidacy "setting error"
    }

    # If there is only one candidacy, return its name, or
    # return argument itself with bell
    if {[llength $candidacy] == 1} {
	return $candidacy
    } else {
	bell ; return $incomp_name
    }
}


# put_history -- Set one of history filenames to printfile
#
# Argument     : History Search Direction (pre/next)
# Return Value : None
#
proc put_history {direc} {
    global history history_num history_max printfile

    # Plus one or minus one according to direc
    if {$direc == "pre"} {
	set history_num [incr history_num -1]
    } else {
	set history_num [incr history_num  1]
    }

    # If history_num is less than 1 or more then history_max, history loop
    # will be stopped and bell rings. And if the history file doesn't exist,
    # recall this procedure
    if {$history_num < 1 } {
	set history_num 0 ; set printfile "" ; bell
    } elseif {$history_num > $history_max} {
	set history_num [expr $history_max + 1] ; set printfile "" ; bell
    } elseif {![file isfile $history($history_num)]} {
	put_history $direc
    } else {
	set printfile $history($history_num)
	cd [file dirname $history($history_num)]
    }
}


# save_history -- Save history filenames to ~/.GP/history
#
# Argument     : None
# Return Value : None
#
proc save_history {} {
    global history history_max env

    set out_fd [open $env(HOME)/.GP/history w]
    # Record the filename if the file exists. 
    for {set i 1} {$i < [expr $history_max+1]} {incr i} {
	if {[file exists $history($i)] && $history($i) != ""} {
	    puts $out_fd $history($i)
	}
    }
    close $out_fd
}


# record_history -- Save history filenames to history stack
#
# Argument     : Printed Filename 
# Return Value : None
#
proc record_history {printed_file} {
    global history history_Max history_max history_num

    # Record the printed file if the file still exists. 
    if {[file exists $printed_file]} {
	set j 1
	for {set i 1} {$i <= $history_Max} {incr i} {
	    set tmp_history($i) ""
	    if {[file exists $history($i)] && $history($i) != ""} {
		set tmp_history($j) $history($i) ; incr j
	    }
	}

	set tmp_history($j) $printed_file
	if {$j != [expr $history_Max + 1]} {
	    set start_j 1 ; set end_j $history_Max ; set history_max $j
	} else {
	    set start_j 2 ; set end_j [expr $history_Max + 1]
	    set history_max $history_Max
	}
	set history_num [expr $history_max + 1]

	set i 1
	for {set j $start_j} {$j <= $end_j} {incr j} {
	    set history($i) $tmp_history($j) ; incr i
	}
    }
}


# check_filetype -- Check file type, then set default printer and file type
#
# Argument     : filename and entry widget path for filename
# Return Value : none
#
proc check_filetype {filename w} {
    global filetype defaultprn Printer FileType printers printfile ext
    
    if {$filename ==""} { return }

    set ext [string tolower [file extension $filename]]
    if {[info exists filetype($ext)] == 0 || $filetype($ext) == "TEXT"} {
	set FileType "TEXT" ; set Printer  $defaultprn(TEXT)
    } else {
	set FileType $filetype($ext)
	set Printer  $defaultprn($filetype($ext))
    }

    if {$Printer == "UNUSE"} {
	set printfile "" ; set Printer $printers(0)
        set tmp [tk_dialog .err "印刷不可" "このファイルは印刷できません\n\
                (管理者に相談して下さい)" info 0 了解] ; return 1
    }

    change_printOption $w $FileType
    $w.filetype conf -text $FileType ; $w.printer  conf -text $Printer

    return 0
}


