mieki256's diary



2023/10/20(金) [n年前の日記]

#1 [ruby][python] Ruby/TkをWindows10上で試用

Windows10 x64 22H2上で Ruby/Tk を動かしてみたい。

Ruby 1.9.3 x86 であればTk拡張まで含めた Ruby/Tk を動かせることは分かったのだけど…。以前試した際の作業メモが残ってた。

_mieki256's diary - Ruby/Tkで拡張Tkを使えるようにするために少し試したり


Ruby 2.x.x 以降で、ActiveTcl を導入せずに Ruby/Tk を動かす方法はないのかなとググっていたら、気になる話を見かけた。

_イマドキ(2018)のWindows版のRubyでrequire 'tk'してエラーにならないようにするには #Ruby - Qiita

Windows環境でもtkパッケージをインストーするだけで動いたとの話。マジ?

自分も試しに、以下の環境で Tk をインストールしてみた。
gem install tk
> ruby --version
ruby 2.6.10p210 (2022-04-12 revision 67958) [i386-mingw32]

> gem install tk
Fetching tk-0.4.0.gem
Temporarily enhancing PATH for MSYS/MINGW...
Using msys2 packages: mingw-w64-i686-tk
Building native extensions. This could take a while...
Successfully installed tk-0.4.0
Parsing documentation for tk-0.4.0
Installing ri documentation for tk-0.4.0
Done installing documentation for tk after 12 seconds
1 gem installed

ビルドが走って、tk 0.4.0 がインストールされた。

この状態で、hello world系の簡単なRuby/Tk使用スクリプトを実行してみたところ、本当に動いてしまった…。ActiveTcl はインストールしてない環境なのに…。おそらく基本機能だけなら動くということだろうけど、まさかこんなにも簡単にインストールできる状態になっていたとは…。もっと面倒臭い作業が必要なのかと思い込んでた…。

ただ、Ruby 2.6.10 x86、3.0.4 x86 + Tk 0.4.0 については特に問題無く動いたけれど、Ruby 3.2.2 x86 + Tk 0.4.0 は実行する度に以下の警告メッセージが表示される。何だろうなコレは…。
> ruby calc.rb
D:/Ruby/Ruby32-x86/lib/ruby/gems/3.2.0/gems/tk-0.4.0/lib/tkutil.so: warning: undefining the allocator of T_DATA class TkUtil::CallbackSubst::Info


さておき。どこらへんに Tcl/Tk 関係が入ってるのか少し調べてみたけれど、Ruby を DevKit付でインストールしたことで、Rubyインストールディレクトリ内に msys32 というディレクトリがあって、そこに MSYS2 関係のファイルが入っていた。その中に、tcl や tk 関連らしいディレクトリやファイルも入っているように見えた。

(Rubyインストールディレクトリ)\msys32\mingw32\bin\tcl86.dll
(Rubyインストールディレクトリ)\msys32\mingw32\bin\tk86.dll
(Rubyインストールディレクトリ)\msys32\mingw32\lib\tcl8.6
(Rubyインストールディレクトリ)\msys32\mingw32\lib\tk8.6
(Rubyインストールディレクトリ)\msys32\usr\lib\tcl8.6

また、以下の場所に、tcltklib.so や tkutil.so もあった。
(Rubyインストールディレクトリ)\lib\ruby\gems\2.6.0\gems\tk-0.4.0\lib\tcltklib.so
(Rubyインストールディレクトリ)\lib\ruby\gems\2.6.0\gems\tk-0.4.0\lib\tkutil.so

MSYS2 が Tcl/Tk関係のファイルを用意してくれるようになって、Ruby/Tk が Windowsでも使えるようになった、という認識でいいのだろうか。

exe化を試した :

ocra を使って exe化できるか試した。ちなみに、Ruby の各バージョンで使える ocra or ocran は以下の通り。
  • Ruby 1.9.3 x86 : ocra 1.3.10
  • Ruby 2.6.10 x86 : ocra 1.3.11
  • Ruby 3.0.4 x86 : ocra 1.3.11
  • Ruby 3.2.2 x86 : ocran 1.3.14 (ocra の fork版。ocra は Ruby 3.1.x 以降で正常動作しない。)

Ruby 1.9.3 x86 の場合は、(Ruby 1.9.3 x86インストールディレクトリ)\lib\tcltk を含めて指定する必要がある。
ocra 03_hello_tk.rb D:\Ruby\Ruby193-x86\lib\tcltk --no-autoload --add-all-core

Ruby 2.6.10 x86, 3.0.4 x86, 3.2.2 x86 は、以下で指定してみた。
ocra 03_hello_tk.rb --no-autoload --add-all-core

