Browse Source

Add ratio options for the Resizer and fix undo manager issue on resizing

pull/67/head v0.4.8
Artur Arseniev 10 years ago
parent
commit
9ac330d578
  1. 2
      bower.json
  2. 24
      dist/grapes.min.js
  3. 2
      package.json
  4. 3
      src/commands/view/Resize.js
  5. 42
      src/demo.js
  6. 33
      src/dom_components/model/Component.js
  7. 19
      src/dom_components/view/ComponentView.js
  8. 6
      src/editor/model/Editor.js
  9. 50
      src/trait_manager/main.js
  10. 10
      src/trait_manager/model/Trait.js
  11. 2
      src/trait_manager/model/Traits.js
  12. 2
      src/trait_manager/view/TraitsView.js
  13. 5
      src/utils/Resizer.js

2
bower.json

@ -1,7 +1,7 @@
{ {
"name": "grapesjs", "name": "grapesjs",
"description": "Open source Web Template Editor", "description": "Open source Web Template Editor",
"version": "0.4.7", "version": "0.4.8",
"author": "Artur Arseniev", "author": "Artur Arseniev",
"homepage": "http://grapesjs.com", "homepage": "http://grapesjs.com",
"main": [ "main": [

24
dist/grapes.min.js

File diff suppressed because one or more lines are too long

2
package.json

@ -1,7 +1,7 @@
{ {
"name": "grapesjs", "name": "grapesjs",
"description": "Open source Web Template Editor", "description": "Open source Web Template Editor",
"version": "0.4.7", "version": "0.4.8",
"author": "Artur Arseniev", "author": "Artur Arseniev",
"license": "BSD-3-Clause", "license": "BSD-3-Clause",
"homepage": "http://grapesjs.com", "homepage": "http://grapesjs.com",

3
src/commands/view/Resize.js

@ -10,8 +10,9 @@ define(function() {
// Create the resizer for the canvas if not yet created // Create the resizer for the canvas if not yet created
if(!canvasResizer) { if(!canvasResizer) {
var canvasView = canvas.getCanvasView(); var canvasView = canvas.getCanvasView();
options.prefix = editor.getConfig().stylePrefix; options.ratioDefault = 1;
options.appendTo = canvas.getResizerEl(); options.appendTo = canvas.getResizerEl();
options.prefix = editor.getConfig().stylePrefix;
options.posFetcher = canvasView.getElementPos.bind(canvasView); options.posFetcher = canvasView.getElementPos.bind(canvasView);
options.mousePosFetcher = canvas.getMouseRelativePos; options.mousePosFetcher = canvas.getMouseRelativePos;
this.canvasResizer = editor.Utils.Resizer.init(options); this.canvasResizer = editor.Utils.Resizer.init(options);

42
src/demo.js

@ -6,6 +6,7 @@ require(['config/require-config'], function() {
{ {
autorender: 0,
noticeOnUnload: 0, noticeOnUnload: 0,
container : '#gjs', container : '#gjs',
height: '100%', height: '100%',
@ -330,6 +331,47 @@ require(['config/require-config'], function() {
window.editor = editor; window.editor = editor;
/*
editor.TraitManager.addType('checkbox', {
events:{
'change .url-input': 'onChangeUrl'
},
onChangeUrl: function() {
var target = this.model.target;
var targetColl = target.collection;
var targetParent = target.collection.parent;
// Create link wrapper if not yet exist
if(targetParent.get('type') != 'link') {
var index = targetColl.indexOf(target);
var linkModel = targetColl.add({type: 'link'}, {at: index});
targetColl.remove(target);
linkModel.get('components').add(target);
console.log('Created link');
} else {
// update it
console.log('Link exist ', targetParent);
}
//this.components.parent = this;
console.log('changed url for', targetParent);
},
render : function() {
this.$el.html(
'<div class="gjs-trt-trait"><div class="gjs-label">Url</div>'+
'<div class="gjs-field gjs-field-text">'+
'<div class="gjs-input-holder"><input placeholder="google.com" class="url-input"></div>'+
'</div>'+
'</div>' +
'<div class="gjs-trt-trait"><div class="gjs-label">Taget</div>'+
'<div class="gjs-field gjs-field-text">'+
'<div class="gjs-input-holder"><input class="target-input"></div>'+
'</div>'+
'</div>');
return this;
},
});*/
editor.render();
}); });
}); });

33
src/dom_components/model/Component.js

@ -4,9 +4,11 @@ define(['backbone','./Components', 'SelectorManager/model/Selectors', 'TraitMana
return Backbone.Model.extend({ return Backbone.Model.extend({
defaults: { defaults: {
// HTML tag of the component
tagName: 'div', tagName: 'div',
// Component type, eg. 'text', 'image', 'video', etc.
type: '', type: '',
editable: false,
// True if the component is removable from the canvas // True if the component is removable from the canvas
removable: true, removable: true,
@ -23,28 +25,47 @@ define(['backbone','./Components', 'SelectorManager/model/Selectors', 'TraitMana
badgable: true, badgable: true,
// True if it's possible to style it // True if it's possible to style it
// Tip: Indicate an array of css properties is possible to style // Tip: Indicate an array of CSS properties which is possible to style
stylable: true, stylable: true,
// True if it's possible to clone the component // True if it's possible to clone the component
copyable: true, copyable: true,
// Indicates if it possible to resize the component (at the moment implemented only on Image) // Indicates if it possible to resize the component (at the moment implemented only on Image Components)
resizable: false, resizable: false,
// TODO // This property is used by the HTML exporter as void elements do not
mirror: '', // have closing tag, eg. <br/>, <hr/>, etc.
void: false, void: false,
// Indicates if the component is in some CSS state like ':hover', ':active', etc.
state: '', state: '',
status: '', status: '',
previousModel: '', previousModel: '',
content: '', content: '',
style: {}, style: {},
attributes: {}, attributes: {},
classes: '', classes: '',
traits: ['id', 'title'], traits: ['id', 'title'],
/**
* Set an array of items to show up inside the toolbar (eg. move, clone, delete)
* when the component is selected
* toolbar: [{
* attributes: {class: 'fa fa-arrows'},
* command: 'tlb-move',
* },{
* attributes: {class: 'fa fa-clone'},
* command: 'tlb-clone',
* }]
*/
toolbar: null, toolbar: null,
// TODO
editable: false,
mirror: '',
}, },
initialize: function(o, opt) { initialize: function(o, opt) {

19
src/dom_components/view/ComponentView.js

@ -209,7 +209,7 @@ define(['backbone', './ComponentsView'],
toggleBodyClass('addClass', e, opts); toggleBodyClass('addClass', e, opts);
modelToStyle = em.get('StyleManager').getModelToStyle(model); modelToStyle = em.get('StyleManager').getModelToStyle(model);
}, },
// Update all positioned elements // Update all positioned elements (eg. component toolbar)
onMove: function () { onMove: function () {
editor.trigger('change:canvasOffset'); editor.trigger('change:canvasOffset');
}, },
@ -221,11 +221,22 @@ define(['backbone', './ComponentsView'],
if (!modelToStyle) { if (!modelToStyle) {
return; return;
} }
var unit = 'px';
var style = _.clone(modelToStyle.get('style')); var style = _.clone(modelToStyle.get('style'));
style.width = rect.w; style.width = rect.w + (store ? 1 : 0) + unit;
style.height = rect.h; style.height = rect.h + unit;
modelToStyle.set('style', style, {avoidStore: !store}); modelToStyle.set('style', style, {avoidStore: 1});
em.trigger('targetStyleUpdated'); em.trigger('targetStyleUpdated');
// This trick will trigger the Undo Manager. To trigger "change:style"
// on the Model you need to provide a new object and after that
// Undo Manager will trigger only if values are different (this is why
// above I've added + 1 to width if store required)
if(store) {
var style3 = _.clone(style);
style3.width = (rect.w - 1) + unit;
modelToStyle.set('style', style3);
}
} }
} }
}); });

6
src/editor/model/Editor.js

@ -154,9 +154,11 @@ define(['backbone', 'backboneUndo', 'keymaster', 'Utils', 'StorageManager', 'Dev
Backbone.UndoManager.removeUndoType("change"); Backbone.UndoManager.removeUndoType("change");
var beforeCache; var beforeCache;
Backbone.UndoManager.addUndoType("change:style", { Backbone.UndoManager.addUndoType("change:style", {
"on": function (model, value, opt) { "on": function (model, value, opts) {
if(!beforeCache) var opt = opts || {};
if(!beforeCache){
beforeCache = model.previousAttributes(); beforeCache = model.previousAttributes();
}
if (opt && opt.avoidStore) { if (opt && opt.avoidStore) {
return; return;
} else { } else {

50
src/trait_manager/main.js

@ -7,33 +7,33 @@ define(function(require) {
TraitsView = require('./view/TraitsView'); TraitsView = require('./view/TraitsView');
var TraitsViewer; var TraitsViewer;
return { return {
TraitsView: TraitsView, TraitsView: TraitsView,
/** /**
* Name of the module * Name of the module
* @type {String} * @type {String}
* @private * @private
*/ */
name: 'TraitManager', name: 'TraitManager',
/** /**
* Get configuration object * Get configuration object
* @return {Object} * @return {Object}
* @private * @private
*/ */
getConfig: function(){ getConfig: function() {
return c; return c;
}, },
/** /**
* Initialize module. Automatically called with a new instance of the editor * Initialize module. Automatically called with a new instance of the editor
* @param {Object} config Configurations * @param {Object} config Configurations
*/ */
init: function(config) { init: function(config) {
c = config || {}; c = config || {};
for (var name in defaults) { for (var name in defaults) {
if (!(name in c)) if (!(name in c))
c[name] = defaults[name]; c[name] = defaults[name];
} }
@ -41,13 +41,13 @@ define(function(require) {
var ppfx = c.pStylePrefix; var ppfx = c.pStylePrefix;
if(ppfx) if(ppfx)
c.stylePrefix = ppfx + c.stylePrefix; c.stylePrefix = ppfx + c.stylePrefix;
TraitsViewer = new TraitsView({ TraitsViewer = new TraitsView({
collection: [], collection: [],
editor: c.em, editor: c.em,
config: c, config: c,
}); });
return this; return this;
}, },
/** /**
* *
@ -58,6 +58,16 @@ define(function(require) {
return TraitsViewer; return TraitsViewer;
}, },
/**
* Add new trait type
* @param {string} name Type name
* @param {Object} methods Object representing the trait
*/
addType: function (name, trait) {
var itemView = TraitsViewer.itemView;
TraitsViewer.itemsView[name] = itemView.extend(trait);
},
}; };
}; };
}); });

10
src/trait_manager/model/Trait.js

@ -4,17 +4,17 @@ define(['backbone'],
return Backbone.Model.extend({ return Backbone.Model.extend({
defaults: { defaults: {
type: 'text', // text, number, range, select type: 'text', // text, number, range, select
label: '', label: '',
name: '', name: '',
min: '', min: '',
max: '', max: '',
value: '', value: '',
target: '', target: '',
default: '', default: '',
placeholder: '', placeholder: '',
changeProp: 0, changeProp: 0,
options: [], options: [],
}, },
initialize: function(){ initialize: function(){
@ -24,5 +24,5 @@ define(['backbone'],
} }
}, },
}); });
}); });

2
src/trait_manager/model/Traits.js

@ -11,7 +11,7 @@ define(['backbone','./Trait', './TraitFactory'],
add: function(models, opt) { add: function(models, opt) {
// Use TraitFactory if necessary // Use TraitFactory if necessary
if(typeof models === 'string' || models instanceof Array){ if(typeof models === 'string' || models instanceof Array) {
if(typeof models === 'string') if(typeof models === 'string')
models = [models]; models = [models];
for(var i = 0, len = models.length; i < len; i++) { for(var i = 0, len = models.length; i < len; i++) {

2
src/trait_manager/view/TraitsView.js

@ -25,11 +25,11 @@ define(['backbone', 'Abstract/view/DomainViews', './TraitView', './TraitSelectVi
* @private * @private
*/ */
updatedCollection: function() { updatedCollection: function() {
this.el.className = this.className;
var comp = this.em.get('selectedComponent'); var comp = this.em.get('selectedComponent');
if(comp){ if(comp){
this.collection = comp.get('traits'); this.collection = comp.get('traits');
this.render(); this.render();
this.el.className = this.className;
} }
}, },

5
src/utils/Resizer.js

@ -6,6 +6,7 @@ define(function(require) {
// Indicates custom target updating strategy // Indicates custom target updating strategy
updateTarget: null, updateTarget: null,
// Function which gets HTMLElement as an arg and returns it relative position // Function which gets HTMLElement as an arg and returns it relative position
ratioDefault: 0,
posFetcher: null, posFetcher: null,
onStart: null, onStart: null,
onMove: null, onMove: null,
@ -342,6 +343,7 @@ define(function(require) {
* @return {Object} * @return {Object}
*/ */
calc: function(data) { calc: function(data) {
var opts = this.opts || {};
var startDim = this.startDim; var startDim = this.startDim;
var box = { var box = {
t: 0, t: 0,
@ -368,7 +370,8 @@ define(function(require) {
} }
// Enforce aspect ratio (unless shift key is being held) // Enforce aspect ratio (unless shift key is being held)
if (attr.indexOf('c') < 0 && data.keys.shift) { var ratioActive = opts.ratioDefault ? !data.keys.shift : data.keys.shift;
if (attr.indexOf('c') < 0 && ratioActive) {
var ratio = startDim.w / startDim.h; var ratio = startDim.w / startDim.h;
if (box.w / box.h > ratio) { if (box.w / box.h > ratio) {
box.h = Math.round(box.w / ratio); box.h = Math.round(box.w / ratio);

Loading…
Cancel
Save