[pitivi] viewer: Add undo/redo support to the transformation box
- From: Thibault Saunier <tsaunier src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [pitivi] viewer: Add undo/redo support to the transformation box
- Date: Thu, 7 Apr 2016 12:40:05 +0000 (UTC)
commit 2a4e9ad013b64e8e2d8e31666a1712c04edb544c
Author: Thibault Saunier <tsaunier gnome org>
Date: Fri Apr 1 11:34:38 2016 +0200
viewer: Add undo/redo support to the transformation box
+ Add the notion of FinalizingAction to UndoableActionStack so that
we can commit the timeline *only* once after all actions have been
executed
Differential Revision: https://phabricator.freedesktop.org/D844
pitivi/undo/timeline.py | 13 +++++++++++--
pitivi/undo/undo.py | 22 +++++++++++++++++++---
pitivi/viewer/move_scale_overlay.py | 16 +++++++++++++++-
pitivi/viewer/overlay_stack.py | 2 +-
pre-commit.hook | 1 +
5 files changed, 47 insertions(+), 7 deletions(-)
---
diff --git a/pitivi/undo/timeline.py b/pitivi/undo/timeline.py
index c4fbacd..1dc887f 100644
--- a/pitivi/undo/timeline.py
+++ b/pitivi/undo/timeline.py
@@ -24,10 +24,19 @@ from gi.repository import GES
from gi.repository import GObject
from pitivi.utils.loggable import Loggable
-from pitivi.undo.undo import PropertyChangeTracker, UndoableAction
+from pitivi.undo.undo import PropertyChangeTracker, UndoableAction,\
+ FinalizingAction
from pitivi.effects import PROPS_TO_IGNORE
+class CommitTimelineFinalizingAction(FinalizingAction):
+ def __init__(self, pipeline):
+ self.__pipeline = pipeline
+
+ def do(self):
+ self.__pipeline.commit_timeline()
+
+
class TrackElementPropertyChanged(UndoableAction):
def __init__(self, track_element, property_name, old_value, new_value):
@@ -592,7 +601,7 @@ class TimelineLogObserver(Loggable):
self._controlBindingAddedCb)
if isinstance(track_element, GES.BaseEffect):
self.children_props_tracker.addTrackElement(track_element)
- elif isinstance(track_element, GES.TitleSource):
+ elif isinstance(track_element, GES.VideoSource):
self.children_props_tracker.addTrackElement(track_element)
def _disconnectFromTrackElement(self, track_element):
diff --git a/pitivi/undo/undo.py b/pitivi/undo/undo.py
index c6f803f..ace492d 100644
--- a/pitivi/undo/undo.py
+++ b/pitivi/undo/undo.py
@@ -79,6 +79,15 @@ class UndoableAction(GObject.Object, Loggable):
self.emit("undone")
+class FinalizingAction:
+ """
+ Base class for actions to happen when an UndoableActionStack is
+ done or undone.
+ """
+ def do(self):
+ raise NotImplementedError()
+
+
class UndoableActionStack(UndoableAction):
"""
@@ -89,12 +98,13 @@ class UndoableActionStack(UndoableAction):
"cleaned": (GObject.SIGNAL_RUN_LAST, None, ()),
}
- def __init__(self, action_group_name):
+ def __init__(self, action_group_name, finalizing_action=None):
UndoableAction.__init__(self)
self.action_group_name = action_group_name
self.done_actions = []
self.undone_actions = []
self.actions = []
+ self.finalizing_action = finalizing_action
def push(self, action):
self.done_actions.append(action)
@@ -109,11 +119,17 @@ class UndoableActionStack(UndoableAction):
self.done_actions = self.undone_actions[::-1]
self.emit("done")
+ if self.finalizing_action:
+ self.finalizing_action.do()
+
def undo(self):
self._runAction(self.done_actions, "undo")
self.undone_actions = self.done_actions[::-1]
self.emit("undone")
+ if self.finalizing_action:
+ self.finalizing_action.do()
+
def clean(self):
actions = self.done_actions + self.undone_actions
self.undone_actions = []
@@ -152,13 +168,13 @@ class UndoableActionLog(GObject.Object, Loggable):
self.running = False
self._checkpoint = self._takeSnapshot()
- def begin(self, action_group_name):
+ def begin(self, action_group_name, finalizing_action=None):
self.debug("Beginning %s", action_group_name)
if self.running:
self.debug("Abort because already running")
return
- stack = UndoableActionStack(action_group_name)
+ stack = UndoableActionStack(action_group_name, finalizing_action)
nested = self._stackIsNested(stack)
self.stacks.append(stack)
self.debug("begin action group %s, nested %s",
diff --git a/pitivi/viewer/move_scale_overlay.py b/pitivi/viewer/move_scale_overlay.py
index b368656..2c9fac4 100644
--- a/pitivi/viewer/move_scale_overlay.py
+++ b/pitivi/viewer/move_scale_overlay.py
@@ -27,6 +27,8 @@ from math import pi
from gi.repository import Gdk
+from pitivi.undo.timeline import CommitTimelineFinalizingAction
+from pitivi.utils.misc import disconnectAllByFunc
from pitivi.viewer.overlay import Overlay
@@ -304,13 +306,14 @@ class MoveScaleOverlay(Overlay):
"""
Viewer overlays class for GESVideoSource transformations
"""
- def __init__(self, stack, source):
+ def __init__(self, stack, action_log, source):
Overlay.__init__(self, stack, source)
self.__clicked_handle = None
self.__click_diagonal_sign = None
self.__box_hovered = False
+ self.__action_log = action_log
self.hovered_handle = None
# Corner handles need to be ordered for drawing.
@@ -327,6 +330,7 @@ class MoveScaleOverlay(Overlay):
for key in self.handles:
self.handles[key].set_placement(key)
+ self._source.connect("deep-notify", self.__source_property_changed_cb)
self.update_from_source()
def __get_source_position(self):
@@ -410,9 +414,13 @@ class MoveScaleOverlay(Overlay):
return size[0] / size[1]
def on_button_press(self):
+ disconnectAllByFunc(self._source, self.__source_property_changed_cb)
self.click_source_position = self.__get_source_position()
self.__clicked_handle = None
+ self.__action_log.begin("Video position change",
+ CommitTimelineFinalizingAction(
+ self._source.get_timeline().get_parent()))
if self.hovered_handle:
self.hovered_handle.on_click()
self.__clicked_handle = self.hovered_handle
@@ -429,6 +437,7 @@ class MoveScaleOverlay(Overlay):
self.update_from_source()
self.on_hover(cursor_position)
+ self.__action_log.commit()
if self.__clicked_handle:
if not self.__clicked_handle.hovered:
self.stack.reset_cursor()
@@ -437,8 +446,13 @@ class MoveScaleOverlay(Overlay):
elif self._is_hovered():
self.stack.set_cursor("grab")
+ self._source.connect("deep-notify", self.__source_property_changed_cb)
self.queue_draw()
+ def __source_property_changed_cb(self, unused_source, unused_gstelement,
+ unused_pspec):
+ self.update_from_source()
+
def on_motion_notify(self, cursor_pos):
click_to_cursor = self.stack.get_normalized_drag_distance(cursor_pos)
if self.__clicked_handle:
diff --git a/pitivi/viewer/overlay_stack.py b/pitivi/viewer/overlay_stack.py
index ae7dfef..f2db4f8 100644
--- a/pitivi/viewer/overlay_stack.py
+++ b/pitivi/viewer/overlay_stack.py
@@ -60,7 +60,7 @@ class OverlayStack(Gtk.Overlay):
if type(source) == GES.TitleSource:
overlay = TitleOverlay(self, source)
else:
- overlay = MoveScaleOverlay(self, source)
+ overlay = MoveScaleOverlay(self, self.app.action_log, source)
self.add_overlay(overlay)
self.__overlays[source] = overlay
diff --git a/pre-commit.hook b/pre-commit.hook
index 54062a1..83e4243 100755
--- a/pre-commit.hook
+++ b/pre-commit.hook
@@ -67,6 +67,7 @@ pitivi/undo/undo.py \
pitivi/undo/timeline.py \
pitivi/render.py \
pitivi/viewer/move_scale_overlay.py \
+pitivi/viewer/overlay_stack.py \
"
git-pylint-commit-hook --help |grep ignore > /dev/null 2>&1
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]