exeが生成できて、実行もできた。

出来上がった exe を、他のPCにコピーして、動くかどうか確認してみた。スペックは、CPU Athlon 5350 Quad-Core (2GHz, 4core, TDP 25W)、RAM 4GB、Cドライブ SSD。OS は Windows10 x64 22H2。

Ruby 1.9.3 x86 で生成したexeは、一応動いてくれた。ただ、Hello World 系の、ウインドウとメッセージを表示するだけのプログラムなのに、ウインドウが表示されるまで1分かかった。

Ruby 2.6.10 x86 で生成したexeは、tcltklib.so が見つからないとエラーが出て、実行することはできなかった。しかもそのエラーが出てくるまで、1分10秒かかった。

Ruby 2.6.10 x86 で生成したexeも動くようにしたい。以下の記事が参考になった。

_Ruby ocraでtkを用いたGUIプログラムを実行ファイル化したが、上手く起動できない。
_Problems with tk gem on windows - Issue #131 - larsch/ocra - GitHub

ocra 03_hello_tk.rb D:\Ruby\Ruby26-x86\msys32\usr\bin\msys-2.0.dll D:\Ruby\Ruby26-x86\msys32\mingw32\lib\tcl8.6 D:\Ruby\Ruby26-x86\msys32\lib\tk8.6 --no-autoload --add-all-core --no-lzma --gem-all

要するに、ocra に以下の指定も追加する模様。
(Rubyインストールディレクトリ)\msys32\usr\bin\msys-2.0.dll
(Rubyインストールディレクトリ)\msys32\mingw32\lib\tcl8.6
(Rubyインストールディレクトリ)\msys32\lib\tk8.6
--no-autoload
--add-all-core
--no-lzma
--gem-all

  • --no-lzma をつけてexeを作ると、無圧縮状態でexeを生成するので、展開時間が早くなるはず。実際、Ruby 1.9.3 x86 を使ってexe化したソレは、ウインドウが表示されるまでの待ち時間が、1分から34秒まで短くなった。
  • Ruby 2.6.10 x86 で生成した exe も実行できるようになった。おそらく --gem-all が効いてくれた気がする。しかし、--no-lzma をつけても、ウインドウが表示されるまで1分10秒かかった。

まあ、なんというか、こんなに待たされてしまうとなると、実用的ではないなと…。

余談。Pythonで試してみた :

Python 3.10.10 + tkinter を使っている、Hello World系の、ウインドウとメッセージのみを表示をするPythonスクリプトを、pyinstaller 6.1.0 を使ってexe化して、Ruby/Tk と同様に別PCにコピーして動作確認してみた。

pyinstaller 01_helloworld_tkinter.py

pyinstaller で exe化されたソレは、tkinter のウインドウが表示されるまで、1秒もかからなかった…。

Ruby/Tk なら34秒。Python + tkinter なら1秒…。うーん。

もっとも、pyinstaller はオプションを付けずに実行すると、動作に必要なファイルを展開してある状態で exe を生成するので、おそらくそのあたりがかなり効いているのではなかろうか。これは比較として全くフェアじゃないだろう。

であればと、1つのexeファイルにする --onefile オプションをつけてexe化してみた。
pyinstaller 01_helloworld_tkinter.py --onefile

しかしこの場合も、最初の実行時は10秒、2回目の実行時は5秒ほどで、tkinter のウインドウが表示された。

ローカルで動くGUIアプリをこの手の _LL で作ってexe化して配布するなら、Ruby よりも Python を選んだほうがいいのだなと再認識してしまった…。

ちなみに、メインPC、CPU AMD Ryzen 5 5600X(3.7 - 4.6GHz, 6core), RAM 16GB の環境で Ruby/Tk のソレを動かすと、ウインドウが表示されるまで6〜3秒ぐらいかかる。Python + tkinter は1秒もかからず起動するので、Ruby/Tk を exe化したソレが数倍遅いのは間違いなさそう。

Rubyのソレは、ひょっとするとファイル展開時にCPUパワーを必要としているのだろうか…? であれば、事前にファイルを展開した状態で exe を作れるなら、実用的な起動時間になる可能性がある…? そういうexe化ツールは無いのかな?

実験に使ったスクリプト :


以上、1 日分です。

過去ログ表示

Prev - 2023/10 - Next
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31

カテゴリで表示

検索機能は Namazu for hns で提供されています。(詳細指定/ヘルプ


注意: 現在使用の日記自動生成システムは Version 2.19.6 です。
公開されている日記自動生成システムは Version 2.19.5 です。

Powered by hns-2.19.6, HyperNikkiSystem Project