How to implement tk scrollbar for multiple listboxes (TCL)? - windows

I tried all sort of options but no success in implement simple scrollbar for two or more listboxes. Following is my code giving error while scrolling. I hope you guys are helping me...
scrollbar .scroll -orient v
pack .scroll -side left -fill y
listbox .lis1
pack .lis1 -side left
listbox .lis2
pack .lis2 -side left
for {set x 0} {$x < 100} {incr x} {
.lis1 insert end $x
.lis2 insert end $x
}
.lis1 configure -yscrollcommand [list .scroll set]
.lis2 configure -yscrollcommand [list .scroll set]
.scroll configure -command ".lis1 yview .lis2 yview ";
thanking you.

There are a number of examples on the Tcler's wiki, but the core principle is to use a procedure to ensure that the scrolling protocol is synchronized between the widgets. Here's an example based off that wiki page:
# Some data to scroll through
set ::items [lrepeat 10 {*}"The quick brown fox jumps over the lazy dog."]
# Some widgets that will scroll together
listbox .list1 -listvar ::items -yscrollcommand {setScroll .scroll}
listbox .list2 -listvar ::items -yscrollcommand {setScroll .scroll}
scrollbar .scroll -orient vertical -command {synchScroll {.list1 .list2} yview}
# The connectors
proc setScroll {s args} {
$s set {*}$args
{*}[$s cget -command] moveto [lindex [$s get] 0]
}
proc synchScroll {widgets args} {
foreach w $widgets {$w {*}$args}
}
# Put the GUI together
pack .list1 .scroll .list2 -side left -fill y
It's worth noting that you can also plug any other scrollable widget into this scheme; everything in Tk scrolls the same way (except with -xscrollcommand and xview for horizontal scrolling, together with a change of scrollbar orientation). Furthermore, the connectors here, unlike the ones on the wiki page, can be used with multiple groups of scrolled widgets at once; the knowledge of what is scrolled together is stored in the -command option of the scrollbar (first argument to synchScroll callback).
[EDIT]: For 8.4 and before, you need slightly different connector procedures:
# The connectors
proc setScroll {s args} {
eval [list $s set] $args
eval [$s cget -command] [list moveto [lindex [$s get] 0]]
}
proc synchScroll {widgets args} {
foreach w $widgets {eval [list $w] $args}
}
Everything else will be the same.

I know that this post is really old but I recently discovered what I think is a fairly simple solution. Instead of using the vertical scrollbar I found that I can use the slider widget. With the slider you can get the position of the slider and use that to set the yview of the listbox(es). Multiple listboxes can be scrolled simultaneously. I use vtcl to build the GUI so the code I can provide may not beimmediately obvious for those using tk wm comands. But here is the code I use. It is bound to slider motion.
set listIndex [$widget(Scale1) get]
$widget(Listbox1) yview $listIndex
$widget(Listbox2) yview $listIndex
Hope that is helpful to somebody.

If you plan to do much work in the the callback command - make a procedure to do it as that is both faster (the procedure gets byte compiled) and less likely to introduce tcl syntax problems. In this case you are trying to perform two tcl commands in the scrollbar function so you need to separate the statements using newline or a semicolon.
Calling the scrollbar set function from both listboxes will just have the second one override the first. You either need a function to merge those two or if the lists have the same lengths, just call it from one of them to set the scrollbar size and position and then update all listboxes with the scrollbar callback.
There is a multilistbox package somewhere - try the Tcl wiki to locate examples.

Related

Dropdown menu button in tcl/tk

Is there any way to create a drop down toolbar button(Like Paste button in MS Word) using Tcl/TK?.I have googled a lot but nothing found.Any help will be appreciable.
You probably want to use a menubutton and a menu, probably with radiobutton entries if I've understood which UI element in Word you're talking about. (Or maybe a ttk::menubutton and menu.) Now, if you're doing something very simple with it then you can make do with just tk_optionMenu as a way to combine those commands, but that's just a simple procedure; if you're doing something complicated with the menu, it's probably easier to write it yourself or at least to get the code for tk_optionMenu and to customise it how you want it to work.
The source code for tk_optionMenu isn't very long; I'll paste the non-comment parts of it here:
proc ::tk_optionMenu {w varName firstValue args} {
upvar #0 $varName var
if {![info exists var]} {
set var $firstValue
}
menubutton $w -textvariable $varName -indicatoron 1 -menu $w.menu \
-relief raised -highlightthickness 1 -anchor c \
-direction flush
menu $w.menu -tearoff 0
$w.menu add radiobutton -label $firstValue -variable $varName
foreach i $args {
$w.menu add radiobutton -label $i -variable $varName
}
return $w.menu
}
You probably want to pay attention to how the menubutton and menu are connected to each other. ttk::menubutton is mostly a drop-in replacement for menubutton, except for different look-and-feel configuration options.

