Browse Source

textblock table vert sep fixes

master
Julian Noble 7 months ago
parent
commit
1b9a294058
  1. 2
      src/bootsupport/modules/punk/lib-0.1.1.tm
  2. 225
      src/bootsupport/modules/textblock-0.1.1.tm
  3. 15
      src/modules/patternpunk-1.1.tm
  4. 79
      src/modules/punk-0.1.tm
  5. 223
      src/modules/textblock-999999.0a1.0.tm

2
src/bootsupport/modules/punk/lib-0.1.1.tm

@ -221,7 +221,7 @@ namespace eval punk::lib {
#[para]We want to resolve the index used, without passing arbitrary expressions into the 'expr' function - which could have security risks. #[para]We want to resolve the index used, without passing arbitrary expressions into the 'expr' function - which could have security risks.
#[para]lindex_resolve will parse the index expression and return -1 if the supplied index expression is out of bounds for the supplied list. #[para]lindex_resolve will parse the index expression and return -1 if the supplied index expression is out of bounds for the supplied list.
#[para]Otherwise it will return an integer corresponding to the position in the list. #[para]Otherwise it will return an integer corresponding to the position in the list.
#[para]Like Tcl list commands - it will produce an error if the form of the #[para]Like Tcl list commands - it will produce an error if the form of the index is not acceptable
#Note that for an index such as $x+1 - we never see the '$x' as it is substituted in the calling command. We will get something like 10+1 - which we will resolve (hopefully safely) with expr #Note that for an index such as $x+1 - we never see the '$x' as it is substituted in the calling command. We will get something like 10+1 - which we will resolve (hopefully safely) with expr
if {![llength $list]} { if {![llength $list]} {

225
src/bootsupport/modules/textblock-0.1.1.tm

@ -52,7 +52,9 @@ namespace eval textblock {
]\ ]\
-framemap_header [list headerleft {} headerinner {} headerright {} headersolo {}]\ -framemap_header [list headerleft {} headerinner {} headerright {} headersolo {}]\
-show_edge 1\ -show_edge 1\
-show_separators 1\ -show_seps 1\
-show_hseps ""\
-show_vseps ""\
-show_header ""\ -show_header ""\
-show_footer ""\ -show_footer ""\
] ]
@ -76,8 +78,8 @@ namespace eval textblock {
onlyright [list hlt hlb tlc blc brc trc vlr]\ onlyright [list hlt hlb tlc blc brc trc vlr]\
onlysolo [list hlt hlb vll vlr blc brc trc brc]\ onlysolo [list hlt hlb vll vlr blc brc trc brc]\
] ]
variable table_sep_parts variable table_hseps
set table_sep_parts [dict create\ set table_hseps [dict create\
topleft [list blc hlb]\ topleft [list blc hlb]\
topinner [list blc hlb]\ topinner [list blc hlb]\
topright [list blc hlb brc]\ topright [list blc hlb brc]\
@ -95,6 +97,31 @@ namespace eval textblock {
onlyright [list]\ onlyright [list]\
onlysolo [list]\ onlysolo [list]\
] ]
variable table_vseps
set table_vseps [dict create\
headerleft [list]\
headerinner [list vll tlc blc]\
headerright [list vll tlc blc]\
headersolo [list]\
topleft [list]\
topinner [list vll tlc blc]\
topright [list vll tlc blc]\
topsolo [list]\
middleleft [list]\
middleinner [list vll tlc blc]\
middleright [list vll tlc blc]\
middlesolo [list]\
bottomleft [list]\
bottominner [list vll tlc blc]\
bottomright [list vll tlc blc]\
bottomsolo [list]\
onlyleft [list]\
onlyinner [list vll tlc blc]\
onlyright [list vll tlc blc]\
onlysolo [list]\
]
variable header_border_parts variable header_border_parts
set header_border_parts [dict create\ set header_border_parts [dict create\
headerleft [list vll tlc blc hlt]\ headerleft [list vll tlc blc hlt]\
@ -117,9 +144,9 @@ namespace eval textblock {
return $map return $map
} }
proc table_sep_map {char} { proc table_sep_map {char} {
variable table_sep_parts variable table_hseps
set map [list] set map [list]
dict for {celltype parts} $table_sep_parts { dict for {celltype parts} $table_hseps {
set tmap [list] set tmap [list]
foreach p $parts { foreach p $parts {
dict set tmap $p $char dict set tmap $p $char
@ -188,6 +215,30 @@ namespace eval textblock {
set o_rowstates [dict create] ;#actual row data such as -minheight and -maxheight detected from supplied row data set o_rowstates [dict create] ;#actual row data such as -minheight and -maxheight detected from supplied row data
} }
method Get_seps {} {
set requested_seps [dict get $o_opts_table -show_seps]
set requested_seps_h [dict get $o_opts_table -show_hseps]
set requested_seps_v [dict get $o_opts_table -show_vseps]
set seps $requested_seps
set seps_h $requested_seps_h
set seps_v $requested_seps_v
if {$requested_seps eq ""} {
if {$requested_seps_h eq ""} {
set seps_h 1
}
if {$requested_seps_v eq ""} {
set seps_v 1
}
} else {
if {$requested_seps_h eq ""} {
set seps_h $seps
}
if {$requested_seps_v eq ""} {
set seps_v $seps
}
}
return [dict create horizontal $seps_h vertical $seps_v]
}
method Get_frametypes {} { method Get_frametypes {} {
set requested_ft [dict get $o_opts_table -frametype] set requested_ft [dict get $o_opts_table -frametype]
set requested_ft_header [dict get $o_opts_table -frametype_header] set requested_ft_header [dict get $o_opts_table -frametype_header]
@ -242,6 +293,21 @@ namespace eval textblock {
set checked_opts [list] set checked_opts [list]
dict for {k v} $args { dict for {k v} $args {
switch -- $k { switch -- $k {
-ansibase_header - -ansibase_body - -ansiborder_header - -ansiborder-body - -ansiborder_footer {
set parts [punk::ansi::ta::split_codes_single $v] ;#caller may have supplied separated codes eg "[a+ Yellow][a+ red]"
set ansi_codes [list] ;
foreach {pt code} $parts {
if {$pt ne ""} {
#we don't expect plaintext in an ansibase
error "Unable to interpret $k value as ansi SGR codes. Plaintext detected. Consider using for example: '\[punk::ansi::a+ green]' (or alias '\[a+ green]') to build ansi. debug view: [punk::ansi::ansistring VIEW $v]"
}
if {$code ne ""} {
lappend ansi_codes $code
}
}
set ansival [punk::ansi::codetype::sgr_merge $ansi_codes]
lappend checked_opts $k $ansival
}
-ansireset { -ansireset {
if {$v eq "\uFFEF"} { if {$v eq "\uFFEF"} {
lappend checked_opts $k "\x1b\[m" ;# [a] lappend checked_opts $k "\x1b\[m" ;# [a]
@ -607,56 +673,35 @@ namespace eval textblock {
left { left {
set header_boxlimits {hl tlc blc vll} set header_boxlimits {hl tlc blc vll}
set header_joins [list down-$ftype_body] set header_joins [list down-$ftype_body]
set boxlimits_build {hlb blc vll} set boxlimits_position {hlb blc vll}
set boxlimits {}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vll tlc} set boxlimits_headerless {hlb hlt blc vll tlc}
set joins {down} set joins {down}
} }
inner { inner {
set header_boxlimits {hl tlc blc vll} set header_boxlimits {hl tlc blc vll}
set header_joins [list left down-$ftype_body] set header_joins [list left down-$ftype_body]
set boxlimits_build {hlb blc vll} set boxlimits_position {hlb blc vll}
set boxlimits {}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vll tlc} set boxlimits_headerless {hlb hlt blc vll tlc}
set joins {down left} set joins {down left}
} }
right { right {
set header_boxlimits {hl tlc blc vl trc brc} set header_boxlimits {hl tlc blc vll vlr trc brc}
set header_joins [list left down-$ftype_body] set header_joins [list left down-$ftype_body]
set boxlimits_build {hlb blc vll vlr brc} set boxlimits_position {hlb blc vll vlr brc}
set boxlimits {}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vll vlr brc tlc trc} set boxlimits_headerless {hlb hlt blc vll vlr brc tlc trc}
set joins {down left} set joins {down left}
} }
solo { solo {
set header_boxlimits {hl tlc blc vl trc brc} set header_boxlimits {hl tlc blc vll vlr trc brc}
set header_joins [list down-$ftype_body] set header_joins [list down-$ftype_body]
set boxlimits_build {hlb blc vll vlr brc} set boxlimits_position {hlb blc vll vlr brc}
set boxlimits {} set boxlimits_headerless {hlb hlt blc vll vlr brc tlc trc}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vl brc tlc trc}
set joins {down} set joins {down}
} }
} }
#use struct::set instead of simple for loop - will be faster at least when critcl available
set boxlimits [struct::set intersect [dict get $o_opts_table -framelimits_body] $boxlimits_position]
upvar ::textblock::class::opts_table_defaults tdefaults upvar ::textblock::class::opts_table_defaults tdefaults
set defaultmap [dict get $tdefaults -framemap_body] set defaultmap [dict get $tdefaults -framemap_body]
set default_hmap [dict get $tdefaults -framemap_header] set default_hmap [dict get $tdefaults -framemap_header]
@ -667,46 +712,23 @@ namespace eval textblock {
set fmap [dict merge $defaultmap [dict get $o_opts_table -framemap_body]] set fmap [dict merge $defaultmap [dict get $o_opts_table -framemap_body]]
set hmap [dict merge $default_hmap [dict get $o_opts_table -framemap_header]] set hmap [dict merge $default_hmap [dict get $o_opts_table -framemap_header]]
} }
set sep_elements $::textblock::class::table_sep_parts set sep_elements_horizontal $::textblock::class::table_hseps
set sep_elements_vertical $::textblock::class::table_vseps
switch -- $opt_posn { set topmap [dict get $fmap top$opt_posn]
left { set botmap [dict get $fmap bottom$opt_posn]
set topmap [dict get $fmap topleft] set midmap [dict get $fmap middle$opt_posn]
set botmap [dict get $fmap bottomleft] set onlymap [dict get $fmap only$opt_posn]
set midmap [dict get $fmap middleleft] set hdrmap [dict get $hmap header$opt_posn]
set onlymap [dict get $fmap onlyleft] set topseps_h [dict get $sep_elements_horizontal top$opt_posn]
set hdrmap [dict get $hmap headerleft] set topseps_v [dict get $sep_elements_vertical top$opt_posn]
set topseps [dict get $sep_elements topleft] set midseps_h [dict get $sep_elements_horizontal middle$opt_posn]
set midseps [dict get $sep_elements middleleft] set midseps_v [dict get $sep_elements_vertical middle$opt_posn]
} set botseps_v [dict get $sep_elements_vertical bottom$opt_posn]
inner {
set topmap [dict get $fmap topinner] set headerseps_v [dict get $sep_elements_vertical header$opt_posn]
set botmap [dict get $fmap bottominner]
set midmap [dict get $fmap middleinner] lassign [my Get_seps] _h show_seps_h _v show_seps_v
set onlymap [dict get $fmap onlyinner]
set hdrmap [dict get $hmap headerinner]
set topseps [dict get $sep_elements topinner]
set midseps [dict get $sep_elements middleinner]
}
right {
set topmap [dict get $fmap topright]
set botmap [dict get $fmap bottomright]
set midmap [dict get $fmap middleright]
set onlymap [dict get $fmap onlyright]
set hdrmap [dict get $hmap headerright]
set topseps [dict get $sep_elements topright]
set midseps [dict get $sep_elements middleright]
}
solo {
set topmap [dict get $fmap topsolo]
set botmap [dict get $fmap bottomsolo]
set midmap [dict get $fmap middlesolo]
set onlymap [dict get $fmap onlysolo]
set hdrmap [dict get $hmap headersolo]
set topseps [dict get $sep_elements topsolo]
set midseps [dict get $sep_elements middlesolo]
}
}
if {$do_show_header} { if {$do_show_header} {
#puts "boxlimitsinfo header $opt_posn: -- boxlimits $header_boxlimits -- boxmap $hdrmap" #puts "boxlimitsinfo header $opt_posn: -- boxlimits $header_boxlimits -- boxmap $hdrmap"
@ -732,9 +754,14 @@ namespace eval textblock {
set hval_block [join $hval_lines \n] set hval_block [join $hval_lines \n]
set headercell [overtype::left -experimental test_mode $ansibase_header$hcell_blank$RST $hval_block] set headercell [overtype::left -experimental test_mode $ansibase_header$hcell_blank$RST $hval_block]
set hlims $header_boxlimits
if {!$show_seps_v} {
set hlims [struct::set difference $header_boxlimits $headerseps_v]
}
set header_frame [textblock::frame -width [expr {$colwidth+2}] -type [dict get $ftypes header]\ set header_frame [textblock::frame -width [expr {$colwidth+2}] -type [dict get $ftypes header]\
-ansibase $ansibase_header -ansiborder $ansiborder_final\ -ansibase $ansibase_header -ansiborder $ansiborder_final\
-boxlimits $header_boxlimits -boxmap $hdrmap -joins $header_joins $hval\ -boxlimits $hlims -boxmap $hdrmap -joins $header_joins $hval\
] ]
#puts ">> '[ansistring VIEW $hval]' -> $header_frame" #puts ">> '[ansistring VIEW $hval]' -> $header_frame"
@ -747,24 +774,18 @@ namespace eval textblock {
set blims_mid $boxlimits set blims_mid $boxlimits
set blims_top $boxlimits set blims_top $boxlimits
set blims_bot $boxlimits
set blims_top_headerless $boxlimits_headerless set blims_top_headerless $boxlimits_headerless
if {![dict get $o_opts_table -show_separators]} { if {!$show_seps_h} {
foreach el $midseps { set blims_mid [struct::set difference $blims_mid $midseps_h]
set elposn [lsearch $blims_mid $el] set blims_top [struct::set difference $blims_top $topseps_h]
if {$elposn >= 0} { set blims_top_headerless [struct::set difference $blims_top_headerless $topseps_h]
set blims_mid [lremove $blims_mid $elposn] }
} if {!$show_seps_v} {
} set blims_mid [struct::set difference $blims_mid $midseps_v]
foreach el $topseps { set blims_top [struct::set difference $blims_top $topseps_v]
set elposn [lsearch $blims_top $el] set blims_top_headerless [struct::set difference $blims_top_headerless $topseps_v]
if {$elposn >= 0} { set blims_bot [struct::set difference $blims_bot $botseps_v]
set blims_top [lremove $blims_top $elposn]
}
set elposn [lsearch $blims_top_headerless $el]
if {$elposn >= 0} {
set blims_top_headerless [lremove $blims_top_headerless $elposn]
}
}
} }
set colidx [lindex [dict keys $o_columndefs] $index_expression] ;#convert possible end-1,2+2 etc expression to >= 0 integer in dict range set colidx [lindex [dict keys $o_columndefs] $index_expression] ;#convert possible end-1,2+2 etc expression to >= 0 integer in dict range
@ -819,10 +840,10 @@ namespace eval textblock {
if {$r == $rmax} { if {$r == $rmax} {
set joins [lremove $joins [lsearch $joins down*]] set joins [lremove $joins [lsearch $joins down*]]
set bmap $botmap set bmap $botmap
set blims $boxlimits set blims $blims_bot
} else { } else {
set bmap $midmap set bmap $midmap
set blims $blims_mid ;#will only be reduced from boxlimits if -show_separators was processed above set blims $blims_mid ;#will only be reduced from boxlimits if -show_seps was processed above
} }
append output [textblock::frame -type [dict get $ftypes body] -ansibase $ansibase -ansiborder $border_ansi_final -boxlimits $blims -boxmap $bmap -joins $joins $c]\n append output [textblock::frame -type [dict get $ftypes body] -ansibase $ansibase -ansiborder $border_ansi_final -boxlimits $blims -boxmap $bmap -joins $joins $c]\n
} }
@ -1102,16 +1123,16 @@ namespace eval textblock {
namespace eval ::term::ansi::code::macros::cd {namespace export -clear} namespace eval ::term::ansi::code::macros::cd {namespace export -clear}
} }
proc list_as_table {datalist table_or_colcount args} { proc list_as_table {table_or_colcount datalist args} {
set defaults [dict create\ set defaults [dict create\
-return string\ -return string\
-frametype \uFFEF\ -frametype \uFFEF\
-show_edge \uFFEF\ -show_edge \uFFEF\
-show_separators \uFFEF\ -show_seps \uFFEF\
] ]
foreach {k v} $args { foreach {k v} $args {
switch -- $k { switch -- $k {
-return - -show_edge - -show_separators - -frametype {} -return - -show_edge - -show_seps - -frametype {}
default { default {
error "unrecognised option '$k'. Known options [dict keys $defaults]" error "unrecognised option '$k'. Known options [dict keys $defaults]"
} }
@ -1132,10 +1153,10 @@ namespace eval textblock {
if {[dict get $opts -show_edge] eq "\uFFEF"} { if {[dict get $opts -show_edge] eq "\uFFEF"} {
dict set opts -show_edge 1 dict set opts -show_edge 1
} }
if {[dict get $opts -show_separators] eq "\uFFEF"} { if {[dict get $opts -show_seps] eq "\uFFEF"} {
dict set opts -show_separators 1 dict set opts -show_seps 1
} }
set t [textblock::class::table new -show_header 0 -show_edge [dict get $opts -show_edge] -frametype [dict get $opts -frametype] -show_separators [dict get $opts -show_separators]] set t [textblock::class::table new -show_header 0 -show_edge [dict get $opts -show_edge] -frametype [dict get $opts -frametype] -show_seps [dict get $opts -show_seps]]
for {set c 0} {$c < $cols} {incr c} { for {set c 0} {$c < $cols} {incr c} {
$t add_column -header c$c $t add_column -header c$c
} }
@ -2839,7 +2860,7 @@ namespace eval textblock {
#boxlimits used for partial borders in table generation #boxlimits used for partial borders in table generation
set all_exact_boxlimits [list vll vlr hlt hlb tlc blc trc blc] set all_exact_boxlimits [list vll vlr hlt hlb tlc blc trc blc]
set unspecified_limits [struct::set diff $all_exact_boxlimits $exact_boxlimits] set unspecified_limits [struct::set difference $all_exact_boxlimits $exact_boxlimits]
foreach lim $unspecified_limits { foreach lim $unspecified_limits {
switch -- $lim { switch -- $lim {
vll { vll {

15
src/modules/patternpunk-1.1.tm

@ -20,7 +20,7 @@ pattern::init
::>pattern .. Create ::>punk ::>pattern .. Create ::>punk
::>punk .. Property license {Public Domain} ::>punk .. Property license {Public Domain}
::>punk .. Property logo2 [string trim { ::>punk .. Property logo_ascii [string trim {
+-----------------------+ +-----------------------+
| Pattern PUNK | | Pattern PUNK |
| . \\\_ . | | . \\\_ . |
@ -32,7 +32,7 @@ pattern::init
| . _+ +_ . | | . _+ +_ . |
+-----------------------+ +-----------------------+
} \n] } \n]
set ::punk::bannerTemplate [string trim { set ::punk::bannerTemplate0 [string trim {
+-----------------------+ +-----------------------+
| .000000000000000. | | .000000000000000. |
| .*. \\\_ .=. | | .*. \\\_ .=. |
@ -44,6 +44,16 @@ set ::punk::bannerTemplate [string trim {
|111111111_+ +_2222222| |111111111_+ +_2222222|
+-----------------------+ +-----------------------+
} \n] } \n]
set ::punk::bannerTemplate [string trim {
.000000000000000.
.*. \\\_ .=.
.*.*. \@ > .=.=.
.*.*.*. | ~ .=.=.=.
.*.*. \_- -_/ .=.=.
.*. \\ .=.
. / \ .
111111111_+ +_2222222
} \n]
>punk .. Method banner {args} { >punk .. Method banner {args} {
set defaults [list -title "Pattern PUNK" -left "" -right ""] set defaults [list -title "Pattern PUNK" -left "" -right ""]
@ -54,7 +64,6 @@ set ::punk::bannerTemplate [string trim {
set word1 [overtype::left [string repeat " " 9] [dict get $opts -left]] set word1 [overtype::left [string repeat " " 9] [dict get $opts -left]]
set word2 [overtype::right [string repeat " " 7] [dict get $opts -right]] set word2 [overtype::right [string repeat " " 7] [dict get $opts -right]]
set title [overtype::centre [string repeat " " 15] [dict get $opts -title]] set title [overtype::centre [string repeat " " 15] [dict get $opts -title]]
return [string map [list 111111111 $word1 2222222 $word2 000000000000000 $title] $::punk::bannerTemplate] return [string map [list 111111111 $word1 2222222 $word2 000000000000000 $title] $::punk::bannerTemplate]
} }

79
src/modules/punk-0.1.tm

@ -6918,32 +6918,12 @@ namespace eval punk {
catch { catch {
package require patternpunk package require patternpunk
#lappend chunks [list stderr [>punk . rhs]] #lappend chunks [list stderr [>punk . rhs]]
append mascotblock [>punk . banner -title "Punk Shell" -left Tcl -right [package provide Tcl]] append mascotblock [textblock::frame [>punk . banner -title "Punk Shell" -left Tcl -right [package provide Tcl]]]
} }
set topic [lindex $args end] set topic [lindex $args end]
set argopts [lrange $args 0 end-1] set argopts [lrange $args 0 end-1]
set text ""
if {$topic in [list env environment]} {
set known $::punk::config::known_punk_env_vars
append text $linesep\n
append text "punk environment vars:\n"
append text $linesep\n
set col1 [string repeat " " 25]
set col2 [string repeat " " 50]
foreach v $known {
set c1 [overtype::left $col1 $v]
if {[info exists ::env($v)]} {
set c2 [overtype::left $col2 [set ::env($v)]
} else {
set c2 [overtype::right $col2 "(NOT SET)"]
}
append text "$c1 $c2\n"
}
append text $linesep\n
lappend chunks [list stdout $text]
}
set text "" set text ""
append text "Punk core navigation commands:\n" append text "Punk core navigation commands:\n"
@ -6964,11 +6944,17 @@ namespace eval punk {
set descr [lsearch -all -inline -index 1 -subindices $cmdinfo *] set descr [lsearch -all -inline -index 1 -subindices $cmdinfo *]
set widest1 [tcl::mathfunc::max {*}[lmap v $cmds {string length $v}]] set widest1 [tcl::mathfunc::max {*}[lmap v $cmds {string length $v}]]
set widest2 [tcl::mathfunc::max {*}[lmap v $descr {string length $v}]] set widest2 [tcl::mathfunc::max {*}[lmap v $descr {string length $v}]]
set col1 "[string repeat " " $widest1] " set t [textblock::class::table new -show_seps 0]
set col2 "[string repeat " " $widest2] "
foreach c $cmds d $descr { foreach c $cmds d $descr {
append text " [overtype::left $col1 $c][overtype::left $col2 $d]" \n #append text " [overtype::left $col1 $c][overtype::left $col2 $d]" \n
$t add_row [list $c $d]
} }
set widest1 [$t column_datawidth 0]
$t configure_column 0 -minwidth [expr {$widest1 + 2}]
set widest2 [$t column_datawidth 1]
$t configure_column 1 -minwidth [expr {$widest2 + 1}]
append text [$t print]
set warningblock "" set warningblock ""
@ -6978,15 +6964,40 @@ namespace eval punk {
append warningblock \n "WARNING: textblock package couldn't be loaded. Side-by-side display not available" append warningblock \n "WARNING: textblock package couldn't be loaded. Side-by-side display not available"
} else { } else {
set introblock [textblock::join " " $mascotblock " " $text] set introblock [textblock::join " " \n$mascotblock " " $text]
} }
lappend chunks [list stdout $introblock]
if {$topic in [list tcl]} { if {$topic in [list tcl]} {
if {[punk::repl::has_script_var_bug]} { if {[punk::repl::has_script_var_bug]} {
append warningblock \n "minor warning: punk::repl::has_script_var_bug returned true! (string rep for list variable in script generated when script changed)" append warningblock \n "minor warning: punk::repl::has_script_var_bug returned true! (string rep for list variable in script generated when script changed)"
} }
} }
set text ""
if {$topic in [list env environment]} {
set known $::punk::config::known_punk_env_vars
append text $linesep\n
append text "punk environment vars:\n"
append text $linesep\n
set col1 [string repeat " " 25]
set col2 [string repeat " " 50]
foreach v $known {
set c1 [overtype::left $col1 $v]
if {[info exists ::env($v)]} {
set c2 [overtype::left $col2 [set ::env($v)]
} else {
set c2 [overtype::right $col2 "(NOT SET)"]
}
append text "$c1 $c2\n"
}
append text $linesep\n
lappend chunks [list stdout $text]
}
if {$topic in [list console terminal]} { if {$topic in [list console terminal]} {
lappend cstring_tests [dict create\ lappend cstring_tests [dict create\
type "PM "\ type "PM "\
@ -7034,24 +7045,26 @@ namespace eval punk {
} }
} }
lappend chunks [list stdout $introblock]
lappend chunks [list stderr $warningblock] lappend chunks [list stderr $warningblock]
if {$topic in [list topics help]} { if {$topic in [list topics help]} {
set text "" set text ""
set topics [dict create\ set topics [dict create\
"topic|help" "List help topics"\ "topics|help" "List help topics"\
"tcl" "Tcl version warnings"\ "tcl" "Tcl version warnings"\
"env|environment" "punkshell environment vars"\ "env|environment" "punkshell environment vars"\
"console|terminal" "Some console behaviour tests and warnings"\ "console|terminal" "Some console behaviour tests and warnings"\
] ]
set col1 [string repeat " " 20]
append text \n [string repeat - 20] set t [textblock::class::table new -show_seps 0]
append text \n "Topic" $t add_column -header "Topic"
append text \n [string repeat - 20] $t add_column
foreach {k v} $topics { foreach {k v} $topics {
append text \n "[overtype::left $col1 $k] $v" $t add_row [list $k $v]
} }
append text \n set widest0 [$t column_datawidth 0]
$t configure_column 0 -minwidth [expr {$widest0 + 4}]
append text \n[$t print]
lappend chunks [list stdout $text] lappend chunks [list stdout $text]
} }

223
src/modules/textblock-999999.0a1.0.tm

@ -52,7 +52,9 @@ namespace eval textblock {
]\ ]\
-framemap_header [list headerleft {} headerinner {} headerright {} headersolo {}]\ -framemap_header [list headerleft {} headerinner {} headerright {} headersolo {}]\
-show_edge 1\ -show_edge 1\
-show_separators 1\ -show_seps 1\
-show_hseps ""\
-show_vseps ""\
-show_header ""\ -show_header ""\
-show_footer ""\ -show_footer ""\
] ]
@ -76,8 +78,8 @@ namespace eval textblock {
onlyright [list hlt hlb tlc blc brc trc vlr]\ onlyright [list hlt hlb tlc blc brc trc vlr]\
onlysolo [list hlt hlb vll vlr blc brc trc brc]\ onlysolo [list hlt hlb vll vlr blc brc trc brc]\
] ]
variable table_sep_parts variable table_hseps
set table_sep_parts [dict create\ set table_hseps [dict create\
topleft [list blc hlb]\ topleft [list blc hlb]\
topinner [list blc hlb]\ topinner [list blc hlb]\
topright [list blc hlb brc]\ topright [list blc hlb brc]\
@ -95,6 +97,31 @@ namespace eval textblock {
onlyright [list]\ onlyright [list]\
onlysolo [list]\ onlysolo [list]\
] ]
variable table_vseps
set table_vseps [dict create\
headerleft [list]\
headerinner [list vll tlc blc]\
headerright [list vll tlc blc]\
headersolo [list]\
topleft [list]\
topinner [list vll tlc blc]\
topright [list vll tlc blc]\
topsolo [list]\
middleleft [list]\
middleinner [list vll tlc blc]\
middleright [list vll tlc blc]\
middlesolo [list]\
bottomleft [list]\
bottominner [list vll tlc blc]\
bottomright [list vll tlc blc]\
bottomsolo [list]\
onlyleft [list]\
onlyinner [list vll tlc blc]\
onlyright [list vll tlc blc]\
onlysolo [list]\
]
variable header_border_parts variable header_border_parts
set header_border_parts [dict create\ set header_border_parts [dict create\
headerleft [list vll tlc blc hlt]\ headerleft [list vll tlc blc hlt]\
@ -117,9 +144,9 @@ namespace eval textblock {
return $map return $map
} }
proc table_sep_map {char} { proc table_sep_map {char} {
variable table_sep_parts variable table_hseps
set map [list] set map [list]
dict for {celltype parts} $table_sep_parts { dict for {celltype parts} $table_hseps {
set tmap [list] set tmap [list]
foreach p $parts { foreach p $parts {
dict set tmap $p $char dict set tmap $p $char
@ -188,6 +215,30 @@ namespace eval textblock {
set o_rowstates [dict create] ;#actual row data such as -minheight and -maxheight detected from supplied row data set o_rowstates [dict create] ;#actual row data such as -minheight and -maxheight detected from supplied row data
} }
method Get_seps {} {
set requested_seps [dict get $o_opts_table -show_seps]
set requested_seps_h [dict get $o_opts_table -show_hseps]
set requested_seps_v [dict get $o_opts_table -show_vseps]
set seps $requested_seps
set seps_h $requested_seps_h
set seps_v $requested_seps_v
if {$requested_seps eq ""} {
if {$requested_seps_h eq ""} {
set seps_h 1
}
if {$requested_seps_v eq ""} {
set seps_v 1
}
} else {
if {$requested_seps_h eq ""} {
set seps_h $seps
}
if {$requested_seps_v eq ""} {
set seps_v $seps
}
}
return [dict create horizontal $seps_h vertical $seps_v]
}
method Get_frametypes {} { method Get_frametypes {} {
set requested_ft [dict get $o_opts_table -frametype] set requested_ft [dict get $o_opts_table -frametype]
set requested_ft_header [dict get $o_opts_table -frametype_header] set requested_ft_header [dict get $o_opts_table -frametype_header]
@ -242,6 +293,21 @@ namespace eval textblock {
set checked_opts [list] set checked_opts [list]
dict for {k v} $args { dict for {k v} $args {
switch -- $k { switch -- $k {
-ansibase_header - -ansibase_body - -ansiborder_header - -ansiborder-body - -ansiborder_footer {
set parts [punk::ansi::ta::split_codes_single $v] ;#caller may have supplied separated codes eg "[a+ Yellow][a+ red]"
set ansi_codes [list] ;
foreach {pt code} $parts {
if {$pt ne ""} {
#we don't expect plaintext in an ansibase
error "Unable to interpret $k value as ansi SGR codes. Plaintext detected. Consider using for example: '\[punk::ansi::a+ green]' (or alias '\[a+ green]') to build ansi. debug view: [punk::ansi::ansistring VIEW $v]"
}
if {$code ne ""} {
lappend ansi_codes $code
}
}
set ansival [punk::ansi::codetype::sgr_merge $ansi_codes]
lappend checked_opts $k $ansival
}
-ansireset { -ansireset {
if {$v eq "\uFFEF"} { if {$v eq "\uFFEF"} {
lappend checked_opts $k "\x1b\[m" ;# [a] lappend checked_opts $k "\x1b\[m" ;# [a]
@ -607,56 +673,35 @@ namespace eval textblock {
left { left {
set header_boxlimits {hl tlc blc vll} set header_boxlimits {hl tlc blc vll}
set header_joins [list down-$ftype_body] set header_joins [list down-$ftype_body]
set boxlimits_build {hlb blc vll} set boxlimits_position {hlb blc vll}
set boxlimits {}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vll tlc} set boxlimits_headerless {hlb hlt blc vll tlc}
set joins {down} set joins {down}
} }
inner { inner {
set header_boxlimits {hl tlc blc vll} set header_boxlimits {hl tlc blc vll}
set header_joins [list left down-$ftype_body] set header_joins [list left down-$ftype_body]
set boxlimits_build {hlb blc vll} set boxlimits_position {hlb blc vll}
set boxlimits {}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vll tlc} set boxlimits_headerless {hlb hlt blc vll tlc}
set joins {down left} set joins {down left}
} }
right { right {
set header_boxlimits {hl tlc blc vl trc brc} set header_boxlimits {hl tlc blc vll vlr trc brc}
set header_joins [list left down-$ftype_body] set header_joins [list left down-$ftype_body]
set boxlimits_build {hlb blc vll vlr brc} set boxlimits_position {hlb blc vll vlr brc}
set boxlimits {}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vll vlr brc tlc trc} set boxlimits_headerless {hlb hlt blc vll vlr brc tlc trc}
set joins {down left} set joins {down left}
} }
solo { solo {
set header_boxlimits {hl tlc blc vl trc brc} set header_boxlimits {hl tlc blc vll vlr trc brc}
set header_joins [list down-$ftype_body] set header_joins [list down-$ftype_body]
set boxlimits_build {hlb blc vll vlr brc} set boxlimits_position {hlb blc vll vlr brc}
set boxlimits {} set boxlimits_headerless {hlb hlt blc vll vlr brc tlc trc}
foreach l $boxlimits_build {
if {$l in [dict get $o_opts_table -framelimits_body]} {
lappend boxlimits $l
}
}
set boxlimits_headerless {hlb hlt blc vl brc tlc trc}
set joins {down} set joins {down}
} }
} }
#use struct::set instead of simple for loop - will be faster at least when critcl available
set boxlimits [struct::set intersect [dict get $o_opts_table -framelimits_body] $boxlimits_position]
upvar ::textblock::class::opts_table_defaults tdefaults upvar ::textblock::class::opts_table_defaults tdefaults
set defaultmap [dict get $tdefaults -framemap_body] set defaultmap [dict get $tdefaults -framemap_body]
set default_hmap [dict get $tdefaults -framemap_header] set default_hmap [dict get $tdefaults -framemap_header]
@ -667,46 +712,23 @@ namespace eval textblock {
set fmap [dict merge $defaultmap [dict get $o_opts_table -framemap_body]] set fmap [dict merge $defaultmap [dict get $o_opts_table -framemap_body]]
set hmap [dict merge $default_hmap [dict get $o_opts_table -framemap_header]] set hmap [dict merge $default_hmap [dict get $o_opts_table -framemap_header]]
} }
set sep_elements $::textblock::class::table_sep_parts set sep_elements_horizontal $::textblock::class::table_hseps
set sep_elements_vertical $::textblock::class::table_vseps
switch -- $opt_posn { set topmap [dict get $fmap top$opt_posn]
left { set botmap [dict get $fmap bottom$opt_posn]
set topmap [dict get $fmap topleft] set midmap [dict get $fmap middle$opt_posn]
set botmap [dict get $fmap bottomleft] set onlymap [dict get $fmap only$opt_posn]
set midmap [dict get $fmap middleleft] set hdrmap [dict get $hmap header$opt_posn]
set onlymap [dict get $fmap onlyleft] set topseps_h [dict get $sep_elements_horizontal top$opt_posn]
set hdrmap [dict get $hmap headerleft] set topseps_v [dict get $sep_elements_vertical top$opt_posn]
set topseps [dict get $sep_elements topleft] set midseps_h [dict get $sep_elements_horizontal middle$opt_posn]
set midseps [dict get $sep_elements middleleft] set midseps_v [dict get $sep_elements_vertical middle$opt_posn]
} set botseps_v [dict get $sep_elements_vertical bottom$opt_posn]
inner {
set topmap [dict get $fmap topinner] set headerseps_v [dict get $sep_elements_vertical header$opt_posn]
set botmap [dict get $fmap bottominner]
set midmap [dict get $fmap middleinner] lassign [my Get_seps] _h show_seps_h _v show_seps_v
set onlymap [dict get $fmap onlyinner]
set hdrmap [dict get $hmap headerinner]
set topseps [dict get $sep_elements topinner]
set midseps [dict get $sep_elements middleinner]
}
right {
set topmap [dict get $fmap topright]
set botmap [dict get $fmap bottomright]
set midmap [dict get $fmap middleright]
set onlymap [dict get $fmap onlyright]
set hdrmap [dict get $hmap headerright]
set topseps [dict get $sep_elements topright]
set midseps [dict get $sep_elements middleright]
}
solo {
set topmap [dict get $fmap topsolo]
set botmap [dict get $fmap bottomsolo]
set midmap [dict get $fmap middlesolo]
set onlymap [dict get $fmap onlysolo]
set hdrmap [dict get $hmap headersolo]
set topseps [dict get $sep_elements topsolo]
set midseps [dict get $sep_elements middlesolo]
}
}
if {$do_show_header} { if {$do_show_header} {
#puts "boxlimitsinfo header $opt_posn: -- boxlimits $header_boxlimits -- boxmap $hdrmap" #puts "boxlimitsinfo header $opt_posn: -- boxlimits $header_boxlimits -- boxmap $hdrmap"
@ -732,9 +754,14 @@ namespace eval textblock {
set hval_block [join $hval_lines \n] set hval_block [join $hval_lines \n]
set headercell [overtype::left -experimental test_mode $ansibase_header$hcell_blank$RST $hval_block] set headercell [overtype::left -experimental test_mode $ansibase_header$hcell_blank$RST $hval_block]
set hlims $header_boxlimits
if {!$show_seps_v} {
set hlims [struct::set difference $header_boxlimits $headerseps_v]
}
set header_frame [textblock::frame -width [expr {$colwidth+2}] -type [dict get $ftypes header]\ set header_frame [textblock::frame -width [expr {$colwidth+2}] -type [dict get $ftypes header]\
-ansibase $ansibase_header -ansiborder $ansiborder_final\ -ansibase $ansibase_header -ansiborder $ansiborder_final\
-boxlimits $header_boxlimits -boxmap $hdrmap -joins $header_joins $hval\ -boxlimits $hlims -boxmap $hdrmap -joins $header_joins $hval\
] ]
#puts ">> '[ansistring VIEW $hval]' -> $header_frame" #puts ">> '[ansistring VIEW $hval]' -> $header_frame"
@ -747,24 +774,18 @@ namespace eval textblock {
set blims_mid $boxlimits set blims_mid $boxlimits
set blims_top $boxlimits set blims_top $boxlimits
set blims_bot $boxlimits
set blims_top_headerless $boxlimits_headerless set blims_top_headerless $boxlimits_headerless
if {![dict get $o_opts_table -show_separators]} { if {!$show_seps_h} {
foreach el $midseps { set blims_mid [struct::set difference $blims_mid $midseps_h]
set elposn [lsearch $blims_mid $el] set blims_top [struct::set difference $blims_top $topseps_h]
if {$elposn >= 0} { set blims_top_headerless [struct::set difference $blims_top_headerless $topseps_h]
set blims_mid [lremove $blims_mid $elposn] }
} if {!$show_seps_v} {
} set blims_mid [struct::set difference $blims_mid $midseps_v]
foreach el $topseps { set blims_top [struct::set difference $blims_top $topseps_v]
set elposn [lsearch $blims_top $el] set blims_top_headerless [struct::set difference $blims_top_headerless $topseps_v]
if {$elposn >= 0} { set blims_bot [struct::set difference $blims_bot $botseps_v]
set blims_top [lremove $blims_top $elposn]
}
set elposn [lsearch $blims_top_headerless $el]
if {$elposn >= 0} {
set blims_top_headerless [lremove $blims_top_headerless $elposn]
}
}
} }
set colidx [lindex [dict keys $o_columndefs] $index_expression] ;#convert possible end-1,2+2 etc expression to >= 0 integer in dict range set colidx [lindex [dict keys $o_columndefs] $index_expression] ;#convert possible end-1,2+2 etc expression to >= 0 integer in dict range
@ -819,10 +840,10 @@ namespace eval textblock {
if {$r == $rmax} { if {$r == $rmax} {
set joins [lremove $joins [lsearch $joins down*]] set joins [lremove $joins [lsearch $joins down*]]
set bmap $botmap set bmap $botmap
set blims $boxlimits set blims $blims_bot
} else { } else {
set bmap $midmap set bmap $midmap
set blims $blims_mid ;#will only be reduced from boxlimits if -show_separators was processed above set blims $blims_mid ;#will only be reduced from boxlimits if -show_seps was processed above
} }
append output [textblock::frame -type [dict get $ftypes body] -ansibase $ansibase -ansiborder $border_ansi_final -boxlimits $blims -boxmap $bmap -joins $joins $c]\n append output [textblock::frame -type [dict get $ftypes body] -ansibase $ansibase -ansiborder $border_ansi_final -boxlimits $blims -boxmap $bmap -joins $joins $c]\n
} }
@ -1102,16 +1123,16 @@ namespace eval textblock {
namespace eval ::term::ansi::code::macros::cd {namespace export -clear} namespace eval ::term::ansi::code::macros::cd {namespace export -clear}
} }
proc list_as_table {datalist table_or_colcount args} { proc list_as_table {table_or_colcount datalist args} {
set defaults [dict create\ set defaults [dict create\
-return string\ -return string\
-frametype \uFFEF\ -frametype \uFFEF\
-show_edge \uFFEF\ -show_edge \uFFEF\
-show_separators \uFFEF\ -show_seps \uFFEF\
] ]
foreach {k v} $args { foreach {k v} $args {
switch -- $k { switch -- $k {
-return - -show_edge - -show_separators - -frametype {} -return - -show_edge - -show_seps - -frametype {}
default { default {
error "unrecognised option '$k'. Known options [dict keys $defaults]" error "unrecognised option '$k'. Known options [dict keys $defaults]"
} }
@ -1132,10 +1153,10 @@ namespace eval textblock {
if {[dict get $opts -show_edge] eq "\uFFEF"} { if {[dict get $opts -show_edge] eq "\uFFEF"} {
dict set opts -show_edge 1 dict set opts -show_edge 1
} }
if {[dict get $opts -show_separators] eq "\uFFEF"} { if {[dict get $opts -show_seps] eq "\uFFEF"} {
dict set opts -show_separators 1 dict set opts -show_seps 1
} }
set t [textblock::class::table new -show_header 0 -show_edge [dict get $opts -show_edge] -frametype [dict get $opts -frametype] -show_separators [dict get $opts -show_separators]] set t [textblock::class::table new -show_header 0 -show_edge [dict get $opts -show_edge] -frametype [dict get $opts -frametype] -show_seps [dict get $opts -show_seps]]
for {set c 0} {$c < $cols} {incr c} { for {set c 0} {$c < $cols} {incr c} {
$t add_column -header c$c $t add_column -header c$c
} }

Loading…
Cancel
Save