///------------------------------------------------------------------------------------------------- /// <summary> /// Initializes a new instance of the <see cref="UndoManager" /> class. /// </summary> /// <param name="store"> /// The store. /// </param> /// <param name="capacity"> /// (Optional) /// </param> ///------------------------------------------------------------------------------------------------- public UndoManager(IHyperstore store, int capacity = 100) { Contract.Requires(store, "store"); Contract.Requires(capacity > 0, "capacity"); _store = store; _domainModels = new Dictionary <string, DomainInfo>(StringComparer.OrdinalIgnoreCase); _undos = new RecursiveStack <SessionEvents>(capacity); _redos = new RecursiveStack <SessionEvents>(capacity); Capacity = capacity; }
private void PerformPop(RecursiveStack <SessionEvents> mainStack, RecursiveStack <SessionEvents> altStack, SessionMode mode, int?toSavePoint) { var notify = false; lock (_sync) { int sid = 0; var events = new List <IUndoableEvent>(); using (var session = _store.BeginSession(new SessionConfiguration { Mode = mode })) { IEventDispatcher dispatcher = null; string domainModelName = null; while (mainStack.Count > 0) { if (toSavePoint != null && mainStack.Peek().SessionId == toSavePoint) { break; } var ci = mainStack.Pop(); foreach (var @event in Enumerable.Reverse(ci.Events)) { var evt = @event.GetReverseEvent(session.SessionId); if (evt == null) { continue; } if (domainModelName != evt.Domain) { dispatcher = _domainModels[evt.Domain].Dispatcher; domainModelName = evt.Domain; } dispatcher.HandleEvent(evt); if (evt is IUndoableEvent) { events.Add(evt as IUndoableEvent); } } sid = ci.SessionId; if (toSavePoint == null) { break; } } session.AcceptChanges(); } if (events.Count > 0) { notify = true; altStack.Push(new SessionEvents { SessionId = sid, Events = events.ToList() }); } } if (notify) { OnPropertyChanged("CanUndo"); OnPropertyChanged("CanRedo"); } }