リンク

2017年6月29日木曜日

pythonでGUIツールを作る 〜SuperToolTip(スーパーツールチップ)〜


今回は「ヘッダー部分」「本文」「フッター部分」の3つを指定することができるツールチップをご紹介します。

ツールチップとは、特定のウィジットにマウスカーソルを合わせた時に、数秒間だけ表示されるメッセージのことです。

通常のツールチップはただ文字列を表示するだけですが、スーパーツールチップは、上に書いたように、3箇所に分けて情報を表示することができ、かつ、それぞれの部分に異なる色を設定し、グラデーションにすることもできます。
さらに、3箇所それぞれに画像を表示させるなど、まさにスーパーな機能がついたツールチップです。

通常のツールチップ



環境
  • macOS Sierra 10.12.5
  • python 3.4
  • wxPython 4.0.0a3


スクリプト
# -*- coding: UTF-8 -*-

import wx
import wx.lib.agw.supertooltip as STT

class App(wx.Frame):
    """ GUI """
    def __init__(self, parent, id, title):
        wx.Frame.__init__(self, parent, id, title, size=(250, 200))

        p = wx.Panel(self, wx.ID_ANY)

        button = wx.Button(p, wx.ID_ANY, "ボタン", pos=(100, 50))

        tip = STT.SuperToolTip(message="素敵なメッセージ\n", header='へっだーぶぶん', footer='ふったーぶぶん')
        tip.SetTarget(button)  # ターゲット
        tip.SetDrawHeaderLine(True)  # ヘッダー部の仕切り線:あり
        tip.SetDrawFooterLine(True)  # フッター部の仕切り線:あり
        tip.SetMiddleGradientColour("yellow")
        tip.SetTopGradientColour("green")
        tip.SetBottomGradientColour("red")
        tip.SetBodyImage(wx.Bitmap("icon.png"))

        # レイアウト
        layout = wx.BoxSizer(wx.VERTICAL)
        layout.Add(button, flag=wx.ALL, border=10)
        p.SetSizer(layout)

        self.Show()


if __name__ == "__main__":
    app = wx.App()
    App(None, wx.ID_ANY, 'タイトル')
    app.MainLoop()


実行結果
 ボタンにマウスを合わせるとスーパーツールチップが表示されます。



解説
スーパーツールチップを使用するには、wx.lib.agwパッケージのsurpertooltipクラスをインポートします。
今回は簡略化するため、asを用いて「STT」としました。
import wx.lib.agw.supertooltip as STT

続いてインスタンス化です。
tip = STT.SuperToolTip(message="素敵なメッセージ\n", header='へっだーぶぶん', footer='ふったーぶぶん')
この部分でインスタンス化を行なっています。
この時の引数は(メッセージテキスト、ヘッダーテキスト、フッターテキスト)です。
フッターテキストは省略することもできます。


メソッド紹介
スーパーツールチップで使用頻度が高そうなメソッドを厳選してご紹介します。
# ヘッダー部の仕切り線を有効にする
tip.SetDrawHeaderLine(True)

# フッター部の仕切り線を有効にする
tip.SetDrawFooterLine(True)

# ヘッダーテキストを設定する
tip.SetHeader("新しいテキスト")

# メッセージを設定する
tip.SetMessage("新しい本文")

# フッターテキストを設定する
tip.SetFooter("新しいテキスト")

# ターゲットを設定する
tip.SetTarget(button)

# ヘッダー部分の色を指定する
tip.SetTopGradientColour("green")

# メッセージ部分の色を指定する
tip.SetMiddleGradientColour("red")

# フッター部分の色を指定する
tip.SetBottomGradientColour("yellow")

# ヘッダー部分に表示するイメージを指定する
tip.SetHeaderBitmap(wx.Bitmap("icon.png"))

# メッセージ部分に表示するイメージを指定する
tip.SetBodyImage(wx.Bitmap("icon.png"))

# フッター部分に表示するイメージを指定する
tip.SetFooterBitmap(wx.Bitmap("icon.png"))

# # # # # # # # # # # # # # # # # # # # # # # # # 

# ヘッダーテキストを取得する
tip.GetHeader()

# メッセージを取得する
tip.GetMessage()

# フッターテキストを取得する
tip.GetFooter()

# ターゲットを取得する
tip.GetTarget()

# ヘッダー部分の色を取得する
tip.GetTopGradientColour()

# メッセージ部分の色を取得する
tip.GetMiddleGradientColour()

# フッター部分の色を取得する
tip.GetBottomGradientColour()

# ヘッダー部分のイメージを取得する
tip.GetHeaderBitmap()

# メッセージ部分のイメージを取得する
tip.GetBodyImage()

# フッター部分のイメージを取得する
tip.GetFooterBitmap()


参考
・公式リファレンス:wx.lib.agw.supertooltip.SuperToolTip


まとめ
スーパーツールチップは自由度のかなり高いツールチップです。
できることが多いため、ついつい情報量が多くなりすぎてしまうこともあります。
「ツールチップは補助的な役割」ということを忘れずに、適切な内容にすることを心がけましょう。


5 件のコメント:

  1. これはツールチップとしてではなくて、StaticTextのような役目をしてほしいです。
    可能でしょうか。

    返信削除
    返信
    1. コメントありがとうございます(^^)
      申し訳ありません。
      ご質問の意味がよくわかりません(・・;)
      やりたいことを、もう少し具体的に教示いただけないでしょうか?

      削除
    2. 説明が分かりずらくてすいません。
      wx.StaticTextやwx.Panel などの背景にグラデーションを描画させたいということです。

      削除
    3. 返信ありがとうございます。
      パネルなどの背景色をグラデーションにしたいということですね。
      私も知識がなかったため調べたところ、下記のように書くことでパネル背景をグラデーションにする方法を見つけました。

      import wx

      class MyFrame(wx.Frame):
      ____def __init__(self, parent=None, title=None):
      ________wx.Frame.__init__(self, parent, wx.ID_ANY, title)
      ________self.panel = wx.Panel(self, size=(350, 450))
      ________# this sets up the painting canvas
      ________self.panel.Bind(wx.EVT_PAINT, self.on_paint)
      ________# set frame size to fit panel
      ________self.Fit()

      ____def on_paint(self, event):
      ________# establish the painting canvas
      ________dc = wx.PaintDC(self.panel)
      ________x = 0
      ________y = 0
      ________w, h = self.GetSize()
      ________dc.GradientFillLinear((x, y, w, h), 'blue', 'black')

      app = wx.App(0)
      MyFrame(title='Gradient Test').Show()
      app.MainLoop()

      時間がないため詳細は把握していませんが、青から黒へグラデーションするようです。
      これでご期待の回答になっておりますでしょうか?

      削除
    4. お忙しいところすぐに調べていただきありがとうございます!!
      はい、僕が実現したかったことです。返答ありがとうございました。

      削除