home *** CD-ROM | disk | FTP | other *** search
/ PC Welt 2005 March / PCWELT_3_2005.ISO / pcwsoft / framework-2.2.exe / scrolledlistbox.itk < prev    next >
Encoding:
Text File  |  2003-09-01  |  25.9 KB  |  733 lines

  1. #
  2. # Scrolledlistbox
  3. # ----------------------------------------------------------------------
  4. # Implements a scrolled listbox with additional options to manage
  5. # horizontal and vertical scrollbars.  This includes options to control
  6. # which scrollbars are displayed and the method, i.e. statically,
  7. # dynamically, or none at all.  
  8. #
  9. # ----------------------------------------------------------------------
  10. #  AUTHOR: Mark L. Ulferts             EMAIL: mulferts@austin.dsccc.com
  11. #
  12. #  @(#) $Id: scrolledlistbox.itk,v 1.9 2002/03/16 16:25:44 mgbacke Exp $
  13. # ----------------------------------------------------------------------
  14. #            Copyright (c) 1995 DSC Technologies Corporation
  15. # ======================================================================
  16. # Permission to use, copy, modify, distribute and license this software 
  17. # and its documentation for any purpose, and without fee or written 
  18. # agreement with DSC, is hereby granted, provided that the above copyright 
  19. # notice appears in all copies and that both the copyright notice and 
  20. # warranty disclaimer below appear in supporting documentation, and that 
  21. # the names of DSC Technologies Corporation or DSC Communications 
  22. # Corporation not be used in advertising or publicity pertaining to the 
  23. # software without specific, written prior permission.
  24. # DSC DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING 
  25. # ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, AND NON-
  26. # INFRINGEMENT. THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, AND THE
  27. # AUTHORS AND DISTRIBUTORS HAVE NO OBLIGATION TO PROVIDE MAINTENANCE, 
  28. # SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. IN NO EVENT SHALL 
  29. # DSC BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR 
  30. # ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, 
  31. # WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTUOUS ACTION,
  32. # ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS 
  33. # SOFTWARE.
  34. # ======================================================================
  35.  
  36. #
  37. # Usual options.
  38. #
  39. itk::usual Scrolledlistbox {
  40.     keep -activebackground -activerelief -background -borderwidth -cursor \
  41.      -elementborderwidth -foreground -highlightcolor -highlightthickness \
  42.      -jump -labelfont -selectbackground -selectborderwidth \
  43.      -selectforeground -textbackground -textfont -troughcolor 
  44. }
  45.  
  46. # ------------------------------------------------------------------
  47. #                          SCROLLEDLISTBOX
  48. # ------------------------------------------------------------------
  49. itcl::class iwidgets::Scrolledlistbox {
  50.     inherit iwidgets::Scrolledwidget
  51.  
  52.     constructor {args} {}
  53.     destructor {}
  54.  
  55.     itk_option define -dblclickcommand dblClickCommand Command {}
  56.     itk_option define -selectioncommand selectionCommand Command {}
  57.     itk_option define -width width Width 0
  58.     itk_option define -height height Height 0
  59.     itk_option define -visibleitems visibleItems VisibleItems 20x10
  60.     itk_option define -state state State normal
  61.  
  62.     public method curselection {} 
  63.     public method activate {index} 
  64.     public method bbox {index} 
  65.     public method clear {} 
  66.     public method see {index} 
  67.     public method index {index} 
  68.     public method delete {first {last {}}} 
  69.     public method get {first {last {}}} 
  70.     public method getcurselection {} 
  71.     public method insert {index args} 
  72.     public method nearest {y} 
  73.     public method scan {option args} 
  74.     public method selection {option first {last {}}} 
  75.     public method size {} 
  76.     public method selecteditemcount {} 
  77.     public method justify {direction} 
  78.     public method sort {{mode ascending}} 
  79.     public method xview {args} 
  80.     public method yview {args} 
  81.     public method itemconfigure {args}
  82.  
  83.     protected method _makeSelection {} 
  84.     protected method _dblclick {} 
  85.     protected method _fixIndex {index}
  86.  
  87.     #
  88.     # List the event sequences that invoke single and double selection.
  89.     # Should these change in the underlying Tk listbox, then they must
  90.     # change here too.
  91.     #
  92.     common doubleSelectSeq { \
  93.     <Double-1> 
  94.     }
  95.  
  96.     common singleSelectSeq { \
  97.         <Control-Key-backslash> \
  98.     <Control-Key-slash> \
  99.     <Key-Escape> \
  100.     <Shift-Key-Select> \
  101.     <Control-Shift-Key-space> \
  102.     <Key-Select> \
  103.     <Key-space> \
  104.     <Control-Shift-Key-End> \
  105.     <Control-Key-End> \
  106.     <Control-Shift-Key-Home> \
  107.     <Control-Key-Home> \
  108.     <Key-Down> \
  109.     <Key-Up> \
  110.     <Shift-Key-Down> \
  111.     <Shift-Key-Up> \
  112.     <Control-Button-1> \
  113.     <Shift-Button-1> \
  114.     <ButtonRelease-1> \
  115.     }
  116. }
  117.  
  118. #
  119. # Provide a lowercased access method for the Scrolledlistbox class.
  120. proc ::iwidgets::scrolledlistbox {pathName args} {
  121.     uplevel ::iwidgets::Scrolledlistbox $pathName $args
  122. }
  123.  
  124. #
  125. # Use option database to override default resources of base classes.
  126. #
  127. option add *Scrolledlistbox.labelPos n widgetDefault
  128.  
  129. # ------------------------------------------------------------------
  130. #                        CONSTRUCTOR
  131. # ------------------------------------------------------------------
  132. itcl::body iwidgets::Scrolledlistbox::constructor {args} {
  133.     #
  134.     # Our -width and -height options are slightly different than
  135.     # those implemented by our base class, so we're going to
  136.     # remove them and redefine our own.
  137.     #
  138.     itk_option remove iwidgets::Scrolledwidget::width
  139.     itk_option remove iwidgets::Scrolledwidget::height
  140.  
  141.     # 
  142.     # Create the listbox.
  143.     #
  144.     itk_component add listbox {
  145.     listbox $itk_interior.listbox \
  146.         -width 1 -height 1 \
  147.             -xscrollcommand \
  148.         [itcl::code $this _scrollWidget $itk_interior.horizsb] \
  149.         -yscrollcommand \
  150.         [itcl::code $this _scrollWidget $itk_interior.vertsb]
  151.     } {
  152.     usual
  153.  
  154.     keep -borderwidth -exportselection -relief -selectmode
  155.     keep -listvariable
  156.     
  157.     rename -font -textfont textFont Font
  158.     rename -background -textbackground textBackground Background
  159.     rename -highlightbackground -background background Background
  160.     }
  161.     grid $itk_component(listbox) -row 0 -column 0 -sticky nsew
  162.     grid rowconfigure $_interior 0 -weight 1
  163.     grid columnconfigure $_interior 0 -weight 1
  164.     
  165.     # 
  166.     # Configure the command on the vertical scroll bar in the base class.
  167.     #
  168.     $itk_component(vertsb) configure \
  169.     -command [itcl::code $itk_component(listbox) yview]
  170.  
  171.     #
  172.     # Configure the command on the horizontal scroll bar in the base class.
  173.     #
  174.     $itk_component(horizsb) configure \
  175.         -command [itcl::code $itk_component(listbox) xview]
  176.     
  177.     # 
  178.     # Create a set of bindings for monitoring the selection and install
  179.     # them on the listbox component.
  180.     #
  181.     foreach seq $singleSelectSeq {
  182.         bind SLBSelect$this $seq [itcl::code $this _makeSelection]
  183.     }
  184.  
  185.     foreach seq $doubleSelectSeq {
  186.         bind SLBSelect$this $seq [itcl::code $this _dblclick]
  187.     }
  188.  
  189.     bindtags $itk_component(listbox) \
  190.             [linsert [bindtags $itk_component(listbox)] end SLBSelect$this]
  191.  
  192.     #
  193.     # Also create a set of bindings for disabling the scrolledlistbox.
  194.     # Since the command for it is "break", we can drop the $this since
  195.     # they don't need to be unique to the object level.
  196.     #
  197.     if {[bind SLBDisabled] == {}} {
  198.         foreach seq $singleSelectSeq {
  199.             bind SLBDisabled $seq break
  200.         }
  201.  
  202.         bind SLBDisabled <Button-1> break
  203.  
  204.         foreach seq $doubleSelectSeq {
  205.             bind SLBDisabled $seq break
  206.         }
  207.     }
  208.  
  209.     #
  210.     # Initialize the widget based on the command line options.
  211.     #
  212.     eval itk_initialize $args
  213. }
  214.  
  215. # ------------------------------------------------------------------
  216. #                           DESTURCTOR
  217. # ------------------------------------------------------------------
  218. itcl::body iwidgets::Scrolledlistbox::destructor {} {
  219. }
  220.  
  221. # ------------------------------------------------------------------
  222. #                             OPTIONS
  223. # ------------------------------------------------------------------
  224.  
  225. # ------------------------------------------------------------------
  226. # OPTION: -dblclickcommand
  227. #
  228. # Specify a command to be executed upon double click of a listbox 
  229. # item.  Also, create a couple of bindings used for specific
  230. # selection modes
  231. # ------------------------------------------------------------------
  232. itcl::configbody iwidgets::Scrolledlistbox::dblclickcommand {}
  233.  
  234. # ------------------------------------------------------------------
  235. # OPTION: -selectioncommand
  236. #
  237. # Specifies a command to be executed upon selection of a listbox 
  238. # item.  The command will be called upon each selection regardless 
  239. # of selection mode..
  240. # ------------------------------------------------------------------
  241. itcl::configbody iwidgets::Scrolledlistbox::selectioncommand {}
  242.  
  243. # ------------------------------------------------------------------
  244. # OPTION: -width
  245. #
  246. # Specifies the width of the scrolled list box as an entire unit.
  247. # The value may be specified in any of the forms acceptable to 
  248. # Tk_GetPixels.  Any additional space needed to display the other
  249. # components such as margins and scrollbars force the listbox
  250. # to be compressed.  A value of zero along with the same value for 
  251. # the height causes the value given for the visibleitems option 
  252. # to be applied which administers geometry constraints in a different
  253. # manner.
  254. # ------------------------------------------------------------------
  255. itcl::configbody iwidgets::Scrolledlistbox::width {
  256.     if {$itk_option(-width) != 0} {
  257.         set shell [lindex [grid info $itk_component(listbox)] 1]
  258.  
  259.         #
  260.         # Due to a bug in the tk4.2 grid, we have to check the 
  261.         # propagation before setting it.  Setting it to the same
  262.         # value it already is will cause it to toggle.
  263.         #
  264.         if {[grid propagate $shell]} {
  265.             grid propagate $shell no
  266.         }
  267.     
  268.         $itk_component(listbox) configure -width 1
  269.         $shell configure \
  270.                 -width [winfo pixels $shell $itk_option(-width)] 
  271.     } else {
  272.         configure -visibleitems $itk_option(-visibleitems)
  273.     }
  274. }
  275.  
  276. # ------------------------------------------------------------------
  277. # OPTION: -height
  278. #
  279. # Specifies the height of the scrolled list box as an entire unit.
  280. # The value may be specified in any of the forms acceptable to 
  281. # Tk_GetPixels.  Any additional space needed to display the other
  282. # components such as margins and scrollbars force the listbox
  283. # to be compressed.  A value of zero along with the same value for 
  284. # the width causes the value given for the visibleitems option 
  285. # to be applied which administers geometry constraints in a different
  286. # manner.
  287. # ------------------------------------------------------------------
  288. itcl::configbody iwidgets::Scrolledlistbox::height {
  289.     if {$itk_option(-height) != 0} {
  290.         set shell [lindex [grid info $itk_component(listbox)] 1]
  291.  
  292.         #
  293.         # Due to a bug in the tk4.2 grid, we have to check the 
  294.         # propagation before setting it.  Setting it to the same
  295.         # value it already is will cause it to toggle.
  296.         #
  297.         if {[grid propagate $shell]} {
  298.             grid propagate $shell no
  299.         }
  300.     
  301.         $itk_component(listbox) configure -height 1
  302.         $shell configure \
  303.                 -height [winfo pixels $shell $itk_option(-height)] 
  304.     } else {
  305.         configure -visibleitems $itk_option(-visibleitems)
  306.     }
  307. }
  308.  
  309. # ------------------------------------------------------------------
  310. # OPTION: -visibleitems
  311. #
  312. # Specified the widthxheight in characters and lines for the listbox.
  313. # This option is only administered if the width and height options
  314. # are both set to zero, otherwise they take precedence.  With the
  315. # visibleitems option engaged, geometry constraints are maintained
  316. # only on the listbox.  The size of the other components such as 
  317. # labels, margins, and scrollbars, are additive and independent, 
  318. # effecting the overall size of the scrolled list box.  In contrast,
  319. # should the width and height options have non zero values, they
  320. # are applied to the scrolled list box as a whole.  The listbox 
  321. # is compressed or expanded to maintain the geometry constraints.
  322. # ------------------------------------------------------------------
  323. itcl::configbody iwidgets::Scrolledlistbox::visibleitems {
  324.     if {[regexp {^[0-9]+x[0-9]+$} $itk_option(-visibleitems)]} {
  325.         if {($itk_option(-width) == 0) && \
  326.                 ($itk_option(-height) == 0)} {
  327.             set chars [lindex [split $itk_option(-visibleitems) x] 0]
  328.             set lines [lindex [split $itk_option(-visibleitems) x] 1]
  329.         
  330.             set shell [lindex [grid info $itk_component(listbox)] 1]
  331.  
  332.             #
  333.             # Due to a bug in the tk4.2 grid, we have to check the 
  334.             # propagation before setting it.  Setting it to the same
  335.             # value it already is will cause it to toggle.
  336.             #
  337.             if {! [grid propagate $shell]} {
  338.                 grid propagate $shell yes
  339.             }
  340.         
  341.             $itk_component(listbox) configure -width $chars -height $lines
  342.         }
  343.     
  344.     } else {
  345.         error "bad visibleitems option\
  346.                 \"$itk_option(-visibleitems)\": should be\
  347.         widthxheight"
  348.     }
  349. }
  350.  
  351. # ------------------------------------------------------------------
  352. # OPTION: -state
  353. #
  354. # Specifies the state of the scrolledlistbox which may be either
  355. # disabled or normal.  In a disabled state, the scrolledlistbox 
  356. # does not accept user selection.  The default is normal.
  357. # ------------------------------------------------------------------
  358. itcl::configbody iwidgets::Scrolledlistbox::state {
  359.     set tags [bindtags $itk_component(listbox)]
  360.  
  361.     #
  362.     # If the state is normal, then we need to remove the disabled 
  363.     # bindings if they exist.  If the state is disabled, then we need
  364.     # to install the disabled bindings if they haven't been already.
  365.     #
  366.     switch -- $itk_option(-state) {
  367.         normal {
  368.                 $itk_component(listbox) configure \
  369.                     -foreground $itk_option(-foreground)
  370.                 $itk_component(listbox) configure \
  371.                     -selectforeground $itk_option(-selectforeground)
  372.             if {[set index [lsearch $tags SLBDisabled]] != -1} {
  373.                 bindtags $itk_component(listbox) \
  374.                         [lreplace $tags $index $index]
  375.             }
  376.         }
  377.  
  378.         disabled {
  379.                 $itk_component(listbox) configure \
  380.                     -foreground $itk_option(-disabledforeground)
  381.                 $itk_component(listbox) configure \
  382.                     -selectforeground $itk_option(-disabledforeground)
  383.             if {[set index [lsearch $tags SLBDisabled]] == -1} {
  384.                 bindtags $itk_component(listbox) \
  385.                         [linsert $tags 1 SLBDisabled]
  386.             }
  387.         }
  388.         default {
  389.             error "bad state value \"$itk_option(-state)\":\
  390.                     must be normal or disabled"
  391.         }
  392.     }
  393. }
  394.  
  395. # ------------------------------------------------------------------
  396. #                            METHODS
  397. # ------------------------------------------------------------------
  398.  
  399. # ------------------------------------------------------------------
  400. # METHOD: curselection 
  401. #
  402. # Returns a list containing the indices of all the elements in the 
  403. # listbox that are currently selected.
  404. # ------------------------------------------------------------------
  405. itcl::body iwidgets::Scrolledlistbox::curselection {} {
  406.     return [$itk_component(listbox) curselection]
  407. }
  408.  
  409. # ------------------------------------------------------------------
  410. # METHOD: activate index
  411. #
  412. # Sets the active element to the one indicated by index.
  413. # ------------------------------------------------------------------
  414. itcl::body iwidgets::Scrolledlistbox::activate {index} {
  415.     return [$itk_component(listbox) activate [_fixIndex $index]]
  416. }
  417.  
  418. # ------------------------------------------------------------------
  419. # METHOD: bbox index
  420. #
  421. # Returns four element list describing the bounding box for the list
  422. # item at index
  423. # ------------------------------------------------------------------
  424. itcl::body iwidgets::Scrolledlistbox::bbox {index} {
  425.     return [$itk_component(listbox) bbox [_fixIndex $index]]
  426. }
  427.  
  428. # ------------------------------------------------------------------
  429. # METHOD clear 
  430. #
  431. # Clear the listbox area of all items.
  432. # ------------------------------------------------------------------
  433. itcl::body iwidgets::Scrolledlistbox::clear {} {
  434.     delete 0 end
  435. }
  436.  
  437. # ------------------------------------------------------------------
  438. # METHOD: see index
  439. #
  440. # Adjusts the view such that the element given by index is visible.
  441. # ------------------------------------------------------------------
  442. itcl::body iwidgets::Scrolledlistbox::see {index} {
  443.     $itk_component(listbox) see [_fixIndex $index]
  444. }
  445.  
  446. # ------------------------------------------------------------------
  447. # METHOD: index index
  448. #
  449. # Returns the decimal string giving the integer index corresponding 
  450. # to index.  The index value may be a integer number, active,
  451. # anchor, end, @x,y, or a pattern.
  452. # ------------------------------------------------------------------
  453. itcl::body iwidgets::Scrolledlistbox::index {index} {
  454.     if {[regexp {(^[0-9]+$)|(^active$)|(^anchor$)|(^end$)|(^@-?[0-9]+,-?[0-9]+$)} $index]} {
  455.     return [$itk_component(listbox) index $index]
  456.     
  457.     } else {
  458.         set indexValue [lsearch -glob [get 0 end] $index]
  459.         if {$indexValue == -1} {
  460.             error "bad Scrolledlistbox index \"$index\": must be active,\
  461.                     anchor, end, @x,y, number, or a pattern"
  462.         }
  463.         return $indexValue
  464.     }
  465. }
  466.  
  467. # ------------------------------------------------------------------
  468. # METHOD: _fixIndex index
  469. #
  470. # Similar to the regular "index" method, but it only converts
  471. # the index to a numerical value if it is a string pattern.  If
  472. # the index is in the proper form to be used with the listbox,
  473. # it is left alone.  This fixes problems associated with converting
  474. # an index such as "end" to a numerical value.
  475. # ------------------------------------------------------------------
  476. itcl::body iwidgets::Scrolledlistbox::_fixIndex {index} {
  477.     if {[regexp {(^[0-9]+$)|(^active$)|(^anchor$)|(^end$)|(^@[0-9]+,[0-9]+$)} \
  478.             $index]} {
  479.         return $index
  480.  
  481.     } else {
  482.         set indexValue [lsearch -glob [get 0 end] $index]
  483.  
  484.         if {$indexValue == -1} {
  485.             error "bad Scrolledlistbox index \"$index\": must be active,\
  486.                     anchor, end, @x,y, number, or a pattern"
  487.         }
  488.         return $indexValue
  489.     }
  490. }
  491.  
  492. # ------------------------------------------------------------------
  493. # METHOD: delete first ?last?
  494. #
  495. # Delete one or more elements from list box based on the first and 
  496. # last index values.  Indexes may be a number, active, anchor, end,
  497. # @x,y, or a pattern.
  498. # ------------------------------------------------------------------
  499. itcl::body iwidgets::Scrolledlistbox::delete {first {last {}}} {
  500.     set first [_fixIndex $first]
  501.     
  502.     if {$last != {}} {
  503.         set last [_fixIndex $last]
  504.     } else {
  505.         set last $first
  506.     }
  507.     
  508.     eval $itk_component(listbox) delete $first $last
  509. }
  510.  
  511. # ------------------------------------------------------------------
  512. # METHOD: get first ?last?
  513. #
  514. # Returns the elements of the listbox indicated by the indexes. 
  515. # Indexes may be a number, active, anchor, end, @x,y, ora pattern.
  516. # ------------------------------------------------------------------
  517. itcl::body iwidgets::Scrolledlistbox::get {first {last {}}} {
  518.     set first [_fixIndex $first]
  519.     
  520.     if {$last != {}} {
  521.         set last [_fixIndex $last]
  522.     }
  523.     
  524.     if {$last == {}} {
  525.         return [$itk_component(listbox) get $first]
  526.     } else {
  527.         return [$itk_component(listbox) get $first $last]
  528.     }
  529. }
  530.  
  531. # ------------------------------------------------------------------
  532. # METHOD: getcurselection 
  533. #
  534. # Returns the contents of the listbox element indicated by the current 
  535. # selection indexes.  Short cut version of get and curselection 
  536. # command combination.
  537. # ------------------------------------------------------------------
  538. itcl::body iwidgets::Scrolledlistbox::getcurselection {} {
  539.     set rlist {}
  540.  
  541.     if {[selecteditemcount] > 0} {
  542.         set cursels [$itk_component(listbox) curselection]
  543.     
  544.         switch $itk_option(-selectmode) {
  545.             single -
  546.             browse {
  547.                 set rlist [$itk_component(listbox) get $cursels]
  548.             }
  549.  
  550.             multiple -
  551.             extended {
  552.                 foreach sel $cursels {
  553.                     lappend rlist [$itk_component(listbox) get $sel]
  554.                 }
  555.             }
  556.         }
  557.     }
  558.     
  559.     return $rlist
  560. }
  561.  
  562. # ------------------------------------------------------------------
  563. # METHOD: insert index string ?string ...?
  564. #
  565. # Insert zero or more elements in the list just before the element 
  566. # given by index.
  567. # ------------------------------------------------------------------
  568. itcl::body iwidgets::Scrolledlistbox::insert {index args} {
  569.     set index [_fixIndex $index]
  570.  
  571.     eval $itk_component(listbox) insert $index $args
  572. }
  573.  
  574. # ------------------------------------------------------------------
  575. # METHOD: nearest y
  576. #
  577. # Given a y-coordinate within the listbox, this command returns the 
  578. # index of the visible listbox element nearest to that y-coordinate.
  579. # ------------------------------------------------------------------
  580. itcl::body iwidgets::Scrolledlistbox::nearest {y} {
  581.     $itk_component(listbox) nearest $y
  582. }
  583.  
  584. # ------------------------------------------------------------------
  585. # METHOD: scan option args 
  586. #
  587. # Implements scanning on listboxes.
  588. # ------------------------------------------------------------------
  589. itcl::body iwidgets::Scrolledlistbox::scan {option args} {
  590.     eval $itk_component(listbox) scan $option $args
  591. }
  592.  
  593. # ------------------------------------------------------------------
  594. # METHOD: selection option first ?last?
  595. #
  596. # Adjusts the selection within the listbox.  The index value may be 
  597. # a integer number, active, anchor, end, @x,y, or a pattern.
  598. # ------------------------------------------------------------------
  599. itcl::body iwidgets::Scrolledlistbox::selection {option first {last {}}} {
  600.     set first [_fixIndex $first]
  601.     
  602.     if {$last != {}} {
  603.         set last [_fixIndex $last]
  604.         $itk_component(listbox) selection $option $first $last
  605.     } else {
  606.         $itk_component(listbox) selection $option $first 
  607.     }
  608. }
  609.  
  610. # ------------------------------------------------------------------
  611. # METHOD: size 
  612. #
  613. # Returns a decimal string indicating the total number of elements 
  614. # in the listbox.
  615. # ------------------------------------------------------------------
  616. itcl::body iwidgets::Scrolledlistbox::size {} {
  617.     return [$itk_component(listbox) size]
  618. }
  619.  
  620. # ------------------------------------------------------------------
  621. # METHOD: selecteditemcount 
  622. #
  623. # Returns a decimal string indicating the total number of selected 
  624. # elements in the listbox.
  625. # ------------------------------------------------------------------
  626. itcl::body iwidgets::Scrolledlistbox::selecteditemcount {} {
  627.     return [llength [$itk_component(listbox) curselection]]
  628. }
  629.  
  630. # ------------------------------------------------------------------
  631. # METHOD: justify direction
  632. #
  633. # Justifies the list scrolled region in one of four directions: top,
  634. # bottom, left, or right.
  635. # ------------------------------------------------------------------
  636. itcl::body iwidgets::Scrolledlistbox::justify {direction} {
  637.     switch $direction {
  638.         left { 
  639.             $itk_component(listbox) xview moveto 0
  640.         }
  641.         right {
  642.             $itk_component(listbox) xview moveto 1
  643.         }
  644.         top {
  645.             $itk_component(listbox) yview moveto 0
  646.         }
  647.         bottom {
  648.             $itk_component(listbox) yview moveto 1
  649.         }
  650.         default {
  651.             error "bad justify argument \"$direction\": should\
  652.                 be left, right, top, or bottom"
  653.         }
  654.     }
  655. }
  656.  
  657. # ------------------------------------------------------------------
  658. # METHOD: sort mode
  659. #
  660. # Sort the current list. This can take any sort switch from
  661. # the lsort command: ascii, integer, real, command, 
  662. # increasing/ascending, decreasing/descending, etc.
  663. #     
  664. # ------------------------------------------------------------------
  665. itcl::body iwidgets::Scrolledlistbox::sort {{mode ascending}} {
  666.  
  667.     set vals [$itk_component(listbox) get 0 end]
  668.     if {[llength $vals] == 0} {return}
  669.  
  670.     switch $mode {
  671.         ascending   {set mode increasing}
  672.         descending  {set mode decreasing}
  673.     }
  674.  
  675.     $itk_component(listbox) delete 0 end
  676.     if {[catch {eval $itk_component(listbox) insert end \
  677.             [lsort -${mode} $vals]} errorstring]} {
  678.         error "bad sort argument \"$mode\": must be a valid argument to the\
  679.                 Tcl lsort command"
  680.     }
  681.  
  682.     return
  683. }
  684.  
  685. # ------------------------------------------------------------------
  686. # METHOD: xview args
  687. #
  688. # Change or query the vertical position of the text in the list box.
  689. # ------------------------------------------------------------------
  690. itcl::body iwidgets::Scrolledlistbox::xview {args} {
  691.     return [eval $itk_component(listbox) xview $args]
  692. }
  693.  
  694. # ------------------------------------------------------------------
  695. # METHOD: yview args
  696. #
  697. # Change or query the horizontal position of the text in the list box.
  698. # ------------------------------------------------------------------
  699. itcl::body iwidgets::Scrolledlistbox::yview {args} {
  700.     return [eval $itk_component(listbox) yview $args]
  701. }
  702.  
  703. # ------------------------------------------------------------------
  704. # METHOD: itemconfigure args
  705. #
  706. # This is a wrapper method around the new tk8.3 itemconfigure command
  707. # for the listbox.
  708. # ------------------------------------------------------------------
  709. itcl::body iwidgets::Scrolledlistbox::itemconfigure {args} {
  710.     return [eval $itk_component(listbox) itemconfigure $args]
  711. }
  712.  
  713. # ------------------------------------------------------------------
  714. # PROTECTED METHOD: _makeSelection 
  715. #
  716. # Evaluate the selection command.
  717. # ------------------------------------------------------------------
  718. itcl::body iwidgets::Scrolledlistbox::_makeSelection {} {
  719.     uplevel #0 $itk_option(-selectioncommand)
  720. }
  721.  
  722. # ------------------------------------------------------------------
  723. # PROTECTED METHOD: _dblclick 
  724. #
  725. # Evaluate the double click command option if not empty.
  726. # ------------------------------------------------------------------
  727. itcl::body iwidgets::Scrolledlistbox::_dblclick {} {
  728.     uplevel #0 $itk_option(-dblclickcommand)
  729. }   
  730.  
  731.