こんなページを見つけた。
Ubuntu忘備録: GdkPixbufを高速にリサイズ(cairo)
早くなるなら使ってみようかなと。
comipoli を PyGObject に戻すので Python3 で。
Gjs はリソースの cairo を使うけど PyGObject はモジュールを使う。
Pycairo は Fedora にはデフォルトで入っている。
Pycairo
手持ちの 7952x5304px な巨大画像を同じディレクトリに置いて以下を。
#!/usr/bin/env python3 import gi, sys, cairo, time gi.require_version('Gtk', '3.0') from gi.repository import Gtk, Gdk, GLib, GdkPixbuf class AWindow(Gtk.ApplicationWindow): def __init__(self, app): Gtk.ApplicationWindow.__init__(self, application=app) self.d = Gtk.DrawingArea() self.d.connect('draw', self.on_draw) self.add(self.d) self.pixbuf = GdkPixbuf.Pixbuf.new_from_file('7952x5304.jpg') self.resize(600, 300) self.show_all() def on_draw(self, widget, cr): aw = widget.get_allocated_width() ah = widget.get_allocated_height() # method n = time.time() buf = self.pixbuf.scale_simple(aw//2, ah, GdkPixbuf.InterpType.HYPER) print('method : {}'.format(time.time() - n)) Gdk.cairo_set_source_pixbuf(cr, buf, 0, 0) cr.paint() # function i = time.time() buf2 = self.pixbuf_scale(self.pixbuf, aw//2, ah) print('function: {}'.format(time.time() - i)) Gdk.cairo_set_source_pixbuf(cr, buf2, aw//2, 0) cr.paint() def pixbuf_scale(self, pixbuf, w, h): with cairo.ImageSurface(cairo.Format.ARGB32, w, h) as surface: cr = cairo.Context(surface) pw = pixbuf.get_width() ph = pixbuf.get_height() matrix = cairo.Matrix(w/pw, 0, 0, h/ph, 0, 0) cr.set_matrix(matrix) Gdk.cairo_set_source_pixbuf(cr, pixbuf, 0, 0) cr.paint() return Gdk.pixbuf_get_from_surface(surface, 0, 0, w, h) class AApplication(Gtk.Application): __gtype_name__ = 'AApplication' def __init__(self): GLib.set_prgname('AApplication') Gtk.Application.__init__(self) def do_startup(self): Gtk.Application.do_startup(self) AWindow(self) def do_activate(self): self.props.active_window.present() AApplication().run(sys.argv)
結果
三倍以上遅いんですけど、Python だからだろうか?
ちなみにこのマシンは i5-6500(skylake) 3.2GHz と内蔵グラフィックです。
このスペックでも 0.05 秒でリサイズできるのだから scale_simple で充分かと。