浏览代码

Make prompt a new OutputGutter widget and make that the drag target.

danielballan 8 年之前
父节点
当前提交
db3256567c
共有 1 个文件被更改,包括 148 次插入105 次删除
  1. 148 105
      src/notebook/output-area/widget.ts

+ 148 - 105
src/notebook/output-area/widget.ts

@@ -142,6 +142,15 @@ class OutputAreaWidget extends Widget {
     this.layout = new PanelLayout();
   }
 
+  get mirror(): OutputAreaWidget {
+    let rendermime = this._rendermime;
+    let widget = new OutputAreaWidget({ rendermime });
+    widget.model = this._model;
+    widget.title.text = 'Mirrored Output';
+    widget.title.closable = true;
+    return widget;
+  }
+
   /**
    * A signal emitted when the widget's model changes.
    */
@@ -244,7 +253,6 @@ class OutputAreaWidget extends Widget {
     this._model = null;
     this._rendermime = null;
     this._renderer = null;
-    this._dragData = null;
     super.dispose();
   }
 
@@ -345,6 +353,115 @@ class OutputAreaWidget extends Widget {
     widget.render(output, this._trusted);
   }
 
+  /**
+   * Follow changes on the model state.
+   */
+  private _onModelStateChanged(sender: OutputAreaModel, args: IListChangedArgs<nbformat.IOutput>) {
+    switch (args.type) {
+    case ListChangeType.Add:
+      // Children are always added at the end.
+      this._addChild();
+      break;
+    case ListChangeType.Replace:
+      // Only "clear" is supported by the model.
+
+      // When an output area is cleared and then quickly replaced with new content
+      // (as happens with @interact in widgets, for example), the quickly changing
+      // height can make the page jitter. We introduce a small delay in the minimum height
+      // to prevent this jitter.
+      let rect = this.node.getBoundingClientRect()
+      let oldHeight = this.node.style.minHeight;
+      this.node.style.minHeight = `${rect.height}px`;
+      setTimeout(() => { this.node.style.minHeight = oldHeight; }, 50);
+
+      let oldValues = args.oldValue as nbformat.IOutput[];
+      for (let i = args.oldIndex; i < oldValues.length; i++) {
+        this._removeChild(args.oldIndex);
+      }
+      break;
+    case ListChangeType.Set:
+      this._updateChild(args.newIndex);
+      break;
+    default:
+      break;
+    }
+    this.update();
+  }
+
+  private _trusted = false;
+  private _fixedHeight = false;
+  private _collapsed = false;
+  private _model: OutputAreaModel = null;
+  private _rendermime: RenderMime<Widget> = null;
+  private _renderer: OutputAreaWidget.IRenderer = null;
+}
+
+
+/**
+ * A namespace for OutputAreaWidget statics.
+ */
+export
+namespace OutputAreaWidget {
+  /**
+   * The options to pass to an `OutputAreaWidget`.
+   */
+  export
+  interface IOptions {
+    /**
+     * The rendermime instance used by the widget.
+     */
+    rendermime: RenderMime<Widget>;
+
+    /**
+     * The output widget renderer.
+     *
+     * Defaults to a shared `IRenderer` instance.
+     */
+     renderer?: IRenderer;
+  }
+
+  /**
+   * An output widget renderer.
+   */
+  export
+  interface IRenderer {
+    /**
+     * Create an output widget.
+     *
+     *
+     * @returns A new widget for an output.
+     */
+    createOutput(options: OutputWidget.IOptions): Widget;
+  }
+
+  /**
+   * The default implementation of `IRenderer`.
+   */
+  export
+  class Renderer implements IRenderer {
+    /**
+     * Create an output widget.
+     *
+     *
+     * @returns A new widget for an output.
+     */
+    createOutput(options: OutputWidget.IOptions): OutputWidget {
+      return new OutputWidget(options);
+    }
+  }
+
+  /**
+   * The default `Renderer` instance.
+   */
+  export
+  const defaultRenderer = new Renderer();
+}
+
+/**
+ * The gutter on the left side of the OutputWidget
+ */
+export
+class OutputGutter extends Widget {
   /**
    * Handle the DOM events for the output area widget.
    *
@@ -452,12 +569,8 @@ class OutputAreaWidget extends Widget {
     });
 
     this._drag.mimeData.setData(FACTORY_MIME, () => {
-      let rendermime = this._rendermime;
-      let widget = new OutputAreaWidget({ rendermime });
-      widget.model = this._model;
-      widget.title.text = 'Mirrored Output';
-      widget.title.closable = true;
-      return widget;
+      let output_area = this.parent.parent as OutputAreaWidget;
+      return output_area.mirror;
     });
 
     // Start the drag and remove the mousemove listener.
@@ -469,113 +582,25 @@ class OutputAreaWidget extends Widget {
   }
 
   /**
-   * Follow changes on the model state.
+   * Dispose of the resources held by the widget.
    */
-  private _onModelStateChanged(sender: OutputAreaModel, args: IListChangedArgs<nbformat.IOutput>) {
-    switch (args.type) {
-    case ListChangeType.Add:
-      // Children are always added at the end.
-      this._addChild();
-      break;
-    case ListChangeType.Replace:
-      // Only "clear" is supported by the model.
-
-      // When an output area is cleared and then quickly replaced with new content
-      // (as happens with @interact in widgets, for example), the quickly changing
-      // height can make the page jitter. We introduce a small delay in the minimum height
-      // to prevent this jitter.
-      let rect = this.node.getBoundingClientRect()
-      let oldHeight = this.node.style.minHeight;
-      this.node.style.minHeight = `${rect.height}px`;
-      setTimeout(() => { this.node.style.minHeight = oldHeight; }, 50);
-
-      let oldValues = args.oldValue as nbformat.IOutput[];
-      for (let i = args.oldIndex; i < oldValues.length; i++) {
-        this._removeChild(args.oldIndex);
-      }
-      break;
-    case ListChangeType.Set:
-      this._updateChild(args.newIndex);
-      break;
-    default:
-      break;
+  dispose() {
+    // Do nothing if already disposed.
+    if (this.isDisposed) {
+      return;
     }
-    this.update();
+    this._dragData = null;
+    this._drag = null;
+    this._selectTimer = null;
+    super.dispose();
   }
 
-  private _trusted = false;
-  private _fixedHeight = false;
-  private _collapsed = false;
-  private _model: OutputAreaModel = null;
-  private _rendermime: RenderMime<Widget> = null;
-  private _renderer: OutputAreaWidget.IRenderer = null;
   private _drag: Drag = null;
   private _dragData: { pressX: number, pressY: number } = null;
   private _selectTimer = -1;
 }
 
 
-/**
- * A namespace for OutputAreaWidget statics.
- */
-export
-namespace OutputAreaWidget {
-  /**
-   * The options to pass to an `OutputAreaWidget`.
-   */
-  export
-  interface IOptions {
-    /**
-     * The rendermime instance used by the widget.
-     */
-    rendermime: RenderMime<Widget>;
-
-    /**
-     * The output widget renderer.
-     *
-     * Defaults to a shared `IRenderer` instance.
-     */
-     renderer?: IRenderer;
-  }
-
-  /**
-   * An output widget renderer.
-   */
-  export
-  interface IRenderer {
-    /**
-     * Create an output widget.
-     *
-     *
-     * @returns A new widget for an output.
-     */
-    createOutput(options: OutputWidget.IOptions): Widget;
-  }
-
-  /**
-   * The default implementation of `IRenderer`.
-   */
-  export
-  class Renderer implements IRenderer {
-    /**
-     * Create an output widget.
-     *
-     *
-     * @returns A new widget for an output.
-     */
-    createOutput(options: OutputWidget.IOptions): OutputWidget {
-      return new OutputWidget(options);
-    }
-  }
-
-  /**
-   * The default `Renderer` instance.
-   */
-  export
-  const defaultRenderer = new Renderer();
-}
-
-
 /**
  * An output widget.
  */
@@ -588,7 +613,7 @@ class OutputWidget extends Widget {
     super();
     let layout = new PanelLayout();
     this.layout = layout;
-    let prompt = new Widget();
+    let prompt = new OutputGutter();
     this._placeholder = new Widget();
     this.addClass(OUTPUT_CLASS);
     prompt.addClass(PROMPT_CLASS);
@@ -808,6 +833,24 @@ class OutputWidget extends Widget {
 }
 
 
+/**
+ * A namespace for OutputGutter statics.
+ */
+export
+namespace OutputGutter {
+  /**
+   * The options to pass to an `OutputGutter`.
+   */
+  export
+  interface IOptions {
+    /**
+     * The rendermime instance used by the widget.
+     */
+    rendermime: RenderMime<Widget>;
+  }
+}
+
+
 
 /**
  * A namespace for OutputArea statics.