My code now runs as expected. I had to add a global variable to check if the callback is invoked on the same checkbutton twice in a row.
Code below.
There is one last question remaining.
If the contaning frame has no space arround the checkbuttons, the <<Swipe>> event cannot be executed. Somehow, the binding does not work on the checkbutton itself.
So either I find a way to propagate the event from the button to the containing frame, or I add another binding to the buttons, or I must make sure the frame has some extra empty space for the clicks.
set ::lastcheckbutton ""
destroy .test
toplevel .test
pack [frame .test.f] -side left -expand 1 -fill both
pack [ttk::checkbutton .test.f.b1 -style Toolbutton -text test] -side right -expand 0 -fill x
pack [ttk::checkbutton .test.f.b2 -style Toolbutton -text test] -side right -expand 0 -fill x
pack [ttk::checkbutton .test.f.b3 -style Toolbutton -text test] -side right -expand 0 -fill x
event add <<Swipe>> <B1-Motion>
foreach w {.test.f} {
bind $w <<Swipe>> {::SwipeCallback %X %Y}
}
proc ::SwipeCallback {rootX rootY} {
variable lastcheckbutton
set w [winfo containing $rootX $rootY]
if {$w==""} {
return
}
if {[winfo class $w]=="TCheckbutton" && $lastcheckbutton!=$w} {
$w invoke
set lastcheckbutton $w
}
}