editor: wip full backspace/insert support
[fnpeditor.git] / src / editor / plugins / core / core.js
index 9445682..0ac9cff 100644 (file)
@@ -8,10 +8,10 @@ var _ = require('libs/underscore'),
     footnote = require('plugins/core/footnote'),
     switchTo = require('plugins/core/switch'),
     lists = require('plugins/core/lists'),
-    plugin = {name: 'core', actions: [], canvas: {}, documentExtension: {textNode: {}}},
+    plugin = {name: 'core', actions: [], canvas: {}, documentExtension: {textNode: {}, elementNode: {}}},
     Dialog = require('views/dialog/dialog'),
     canvasElements = require('plugins/core/canvasElements'),
-    metadataEditor = require('./metadataEditor/metadataEditor');
+    metadataEditor = require('plugins/core/metadataEditor/metadataEditor');
 
 
 
@@ -82,6 +82,87 @@ plugin.documentExtension.textNode.transformations = {
     }
 };
 
+plugin.documentExtension.elementNode.transformations = {
+    moveUp: function() {
+        var toMerge = this,
+            prev = toMerge.prev();
+
+        var merge = function(from, to) {
+            var toret;
+            from.contents().forEach(function(node, idx) {
+                var len, ret;
+                if(idx === 0 && node.nodeType === Node.TEXT_NODE) {
+                    len = node.getText().length;
+                }
+                ret = to.append(node);
+                
+                if(idx === 0) {
+                    toret = {
+                        node: ret,
+                        offset: ret.getText().length - len
+                    };
+                }
+            });
+            from.detach();
+            return toret;
+        };
+
+        var strategies = [
+            {
+                applies: function() {
+                    return toMerge.is('p');
+                },
+                run: function() {
+                    if(prev && prev.is('p') || prev.is({tagName: 'header'})) {
+                        return merge(toMerge, prev);
+                    }
+                    if(prev && prev.is('list')) {
+                        var items = prev.contents().filter(function(n) { return n.is('item');});
+                        return merge(toMerge, items[items.length-1]);
+                    }
+                }
+            },
+            {
+                applies: function() {
+                    return toMerge.is({tagName: 'header'});
+                },
+                run: function() {
+                    if(prev && prev.is('p') || prev.is({tagName: 'header'})) {
+                        return merge(toMerge, prev);
+                    }
+                }
+            },
+            {
+                applies: function() {
+                    return toMerge.is('item');
+                },
+                run: function() {
+                    var list;
+                    if(prev && prev.is('item')) {
+                        return merge(toMerge, prev);
+                    } else if(!prev && (list = toMerge.parent()) && list.is('list')) {
+                        list.before(toMerge);
+                        toMerge.setClass('p');
+                        if(!list.contents().length) {
+                            list.detach();
+                        }
+                        return {node: toMerge.contents()[0], offset:0};
+                    }
+                }
+            }
+        ];
+
+        var toret;
+        strategies.some(function(strategy) {
+            if(strategy.applies()) {
+                toret = strategy.run();
+                return true;
+            }
+        });
+        return toret;
+    }
+};
+
 var undoRedoAction = function(dir) {
     return {
         name: dir,