rtcltk-toolkittcltk

Is there a way to specify tcltk version within R?


I was asked if I could "fix" the R script that was created in version 3.2.2 that ceased to work in version 4.2.2.

The script turned out to be Tcl/tk interface using tcltk package. The script starts with tclRequire("BWidget") and tclRequire("Tktable"). GUI it produce is basically,

  1. import csv
  2. select one of column using drop-down
  3. second drop-down menu shows the levels of the above column
  4. do analysis

The problem occurs in number 3, where the drop-down menu is just blank with no selection available when using more recent R version.

While using a same system (Window OS), when using R version 3.2.2, it returns

> tclRequire("BWidget")
<Tcl> 1.8
> tclRequire("Tktable")
<Tcl> 2.9

while using R version 4.2.2 returns

> tclRequire("BWidget")
<Tcl> 1.9.15
> tclRequire("Tktable")
<Tcl> 2.10

It's my first time hearing what Tcl/Tk is, and it seemed the discrepancy in Tcl is the culprit, not the R per se.

I read https://stat.ethz.ch/R-manual/R-devel/library/tcltk/html/TclInterface.html and tried to play around with

addTclPath(path = ".")
tclRequire(package, warn = TRUE)
tclVersion()

but wasn't sure how to do it properly.

Is there a way to specify Tcl to 1.8 and 2.9 even when I am using other version of R?


Solution

  • 1) One way to do this is to replace the contents of the BWidget directory in your R installation with the old one. On Windows you can find it at R.home("Tcl/lib/BWidget").

    2) A different approach is to add a directory containing the bWidget tree to your path.

    Assume that the old BWidget is version 1.9.9 located in C:/PROGRA~1/R/R-3.5.2patched/Tcl/lib which is where they are on my system. Change as needed. In particular you may wish to create a new directory and just place BWidget and TkTable trees under it.

    Then run this R code. First add the indicated directory. Then make sure that the system forgets about BWidget in case it has already been set. Finally load the needed version of BWidget.

    library(tcltk)
    
     addTclPath("C:/PROGRA~1/R/R-3.5.2patched/Tcl/lib")
    .Tcl("package forget BWidget")
    .Tcl("package require -exact BWidget 1.9.9") # this should reply with 1.9.9 
    

    Also note these commands:

     as.character(tcl("set", "auto_path")) # shows path elements
     as.character(tcl("package", "name")) # shows tcl packages
     tcl("package", "provide", "BWidget") # show BWidget version being used
    

    For more information on the tcl package command see: https://www.tcl.tk/man/tcl/TclCmd/package.html

    3) Another approach is to determine the differences in the two versions of BWidget and fix your program. The free winmerge program on Windows is good for comparing two directories. At the Windows cmd line (change directories as needed):

    winmergeu C:/PROGRA~1/R/R-3.5.2patched/Tcl/lib/BWidget C:/PROGRA~1/R/R-4.2/Tcl/lib/BWidget
    

    Update

    Have made some improvements. Seems we don't need to insert new lib at the beginning -- putting it at end is sufficient -- as long as we specify the particular version that we want.