Create new window in tcl/tk

How can i create a same gui every time by clicking the button without closing current one?
wm title . "abcd"
wm geometry . 50x50
pack [button .b -text "new"]
Please help me.
The toplevel command creates a new window for you to put widgets in. It's a good idea to use a procedure for building the overall GUI in that window:
wm title . "abcd"
wm geometry . 50x50
pack [button .b -text "new" -command makeWindow]
set counter 0
proc makeWindow {} {
# Make a unique widget name
global counter
set w .gui[incr counter]
# Make the toplevel
toplevel $w
wm title $w "This is $w"
# Put a GUI in it
pack [label $w.xmpl -text "This is an example"]
pack [button $w.ok -text OK -command [list destroy $w]]
}
Each of these windows that you make is as independent or dependent on the others as you want. It depends on how you write the code, arrange the variables, design the callbacks, etc.

IUP, menu, webbrowser, tree, tabs

I have such menu situation:
int menu_create(Ihandle *menu)
{
hamburger = IupItem("&Hamburger", "hamburger");
IupSetAttributes(hamburger, "AUTOTOGGLE=YES, RADIO=YES");
char* ce = "Ćev&apčići";
cevapcici = IupItem(utf8_to_cp1250(ce), "cevapcici");
IupSetAttributes(cevapcici, "AUTOTOGGLE=YES, RADIO=YES");
exit = IupItem("Exit\tAlt+F4", "exit");
img4 = IupLoadImage("icons\\delete_16x16.ico");
IupSetAttributeHandle(exit, "TITLEIMAGE", img4);
menu = IupMenu(
IupSubmenu("File",
IupMenu(
hamburger,
cevapcici,
IupSeparator(),
IupItem("Carro&t", "carrot"),
IupSeparator(),
exit,
NULL)),
NULL);
IupSetFunction("exit", (Icallback)mnu_exit);
... etc...
IupSetHandle("menu", menu);
return IUP_DEFAULT;
}
How to get "radio toggle group" functionality with items hamburger and cevapcici so first turns off a second checkmark and opposite. This is my try but it don't work.
2) I try webbrowser example from IUP suite on my windows 7. Problem is that bad black flickering appear's during resize (increase). Also, background of webbrowser flicker black during showing.
I try a same example on Ubuntu and there flickering appear's too but it is not so much visible since background is there white.
Is here any way to get rid of those flickering or if not to get white background of webbrowser window on windows?
3) Since webbrowser is ole object (on windows) is it possible to use say "print preview" or "zoom" function by reference from IUP handle or at any other way like we used to do from MS programming tools?
wbInstance.ExecWB(Exec.OLECMDID_OPTICAL_ZOOM, ExecOpt.OLECMDEXECOPT_DONTPROMPTUSER, 150, DBNull.Value)
4) How can I get key_up event fired from IupTree?
5) Interesting situation with IupTabs:
frame3 = IupHbox(mat, val, NULL);
vboxt1 = IupVbox(frame3, NULL);
vboxt2 = IupVbox(frame3, NULL);
IupSetAttribute(vboxt1, "TABTITLE", "First documents... ");
IupSetAttribute(vboxt2, "TABTITLE", "Second documents... ");
tabs = IupTabs(vboxt1, vboxt2, NULL);
hbox1 = IupHbox(tabs, IupVbox(frame, tree, frame2, NULL), NULL);
dlg = IupDialog(hbox1);
When I set frame3 which should be a same for both tabs my GUI frozes.
However, I have to got same "mat" (IupMatrix) in both tabs because by changing tabs other data load in matrix but similar enough to use same matrix and related functions.
What to do here?
1) The RADIO attribute belongs to the IupMenu, not to the IupItem. This also means that all the IupItems inside that menu will be part of the radio.
A workaround would be to manually unset the other toggle inside the action callback.
2) That flicker is not caused by IUP. Don't know why the native controls are doing it.
3) Yes, but you will have to program that using the OLE API. If you take a look at the IupOleControl and IupWebBrower source code and send me the code to do it, I will be happy to add it to IUP.
4) You don't. Use the K_ANY callbacks.
5) You can not reuse a control in different places in any dialog. So you must have two different frames, with two different matrices. What you can do is to encapsulate your matrix, so the same function will create a matrix with the same attributes and callbacks any time you want one.

