blob: 6a1d050eac2061ea82525dabc0070aa7783be633 [file] [log] [blame]
// Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
// @dart = 2.9
part of observable;
/** A change to an observable instance. */
class ChangeEvent {
// TODO(sigmund): capture language issues around enums & create a canonical
// Dart enum design.
/** Type denoting an in-place update event. */
static const UPDATE = 0;
/** Type denoting an insertion event. */
static const INSERT = 1;
/** Type denoting a single-remove event. */
static const REMOVE = 2;
/**
* Type denoting events that affect the entire observable instance. For
* example, a list operation like clear or sort.
*/
static const GLOBAL = 3;
/** The observable instance that changed. */
final Observable target;
/** Whether the change was an [INSERT], [REMOVE], or [UPDATE]. */
final int type;
/** The value after the change (or inserted value in a list). */
final newValue;
/** The value before the change (or removed value from a list). */
final oldValue;
/** Property that changed (null for list changes). */
final String propertyName;
/**
* Index of the list operation. Insertions prepend in front of the given
* index (insert at 0 means an insertion at the beginning of the list).
*/
final int index;
/** Factory constructor for property change events. */
ChangeEvent.property(
this.target, this.propertyName, this.newValue, this.oldValue)
: type = UPDATE,
index = null;
/** Factory constructor for list change events. */
ChangeEvent.list(
this.target, this.type, this.index, this.newValue, this.oldValue)
: propertyName = null;
/** Factory constructor for [GLOBAL] change events. */
ChangeEvent.global(this.target)
: type = GLOBAL,
newValue = null,
oldValue = null,
propertyName = null,
index = null;
}
/** A collection of change events on a single observable instance. */
class EventSummary {
final Observable target;
// TODO(sigmund): evolve this to track changes per property.
List<ChangeEvent> events;
EventSummary(this.target) : events = new List<ChangeEvent>();
void addEvent(ChangeEvent e) {
events.add(e);
}
/** Notify listeners of [target] and parents of [target] about all changes. */
void notify() {
if (!events.isEmpty) {
for (Observable obj = target; obj != null; obj = obj.parent) {
for (final listener in obj.listeners) {
listener(this);
}
}
}
}
}
/** A listener of change events. */
typedef void ChangeListener(EventSummary events);