ClutterActor はアニメーション機能を内蔵している。
clutter_actor_save_easing_state # pause
clutter_actor_set_easing_duration # time
# move, resize, opacity, etc…
clutter_actor_restore_easing_state # start
たったコレだけで様々な変更がアニメーションになって動く。
ということでサンプルコード、クリック毎に Actor が入れ替わります。
#!/usr/bin/gjs const Gtk = imports.gi.Gtk; const GtkClutter = imports.gi.GtkClutter; const Clutter = imports.gi.Clutter; const Lang = imports.lang; const AnimateWin = new Lang.Class({ Name: 'AnimateWin', Extends: Gtk.ApplicationWindow, _init: function(app) { this.parent({ application: app }); this.red = new Clutter.Actor({ background_color: Clutter.Color.new(255, 0, 0, 255), x: 25, y: 25, width: 50, height: 50 }); this.blue = new Clutter.Actor({ background_color: Clutter.Color.new(0, 0, 255, 255), x: 75, y: 75, width: 50, height: 50 }); // action let click = new Clutter.ClickAction(); click.connect("clicked", Lang.bind(this, function() { // pause this.red.save_easing_state(); this.blue.save_easing_state(); // animation time (default 250) this.red.set_easing_duration(2500); // move let [x, y] = this.red.get_position(); let [x2, y2] = this.blue.get_position(); this.red.set_position(x2, y2); this.blue.set_position(x, y); // play this.red.restore_easing_state(); this.blue.restore_easing_state(); })); // Embed let embed = new GtkClutter.Embed(); let stage = embed.get_stage(); stage.add_child(this.red); stage.add_child(this.blue); stage.add_action(click); this.add(embed); this.show_all(); } }); // init GtkClutter.init(null); let app = new Gtk.Application(); app.connect("activate", function() { new AnimateWin(app); }); app.run(null);
コレだけだと使いどころがあんまりなさそうだよね。
しかし、ClutterImage の resize が超滑らかになるメリットがあった!
ということで comipoli に早速採用、永遠に実験用アプリ…