Insert progressbar into statusbar panel using powershell and windows forms

I am currently working on a project that requires me to put a progressbar in one of the panels of a statusbar. Does anyone have any experience with this, or can anyone provide any input or direction on how it is done. I have been searching for 2 days now for a solution with no luck. There is still not an abundance of powershell help out there, especially when it comes to windows forms.
This is relatively simple to do with PowerShell data sources in WPK.
You can get WPK as part of the PowerShellPack.
Here's a pretty decent progress viewer written in WPK:
New-Grid -Columns 2 {
New-TextBlock -Margin 10 -TextWrapping Wrap -ZIndex 1 -HorizontalAlignment Left -FontWeight Bold -FontSize 12 -DataBinding #{
"Text" = "LastProgress.Activity"
}
New-TextBlock -Margin 10 -ZIndex 1 -TextWrapping Wrap -Column 1 -VerticalAlignment Bottom -HorizontalAlignment Right -FontStyle Italic -FontSize 12 -DataBinding #{
"Text" = "LastProgress.StatusDescription"
}
New-ProgressBar -ColumnSpan 2 -MinHeight 250 -Name ProgressPercent -DataBinding #{
"Value" = "LastProgress.PercentComplete"
}
} -DataContext {
Get-PowerShellDataSource -Script {
foreach ($n in 1..100) {
Write-Progress "MajorProgress" "MinorProgress" -PercentComplete $n
Start-Sleep -Milliseconds 250
}
}
} -AsJob
The PowerShellDataSource returns an object with a list of all of the outputs for a given stream and the last item outputted on the given stream (i.e. Progress and LastProgress). In order to display the progress bar, we need bind to the LastProgress property.
The first half of the code declares the progress bar. By using the -DataBinding parameter the TextBlocks and Progress bars will automatically sync to the data context. Data context can either be declared at this level (as is shown in the example) or can be in a parent control.
The DataContext in this example is a simple PowerShell script that uses Write-Progress to output a test message every quarter second, but you can use any script you'd like.
Hope this helps.

How to position editbox's cursor in shoes?

Shoes is very handy GUI tool. I would like to do a search form so that a user is helped to navigate through larger texts for editing. For this I need to move the cursor within an editbox element.
Here you'll see my question in code:
Shoes.app do
stack do
p=para "After pressing 'search' a question will arise"
box=edit_box
box.text="One\nof\nthe\nmost\nstriking\ndifferences\nbetween\na\ncat\nand\na\nlie\nis\nthat\na\ncat\nhas\nonly\nnine lives."
flow :margin_top=>0.1 do
search=edit_line
button("search") do
pos=box.text.index search.text
y = box.text[0..pos].split.size-1 if pos
if not y.nil?
#For example if you searched "only" then
#cursor should jump/scroll to line 17.
#
#Anything there for cursor positioning,
#like: box.cursor=[0,y]
#
p.text="How can I move editbox's cursor in line #{y+1}?"
else
alert "'#{search.text}' not found"
end
end
end
end
end
Is there is any way to change cursor's position of an editbox? If not, do you know an alternative way of implementation?
Unfortunately, Shoes doesn't seem to provide any way to do that. These are the only methods defined on EditBox (it inherits from Native, which has several methods, but again, none to reposition the cursor).
rb_define_method(cEditBox, "text", CASTHOOK(shoes_edit_box_get_text), 0);
rb_define_method(cEditBox, "text=", CASTHOOK(shoes_edit_box_set_text), 1);
rb_define_method(cEditBox, "draw", CASTHOOK(shoes_edit_box_draw), 2);
rb_define_method(cEditBox, "change", CASTHOOK(shoes_control_change), -1);
http://github.com/why/shoes/blob/cea39a8bf9a5b7057b1824a9fab868d1f8609d69/shoes/ruby.c

Resources