diff options
author | Andrej Shadura <andrewsh@debian.org> | 2018-05-08 15:59:31 +0200 |
---|---|---|
committer | Andrej Shadura <andrewsh@debian.org> | 2018-05-08 15:59:31 +0200 |
commit | 47aa8b00b2b11df13a100489e0f904a4947177ef (patch) | |
tree | b35c9acc778ea2f761f3c549f7bee2f4491b3144 /lib/utilities/baseconverter.tcl | |
parent | 5b8466f7fae0e071c0f4eda13051c93313910028 (diff) |
Import Upstream version 1.4.7
Diffstat (limited to 'lib/utilities/baseconverter.tcl')
-rw-r--r-- | lib/utilities/baseconverter.tcl | 952 |
1 files changed, 952 insertions, 0 deletions
diff --git a/lib/utilities/baseconverter.tcl b/lib/utilities/baseconverter.tcl new file mode 100644 index 0000000..82d656a --- /dev/null +++ b/lib/utilities/baseconverter.tcl @@ -0,0 +1,952 @@ +#!/usr/bin/tclsh +# Part of MCU 8051 IDE ( http://mcu8051ide.sf.net ) + +############################################################################ +# Copyright (C) 2007, 2008, 2009, 2010, 2011, 2012 by Martin Ošmera # +# martin.osmera@gmail.com # +# # +# This program is free software; you can redistribute it and#or modify # +# it under the terms of the GNU General Public License as published by # +# the Free Software Foundation; either version 2 of the License, or # +# (at your option) any later version. # +# # +# This program is distributed in the hope that it will be useful, # +# but WITHOUT ANY WARRANTY; without even the implied warranty of # +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # +# GNU General Public License for more details. # +# # +# You should have received a copy of the GNU General Public License # +# along with this program; if not, write to the # +# Free Software Foundation, Inc., # +# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. # +############################################################################ + +# >>> File inclusion guard +if { ! [ info exists _BASECONVERTER_TCL ] } { +set _BASECONVERTER_TCL _ +# <<< File inclusion guard + + +# -------------------------------------------------------------------------- +# DESCRIPTION +# Utility "Base Converter" +# -------------------------------------------------------------------------- + +class BaseConverter { + ## COMMON + common base_c_count 0 ;# Int: Counter of class instances + common INITIAL_HEIGHT 130 ;# Int: Initial heightof the window in pixels + common INITIAL_WIDTH 150 ;# Int: Initial width of the window in pixels + common EXTENDED_WIDTH 340 ;# Int: Width of the window when it is in extended mode + + # On MS Windows these values has to be a bit different + if {$::MICROSOFT_WINDOWS} { + set INITIAL_HEIGHT 125 + set INITIAL_WIDTH 165 + set EXTENDED_WIDTH 355 + } + # Font entryboxes + common entry_font [font create \ + -size -12 \ + -family $::DEFAULT_FIXED_FONT \ + -weight bold \ + ] + + ## PRIVATE + private variable win ;# Widget: Window + private variable win_obj ;# Object: Window object + + private variable less_more_button ;# Widget: Button "Less/More" + private variable enlarge_shrink_button ;# Widget: Button "Enlarge/Shrink" + + private variable right_top_frame ;# Widget: Right top frame + private variable left_top_frame ;# Widget: Left top frame + + private variable less_more 0 ;# Bool: Mode flag "More" + private variable large 0 ;# Bool: Flag enlarged + + private variable left_rows_created 0 ;# Int: Number of created rows in the left frame + private variable right_rows_created 0 ;# Int: Number of created rows in the right frame + + private variable validation_in_progress 0 ;# Bool: Validation procedure in progress + + private variable val_to_set [list {} {} {}] ;# List: Decimal values to set in the bottom 3 entryboxes after enlarge + + private variable entry_h ;# Array of Widget: Entrybox "HEX", index is row (starting from 0) + private variable entry_d ;# Array of Widget: Entrybox "DEC", index is row (starting from 0) + private variable entry_b ;# Array of Widget: Entrybox "BIN", index is row (starting from 0) + private variable entry_o ;# Array of Widget: Entrybox "OCT", index is row (starting from 0) + private variable entry_t ;# Array of Widget: Canvas containing bits + private variable entry_c0 ;# Array of Widget: Entrybox "BCD L", index is row (starting from 0) + private variable entry_c1 ;# Array of Widget: Entrybox "BCD H", index is row (starting from 0) + private variable entry_a ;# Array of Widget: Entrybox "ASCII", index is row (starting from 0) + private variable bit ;# CanvasObject: bit rectangle, $bit(row_number,bit_number) + + ## Object constructor + constructor {} { + # Configure ttk styles + if {!$base_c_count} { + ttk::style configure BaseConverter_Focused_D.TEntry -fieldbackground {#AAAAFF} + ttk::style configure BaseConverter_Focused_I.TEntry -fieldbackground {#DDDDFF} + ttk::style configure BaseConverter_NotFocused.TEntry + } + + incr base_c_count + + create_window + create_gui + } + + ## Object destructor + destructor { + } + + ## Commence a new configuration + # @parm List conf_list - Configuration list previously returned by proc. "get_config" + # @return void + public method set_config {conf_list} { + # Set window position + $win_obj geometry \ + {} {} \ + [lindex $conf_list {0 2}] \ + [lindex $conf_list {0 3}] + + # Adjust modes + if {[lindex $conf_list 2]} { + less_more + } + if {[lindex $conf_list 3]} { + enlarge_shrink + } + + # Fill in the entryboxes + for {set i 0} {$i < $left_rows_created} {incr i} { + validate {t} $i [lindex $conf_list [list 4 $i]] + } + if {$left_rows_created < 6} { + for {set i 0; set j 3} {$i < 3} {incr i; incr j} { + lset val_to_set $i [lindex $conf_list [list 4 $j]] + } + } + + # Adjust flag "Shaded" + if {[lindex $conf_list 1]} { + update + $win_obj collapse_expand + } + } + + ## Get configuration list + # @return List - Configuration list + public method get_config {} { + # Create list of current values in the entryboxes + set values {} + lappend values [$entry_d(0) get] [$entry_d(1) get] [$entry_d(2) get] + if {$left_rows_created > 3} { + lappend values \ + [$entry_d(3) get] \ + [$entry_d(4) get] \ + [$entry_d(5) get] + } else { + lappend values {} {} {} + } + + # Finalize configuration list + return [list \ + [$win_obj geometry] \ + [$win_obj get_minim_flag] \ + $less_more \ + $large \ + $values \ + ] + } + + ## Create window using class "InnerWindow" + # @return void + private method create_window {} { + set win_obj [InnerWindow #auto \ + .baseconverter_${base_c_count} \ + [list $INITIAL_WIDTH $INITIAL_HEIGHT 100 100] \ + [mc "Converter"] \ + ::ICONS::16::kaboodleloop \ + "$this close_window" \ + ] + set win [$win_obj get_frame] + } + + ## Create all window GUI + # @return void + private method create_gui {} { + # Create frames + set top_frame [frame $win.top_frame] + set left_top_frame [frame $top_frame.left_frame] + set right_top_frame [frame $top_frame.right_frame] + set bottom_frame [frame $win.bottom_frame] + + # Start in mode "Shirked" + !"More" + create_left_frame + + ## Create buttons in the bottom frame + # Button "Enlarge"/"Shrink" + set enlarge_shrink_button \ + [ttk::button $bottom_frame.enlarge_shrink_button \ + -text [mc "Enlarge"] \ + -compound left \ + -image ::ICONS::16::1downarrow \ + -command "$this enlarge_shrink" \ + -width 7 \ + -style Flat.TButton \ + ] + pack $enlarge_shrink_button -side left -padx 2 -pady 2 + # Button "More"/"Less" + set less_more_button [ttk::button $bottom_frame.less_more_button\ + -text [mc "More"] \ + -compound right \ + -image ::ICONS::16::1rightarrow \ + -command "$this less_more" \ + -width 5 \ + -style Flat.TButton \ + ] + pack $less_more_button -side right -padx 2 -pady 2 + + # Pack frames + pack $left_top_frame -side left -anchor nw + pack $top_frame -fill both -expand 1 + pack $bottom_frame -fill x + + # Focus the firts hexadecimal entrybox + focus -force $entry_h(0) + } + + ## Close the window and forget configuration + # Calls proc. "::X::__base_converter_close" + # @return void + public method close_window {} { + ::X::__base_converter_close $this + $win_obj close_window + delete object $this + } + + ## Validator for entryboxes + # Can be used to set a certain value for a certain row in this way: + # validate {t} $row_number $decimal_value + # @parm Char type - Value source + # h - Hexadecimal + # d - Decimal + # b - Binary + # o - Octal + # c0 - BCD - Low order nibble + # c1 - BCD - High order nibble + # a - ASCII + # t - Bits (Do not validate, just accept) + # @parm Int row - Row number, starting at zero + # @parm String content - String to validate and evaluate + # @return Bool - 1 == Legal; 0 == Illegal + public method validate {type row content} { + # This method cannot be recursive in any way + if {$validation_in_progress} {return 1} + set validation_in_progress 1 + + # Local variables + set result 1 ;# Bool: Result of validation + set zero_length 0 ;# Bool: Zero length input string + set value {} ;# Mixed: Decimal representation the validate value or {} (no value) + + # Detect zero length input string + if {[string length $content]} { + set zero_length 0 + } else { + set zero_length 1 + set content 0 + } + + # Validate input string + switch -- $type { + {h} { ;# Hexadecimal + if {![regexp {^[[:xdigit:]]{0,2}$} $content]} { + set result 0 + } else { + scan $content "%x" value + } + } + {d} { ;# Decimal + if {![regexp {^[[:digit:]]{0,3}$} $content]} { + set result 0 + } elseif {$content > 255} { + set result 0 + } else { + set value $content + } + } + {b} { ;# Binary + if {![regexp {^[01]{0,8}$} $content]} { + set result 0 + } else { + set value [NumSystem::bin2dec $content] + } + } + {o} { ;# Octal + if {![regexp {^[0-7]{0,3}$} $content]} { + set result 0 + } elseif {$content > 377} { + set result 0 + } else { + scan $content "%o" value + } + } + {c0} { ;# BCD - Low order nibble + if {![regexp {^[[:digit:]]{0,2}$} $content]} { + set result 0 + } elseif {$content > 15} { + set result 0 + } else { + set value [$entry_c1($row) get] + if {![string length $value]} { + set value 0 + } + set value [expr {$content + ($value << 4)}] + } + set zero_length 0 + } + {c1} { ;# BCD - High order nibble + if {![regexp {^[[:digit:]]{0,2}$} $content]} { + set result 0 + } elseif {$content > 15} { + set result 0 + } else { + set value [$entry_c0($row) get] + if {![string length $value]} { + set value 0 + } + set value [expr {$value + ($content << 4)}] + } + set zero_length 0 + } + {a} { ;# ASCII + if {$zero_length} { + set content {} + } + set zero_length 0 + + if {[string length $content] > 1} { + set result 0 + } else { + set value [NumSystem::ascii2dec $content] + } + + if {![string length $value]} { + set value [$entry_d($row) get] + if {![string length $value]} { + set zero_length 1 + } + } + } + {t} { ;# Bits (Do not validate, just accept) + set value $content + } + } + + # Synchronize with the other entryboxes on the row + if {$result} { + fill_entryboxes $row $value $zero_length $type + } + + # Finish ... + set validation_in_progress 0 + return $result + } + + ## Synchronize the specified value with the other entryboxes on the row + # @parm Int row - Row number + # @parm Int value - Value to fill in (in decimal) + # @parm Bool zero_length - Just clear all entryboxes + # @parm Char exclude - Entrybox to exclude during filling + # h - Hexadecimal + # d - Decimal + # b - Binary + # o - Octal + # c0 - BCD - Low order nibble + # c1 - BCD - High order nibble + # a - ASCII + # t - No meaning ... + # @return void + private method fill_entryboxes {row value zero_length exclude} { + # Clear entryboxes on the left + foreach w [list \ + $entry_h($row) $entry_d($row) \ + $entry_b($row) $entry_o($row) \ + ] t { + h d + b o + } \ + { + if {$exclude == $t} { + continue + } + $w delete 0 end + } + + # Fill in entryboxes on the left + if {!$zero_length} { + if {$exclude != {h}} { + $entry_h($row) insert 0 [format {%X} $value] + } + if {$exclude != {d}} { + $entry_d($row) insert 0 $value + } + if {$exclude != {b}} { + $entry_b($row) insert 0 [NumSystem::dec2bin $value] + } + if {$exclude != {o}} { + $entry_o($row) insert 0 [format {%o} $value] + } + } + + if {$row < $right_rows_created} { + # Clear entryboxes on the right + foreach w [list $entry_c0($row) $entry_c1($row) $entry_a($row)] \ + t {c0 c1 a} \ + { + if {$exclude == $t} { + continue + } + + $w delete 0 end + } + + # Adjust canvas widget with bit rectangles + set mask 1 + for {set i 0} {$i < 8} {incr i} { + if {$zero_length} { + set fill {#FFFFFF} + set outline {#888888} + } elseif {[expr $value & $mask]} { + set fill ${::BitMap::one_fill} + set outline ${::BitMap::one_outline} + } else { + set fill ${::BitMap::zero_fill} + set outline ${::BitMap::zero_outline} + } + + $entry_t($row) itemconfigure $bit($row,$i) \ + -fill $fill -outline $outline + + set mask [expr {$mask << 1}] + } + + # Fill in entryboxes on the right + if {!$zero_length} { + if {$exclude != {c0}} { + $entry_c0($row) insert 0 [expr {$value & 0x0F}] + } + if {$exclude != {c1}} { + $entry_c1($row) insert 0 [expr {$value >> 4}] + } + if {$exclude != {a}} { + if {$value > 31 && $value < 127} { + $entry_a($row) insert 0 [format {%c} $value] + } + } + } + } + } + + ## Handles event <Enter> on canvas widget with bits, + # @parm Int r - Row number (0..5) + # @parm Int b - Bit number (0..7) + # @return void + public method bit_enter {r b} { + # Determinate current rectangle fill and outline + set fill [$entry_t($r) itemcget $bit($r,$b) -fill] + set outline [$entry_t($r) itemcget $bit($r,$b) -outline] + + # Determinate new rectangle fill and outline + if {$fill == ${::BitMap::one_fill}} { + set fill ${::BitMap::one_a_fill} + set outline ${::BitMap::one_a_outline} + } elseif {$fill == ${::BitMap::zero_fill}} { + set fill ${::BitMap::zero_a_fill} + set outline ${::BitMap::zero_a_outline} + } + + # Set new rectangle fill and outline and adjust cursor + $entry_t($r) itemconfigure $bit($r,$b) \ + -fill $fill -outline $outline + $entry_t($r) configure -cursor hand2 + } + + ## Handles event <leave> on canvas widget with bits, + # @parm Int r - Row number (0..5) + # @parm Int b - Bit number (0..7) + # @return void + public method bit_leave {r b} { + # Determinate current rectangle fill and outline + set fill [$entry_t($r) itemcget $bit($r,$b) -fill] + set outline [$entry_t($r) itemcget $bit($r,$b) -outline] + + # Determinate new rectangle fill and outline + if {$fill == ${::BitMap::one_a_fill}} { + set fill ${::BitMap::one_fill} + set outline ${::BitMap::one_outline} + } elseif {$fill == ${::BitMap::zero_a_fill}} { + set fill ${::BitMap::zero_fill} + set outline ${::BitMap::zero_outline} + } + + # Set new rectangle fill and outline and adjust cursor + $entry_t($r) itemconfigure $bit($r,$b) \ + -fill $fill -outline $outline + $entry_t($r) configure -cursor left_ptr + } + + ## Handles event <Button-1> on canvas widget with bits, + # @parm Int r - Row number (0..5) + # @parm Int b - Bit number (0..7) + # @return void + public method bit_click {r b} { + # Determinate current rectangle fill + set fill [$entry_t($r) itemcget $bit($r,$b) -fill] + + # Determinate new bit value + if { + $fill == ${::BitMap::one_a_fill} + || + $fill == ${::BitMap::one_fill} + } then { + set value 0 + } else { + set value [expr {1 << $b}] + } + + # Determinate new value for the whole row + set dec [$entry_d($r) get] + if {![string length $dec]} { + set dec 0 + } + set dec [expr {$dec & (0x0FF ^ (1 << $b))}] + incr dec $value + + # Set new value for the whole row + validate {t} $r $dec + } + + ## Set envent binds specific to this appliaction for the specified entrybox + # @parm Widget w - Entrybox widget + # @parm Char t - Entrybox type + # h - Hexadecimal + # d - Decimal + # b - Binary + # o - Octal + # c0 - BCD - Low order nibble + # c1 - BCD - High order nibble + # a - ASCII + # @parm Int r - Row number (0..5) + # @return void + private method set_bindings_for_an_entrybox {w t r} { + bind $w <Key-Up> "$this entry_key $t $r u; break" + bind $w <Key-Down> "$this entry_key $t $r d; break" + bind $w <Key-Left> "$this entry_key $t $r l; break" + bind $w <Key-Right> "$this entry_key $t $r r; break" + bind $w <Key-Tab> "$this entry_key $t $r t; break" + if {!$::MICROSOFT_WINDOWS} { + bind $w <Key-ISO_Left_Tab> "$this entry_key $t $r s; break" + } + bind $w <Key-Return> "$this entry_key $t $r e; break" + bind $w <Key-KP_Enter> "$this entry_key $t $r e; break" + + bind $w <FocusIn> "$this entry_focus $t $r 1" + bind $w <FocusOut> "$this entry_focus $t $r 0" + } + + ## Create the left frame of the window + # @return void + private method create_left_frame {} { + # Create labels + if {!$left_rows_created} { + set col 1 + foreach text { + {HEX} {DEC} {BIN} {OCT} + } { + grid [label $left_top_frame.header_lbl_${col} \ + -font $::smallfont -text [mc $text] -pady 0 \ + ] -pady 0 -ipady 0 -row 1 -column $col + incr col + } + } + + # Create entryboxes + set row 0 + for {set row $left_rows_created} {$row < ($large ? 6 : 3)} {incr row} { + set col 1 + foreach width { + 2 3 8 3 + } type { + h d b o + } \ + { + set entry_wgd [ttk::entry $left_top_frame.e_${type}_$row \ + -width $width \ + -validate key \ + -validatecommand "$this validate $type $row %P" \ + -style BaseConverter_NotFocused.TEntry \ + -font $entry_font \ + ] + set entry_${type}($row) $entry_wgd + grid $entry_wgd -row [expr {$row + 2}] -column $col + + set_bindings_for_an_entrybox $entry_wgd $type $row + + incr col + } + } + set left_rows_created $row + + if {$large} { + for {set i 0; set j 3} {$i < 3} {incr i; incr j} { + validate {t} $j [lindex $val_to_set $i] + } + } + } + + ## Create the left frame of the window + # @return void + private method create_right_frame {} { + # Create labels + if {!$right_rows_created} { + set col 1 + grid [label $right_top_frame.header_lbl_${col} \ + -font $::smallfont -text [mc "Bits"] -pady 0 \ + ] -pady 0 -ipady 0 -row 1 -column $col + incr col + grid [label $right_top_frame.header_lbl_${col} \ + -font $::smallfont -text [mc "BCD"] -pady 0 \ + ] -pady 0 -ipady 0 -row 1 -column $col -columnspan 2 + incr col 2 + grid [label $right_top_frame.header_lbl_${col} \ + -font $::smallfont -text [mc "ASCII"] -pady 0\ + ] -pady 0 -ipady 0 -row 1 -column $col + incr col + } + + # Create entryboxes and canvas widget + set row 0 + for {set row $right_rows_created} {$row < ($large ? 6 : 3)} {incr row} { + set col 1 + foreach type { + t c a + } \ + { + switch -- $type { + {a} { ;# ASCII + set entry_wgd [ttk::entry $right_top_frame.e_${type}_$row \ + -width 2 \ + -validate all \ + -validatecommand "$this validate ${type} $row %P" \ + -style BaseConverter_NotFocused.TEntry \ + -font $entry_font \ + ] + set entry_${type}($row) $entry_wgd + grid $entry_wgd -row [expr {$row + 2}] -column $col + set_bindings_for_an_entrybox $entry_wgd $type $row + } + {c} { ;# BCD + set entry_wgd [ttk::entry $right_top_frame.e_${type}1_$row \ + -width 2 \ + -validate all \ + -validatecommand "$this validate ${type}1 $row %P" \ + -style BaseConverter_NotFocused.TEntry \ + -font $entry_font \ + ] + set entry_${type}1($row) $entry_wgd + grid $entry_wgd -row [expr {$row + 2}] -column $col + set_bindings_for_an_entrybox $entry_wgd "${type}1" $row + + incr col + + set entry_wgd [ttk::entry $right_top_frame.e_${type}0_$row \ + -width 2 \ + -validate all \ + -validatecommand "$this validate ${type}0 $row %P" \ + -style BaseConverter_NotFocused.TEntry \ + -font $entry_font \ + ] + set entry_${type}0($row) $entry_wgd + grid $entry_wgd -row [expr {$row + 2}] -column $col + set_bindings_for_an_entrybox $entry_wgd "${type}0" $row + } + {t} { ;# Bits + set x0 2 + + set y0 0 + set y1 2 + + + set canvas [canvas $right_top_frame.canvas_${row} \ + -width 118 -height 18 -bd 0 -bg white \ + -relief flat -highlightthickness 0 \ + ] + grid $canvas -row [expr {$row + 2}] -column $col + set entry_${type}($row) $canvas + + for {set b 7} {$b >= 0} {incr b -1} { + + # Create bit rectagle + set bit($row,$b) [$canvas create \ + rectangle $x0 $y1 \ + [expr {$x0 + 12}] \ + [expr {$y1 + 12}] \ + -fill {#FFFFFF} \ + -outline {#888888} \ + ] + + $canvas bind $bit($row,$b) <Enter> "$this bit_enter $row $b" + $canvas bind $bit($row,$b) <Leave> "$this bit_leave $row $b" + $canvas bind $bit($row,$b) <Button-1> "$this bit_click $row $b" + + # Adjust X position for the next rectagle + incr x0 14 + if {$b == 4} { + incr x0 3 + } + } + } + } + + incr col + } + } + set right_rows_created $row + } + + ## Switch between modes "Enlarged" and "Shrinked" + # @return void + public method enlarge_shrink {} { + # Invert the mode flag + set large [expr {!$large}] + + # Adjust buttons on the bottom bar and create the missing widgets if nessesary + if {$large} { + create_right_frame + create_left_frame + $win_obj geometry {} [expr {[winfo height $entry_h(0)] * 3 + $INITIAL_HEIGHT}] {} {} + $enlarge_shrink_button configure \ + -image ::ICONS::16::1uparrow \ + -text [mc "Shrink"] + } else { + $win_obj geometry {} $INITIAL_HEIGHT {} {} + $enlarge_shrink_button configure \ + -image ::ICONS::16::1downarrow \ + -text [mc "Enlarge"] + + for {set i 0; set j 3} {$i < 3} {incr i; incr j} { + lset val_to_set $i [$entry_d($j) get] + } + } + + # Show or hide appropriate GUI elements + foreach w [list \ + entry_h entry_d entry_b \ + entry_o entry_t entry_c1\ + entry_c0 entry_a \ + ] c { + 1 2 3 + 4 1 2 + 3 4 + } { + for {set i 3; set r 5} {$i < 6} {incr i; incr r} { + if {$large} { + grid [subst -nocommands "\$${w}($i)"] -column $c -row $r + } else { + grid forget [subst -nocommands "\$${w}($i)"] + } + } + } + + } + + ## Switch between modes "More" and "Less" + # @return void + public method less_more {} { + # Invert the mode flag + set less_more [expr {!$less_more}] + + # Adjust GUI + if {$less_more} { + create_right_frame + pack $right_top_frame -side left -anchor nw + $less_more_button configure \ + -compound left -text [mc "Less"] \ + -image ::ICONS::16::1leftarrow + $win_obj geometry $EXTENDED_WIDTH {} {} {} + + for {set i 0} {$i < $right_rows_created} {incr i} { + validate {t} $i [$entry_d($i) get] + } + } else { + pack forget $right_top_frame + $less_more_button configure \ + -compound right -text [mc "More"] \ + -image ::ICONS::16::1rightarrow + $win_obj geometry $INITIAL_WIDTH {} {} {} + } + } + + ## Entybox event handler for <FocusIn> and <FocusOut> + # Change entryboxes background colors + # @parm Char type - Entrybox type + # h - Hexadecimal + # d - Decimal + # b - Binary + # o - Octal + # c0 - BCD - Low order nibble + # c1 - BCD - High order nibble + # a - ASCII + # @parm Int row - Row number (0..5) + # @parm Bool focused - 1 == <FocusIn>; 0 == <FocusOut> + # @return void + public method entry_focus {type row focused} { + if {$focused} { + set style BaseConverter_Focused_I.TEntry + set bg {#DDDDFF} + } else { + set style BaseConverter_NotFocused.TEntry + set bg {#FFFFFF} + } + + foreach w [list \ + $entry_h($row) $entry_d($row) \ + $entry_b($row) $entry_o($row) \ + ] \ + { + $w configure -style $style + } + + if {$right_rows_created > $row} { + foreach w [list \ + $entry_c1($row) \ + $entry_c0($row) \ + $entry_a($row) \ + ] \ + { + $w configure -style $style + } + + $entry_t($row) configure -bg $bg + } + + if {$focused} { + [subst -nocommands "\$entry_${type}($row)"] configure -style BaseConverter_Focused_D.TEntry + } else { + [subst -nocommands "\$entry_${type}($row)"] selection clear + } + + } + + + ## Entybox event handler for <Key-Up>, <Key-Down>, <Key-Left>, <Key-Right>, <Key-Tab>, + #+ <Key-ISO_Left_Tab>, <Key-Return> and <Key-KP_Enter> + # @parm Char type - Entrybox type + # h - Hexadecimal + # d - Decimal + # b - Binary + # o - Octal + # c0 - BCD - Low order nibble + # c1 - BCD - High order nibble + # a - ASCII + # @parm Int y - Row number (0..5) + # @parm Char key - Key pressed + # u - Up + # d - Down + # l - Left + # r - Right + # t - Tab + # s - Shift-Tab + # e - Enter + # @return void + public method entry_key {type y key} { + set entrybox [subst -nocommands "\$entry_${type}($y)"] + set insert [$entrybox index insert] + set max_y $left_rows_created + incr max_y -1 + switch -- $type { + {h} {set x 0} + {d} {set x 1} + {b} {set x 2} + {o} {set x 3} + {c1} {set x 4} + {c0} {set x 5} + {a} {set x 6} + } + + $entrybox selection clear + switch -- $key { + {u} { ;# Up + if {!$y} { + return + } + incr y -1 + } + {d} { ;# Down + if {$y == $max_y} { + return + } + incr y + } + {l} { ;# Left + if {!$x || $insert} { + $entrybox icursor [expr {$insert-1}] + return + } + incr x -1 + } + {r} { ;# Right + if {($x == 6) || ($insert != [$entrybox index end])} { + $entrybox icursor [expr {$insert+1}] + return + } + incr x + } + {t} { ;# Tab + if {$x == 6} { + return + } + incr x + } + {s} { ;# Shift-Tab + if {!$x} { + return + } + incr x -1 + } + {e} { ;# Enter + if {$y == $max_y} { + return + } + incr y + } + } + + if {$x > 3 && $y >= $right_rows_created} { + return + } + + set insert [expr {[$entrybox index end] - $insert}] + switch -- $x { + {0} {set type h} + {1} {set type d} + {2} {set type b} + {3} {set type o} + {4} {set type c1} + {5} {set type c0} + {6} {set type a} + } + set entrybox [subst -nocommands "\$entry_${type}($y)"] + $entrybox selection range 0 end + $entrybox icursor [expr {[$entrybox index end] - $insert}] + focus $entrybox + } +} + +# >>> File inclusion guard +} +# <<< File inclusion guard |