【问题标题】:Changing the icon in matplotlib navigation toolbar using GTK backend使用 GTK 后端更改 matplotlib 导航工具栏中的图标
【发布时间】:2021-12-18 08:12:21
【问题描述】:

以前在 Stack Overflow 上也有人问过类似的问题,但是没有一个涉及 GTK 后端,也没有一个涉及需要更改后端搜索的路径。这里的类似问题包括thisthis 等等。 GTK后端的相关代码为here

顺便说一句,如果它是相关的,我正在使用 PyInstaller 冻结这个 Python 脚本,我想“更改”图标的原因是因为在某些 Windows 计算机上,我发现这些图标是断开的链接尽管图像出现在正确的位置,但导航工具栏:

\dist\<script name>\matplotlib\mpl-data\images\<image_file>-symbolic.svg

以及具有 GTK 后端 (f'{image_file}-symbolic.svg') 预期格式的图像。我不确定为什么会发生这个问题并且花了很多时间无处可去,所以我想一个可能的解决方法是将图像作为我的报告的一部分存储在我选择的位置并强制它们被使用脚本(以防它是一些奇怪的环境变量或路径问题)。使用下面的示例,我可以成功更改工具提示和图像/图标,但我无法更改图像的位置。 toolitems 的第三个参数控制图像:

list of toolitems to add to the toolbar, format is:
(
   text, # the text of the button (often not visible to users)
   tooltip_text, # the tooltip shown on hover (where possible)
   image_file, # name of the image for the button (without the extension)
   name_of_method, # name of the method in NavigationToolbar2 to call
)

显然,图像必须在预期的路径中,并且必须是不带扩展名的名称。后端代码指定:

image = Gtk.Image.new_from_gicon(
    Gio.Icon.new_for_string(
        str(cbook._get_data_path('images',
                                 f'{image_file}-symbolic.svg'))),
    Gtk.IconSize.LARGE_TOOLBAR)

所以我可以拍摄一个 svg 图像并将其放在我上面给出的路径中,最后附加 -symbolic 并让它工作。但是,有没有办法在与馈送到后端的默认目录不同的路径中执行此操作?我目前使用的代码如下:

from matplotlib.backends.backend_gtk3 import NavigationToolbar2GTK3

class MyToolbar(NavigationToolbar2GTK3):
  def __init__(self, figure_canvas, window):
    self.toolitems = ( 
        ('Home', 'Reset original view', 'home', 'home'),
        ('Back', 'Back to  previous view', 'back', 'back'),
        ('Forward', 'Forward to next view', 'forward', 'forward'),
        (None, None, None, None),
        ('Pan', 'Pan axes with left mouse, zoom with right', 'move', 'pan'),
        ('Zoom', 'Zoom to rectangle', 'zoom_to_rect', 'zoom'),
        ('Subplots', 'Configure subplots', 'subplots', 'configure_subplots'),
        (None, None, None, None),
        ('Save', 'Save the figure', 'filesave', 'save_figure'),
        )

    NavigationToolbar2GTK3.__init__(self, figure_canvas, window)

self.navigation_toolbar = MyToolbar(self._gtkFigure, main)
self.navigation_toolbar.update()

我的期望是某些计算机上出现的断开链接是cbook._get_data_path(由后端使用)由于某种原因出现不同的结果,所以如果我可以在脚本中以某种方式更改它,也许我可以修补问题?任何帮助或指点将不胜感激!

编辑:在挖掘了更多之后,cbook 中的_get_data_path 看起来只是对matplotlib.get_data_path() 的调用。从 here 开始,在 matplotlib 中无法使用自定义数据路径(我一直在寻找 .set_data_path() 方法)。其中一位贡献者建议“获取本机 tk 小部件,并对 iconphoto() 和他们的朋友执行正确的调用。”由于我没有使用 Tkinter 后端,我仍然不确定如何继续。我相当肯定我上面概述的方法不起作用,需要另一种方法,类似于here

【问题讨论】:

    标签: python matplotlib gtk pyinstaller


    【解决方案1】:

    所以最初的问题是在某些 Windows 计算机(不是全部)上,matplotlib 导航工具栏的本机图像显示为断开的链接。当使用self.toolitems 时,您只能指定图像名称。这是为什么? GTK matplotlib 后端有:

    image = Gtk.Image.new_from_gicon(
        Gio.Icon.new_for_string(
            str(cbook._get_data_path('images',
                                     f'{image_file}-symbolic.svg'))),
        Gtk.IconSize.LARGE_TOOLBAR)
    

    所以文件扩展名已经在后端指定了。我的期望是cbook._get_data_path 在出现断开链接的 Windows 计算机上产生不同的路径(而不是它们确实出现的路径)。如前所述,cbook._get_data_path 本质上是对matplotlib.get_data_path() 的调用,可以在代码中使用它来匹配计算机上有效和无效的路径。在 matplotlib API 我们有:

    def get_data_path():
        """Return the path to Matplotlib data."""
        return str(Path(__file__).with_name("mpl-data"))
    

    问题在于两者的返回路径相同。所以这似乎暗示问题出在 GTK 后端本身。我在某处读到某些计算机的 SVG 图像存在问题,因此您应该改用 PNG 图像。我更改了 GTK 后端以反映这一点,这解决了问题:

    f'{image_file}-symbolic.svg' -> f'{image_file}.png'
    

    显然,我认为编辑 matplotlib GTK 后端脚本不是最好的主意。其他一些人建议简单地获取 PNG 文件,将它们重命名为 SVG 文件,然后将 mpl-data 中的原始文件替换为这些文件。这似乎也很草率。我不确定最好的方法是什么,但现在我有这个工作,这就足够了。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-12-23
      • 2015-05-07
      • 2023-02-19
      • 2015-08-05
      • 1970-01-01
      • 2018-11-03
      • 1970-01-01
      • 2020-10-17
      相关资源
      最近更新 更多