Commit 6c2f8a64 authored by Hardik Juneja's avatar Hardik Juneja Committed by Hardik Juneja

erp5_officejs: Image Editor for Officejs

parent 359cc2cd
/*global window, rJS, CKEDITOR*/
/*jslint nomen: true, maxlen:80, indent:2*/
(function (rJS, RSVP) {
"use strict";
rJS(window)
.ready(function (g) {
g.props = {};
})
.ready(function (g) {
return g.getElement()
.push(function (element) {
var textarea = element.querySelector('textarea');
g.props.element = element;
g.props.blob_defer = RSVP.defer();
});
})
.declareAcquiredMethod("submitContent", "triggerSubmit")
.declareMethod('render', function (options) {
this.props.key = options.key || "text_content";
return new RSVP.Queue()
.push(function() {
if (options.value.split('data:')[1] === '') {
return '';
}
return jIO.util.dataURItoBlob(options.value);
})
.push(function(blob) {
if (!blob) {
return {};
blob = new Blob([''], {type: 'image/png'});
}
blob.name = options.name;
FILE.open_handler({target:{files:[blob]}});
return {};
})
})
.declareMethod('getContent', function () {
var result = {},
gadget = this;
return new RSVP.Queue()
.push(function() {
return FILE.save({name: gadget.props.key, type:'BLOB'});
})
.push(function(blob) {
return jIO.util.readBlobAsDataURL(blob);
})
.push(function(datauri) {
return datauri.target.result;
});
});
}(rJS, RSVP));
\ No newline at end of file
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-type" content="text/html; charset=utf-8" />
<meta name="viewport" content="width=device-width, user-scalable=no" />
<title>OfficeJS Router Gadget</title>
<!-- renderjs -->
<script src="rsvp.js" type="text/javascript"></script>
<script src="renderjs.js" type="text/javascript"></script>
<!-- custom script -->
<script src="gadget_officejs_router.js" type="text/javascript"></script>
</head>
<body>
<script data-renderjs-configuration="portal_type" type="text/x-renderjs-configuration">Image</script>
<script data-renderjs-configuration="parent_relative_url" type="text/x-renderjs-configuration">image_module</script>
<script data-renderjs-configuration="document_title" type="text/x-renderjs-configuration">Image</script>
<script data-renderjs-configuration="document_title_plural" type="text/x-renderjs-configuration">Images</script>
<script data-renderjs-configuration="global_setting_gadget_url" type="text/x-renderjs-configuration">https://setting-gadget.app.officejs.com/0.1.1/</script>
</body>
</html>
\ No newline at end of file
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>OfficeJS Jio Web Page View</title>
<script src="rsvp.js"></script>
<script src="renderjs.js"></script>
<script src="handlebars.js"></script>
<script class="view-web-page-template" type="text/x-handlebars-template">
<form class="view-web-page-form">
<div class="center">
<div class="ui-field-contain">
<label data-i18n="Title:">Title:</label>
<div class="ui-input-text ui-body-inherit ui-corner-all ui-shadow-inset">
<input type="text" name="title" value="{{title}}">
</div>
</div>
<button type="submit" data-i18n="Save" style="display:none;">Save</button>
<div class="ui-field-contain">
<label data-i18n="Reference:">Reference:</label>
<input type="text" name="reference" value="{{reference}}">
</div>
<div class="ui-field-contain">
<label data-i18n="Version:">Version:</label>
<input type="text" name="version" value="{{version}}"></label>
</div>
<div class="ui-field-contain">
<label data-i18n="Language:">Language:</label>
<input type="text" name="language" value="{{language}}">
</div>
<div class="ui-field-contain">
<label data-i18n="Description:">Description:</label>
<textarea name="description">{{description}}</textarea>
</div>
<div class='document-content'></div>
</div>
</div>
</form>
</script>
<script src="gadget_officejs_jio_image_view.js"></script>
</head>
<body>
</body>
</html>
/*globals window, rJS, Handlebars, RSVP, loopEventListener, console, URL*/
/*jslint indent: 2, nomen: true, maxlen: 80*/
(function (window, RSVP, rJS, Handlebars, loopEventListener, URL) {
"use strict";
function saveContent(gadget, submit_event) {
var i,
doc = gadget.options.doc,
now = new Date(),
blob;
doc.parent_relative_url = "image_module";
doc.portal_type = "Image";
doc.modification_date = now.toISOString();
for (i = 0; i < submit_event.target.length; i += 1) {
// XXX Should check input type instead
if (submit_event.target[i].name) {
doc[submit_event.target[i].name] = submit_event.target[i].value;
}
}
return RSVP.Queue()
.push(function () {
return gadget.getDeclaredGadget("my_text_content");
})
.push(function (text_content_gadget) {
return text_content_gadget.getContent();
})
.push(function (dataURI) {
return jIO.util.dataURItoBlob(dataURI);
})
.push(function(blob) {
console.log(gadget.options.jio_key);
return RSVP.all([
gadget.put(gadget.options.jio_key, doc),
gadget.putAttachment(gadget.options.jio_key, "data", blob)
]);
});
}
function maximize(gadget) {
var iframe = gadget.props.element.querySelector('iframe'),
iframe_class_string = iframe.getAttribute('class') || "",
class_name = "ui-content-maximize",
class_index = iframe_class_string.indexOf(class_name);
if (class_index === -1) {
iframe_class_string += ' ' + class_name;
iframe.setAttribute('style', '');
iframe.setAttribute('class', iframe_class_string);
return;
}
iframe_class_string = iframe_class_string.substring(0, class_index)
+ iframe_class_string.substring(class_index + class_name.length);
iframe.setAttribute('style', 'width:100%; border: 0 none; height: 600px');
iframe.setAttribute('class', iframe_class_string);
return;
}
var gadget_klass = rJS(window),
source = gadget_klass.__template_element
.querySelector(".view-web-page-template")
.innerHTML,
template = Handlebars.compile(source);
gadget_klass
.ready(function (g) {
g.props = {};
g.options = null;
return g.getElement()
.push(function (element) {
g.props.element = element;
g.props.deferred = RSVP.defer();
});
})
.declareAcquiredMethod("updateHeader", "updateHeader")
.declareAcquiredMethod("get", "jio_get")
.declareAcquiredMethod("translateHtml", "translateHtml")
.declareAcquiredMethod("put", "jio_put")
.declareAcquiredMethod("putAttachment", "jio_putAttachment")
.declareAcquiredMethod("getAttachment", "jio_getAttachment")
.declareAcquiredMethod("redirect", "redirect")
.allowPublicAcquisition('triggerMaximize', function () {
var gadget = this;
return RSVP.Queue()
.push(function () {
return maximize(gadget);
})
.fail(function (e) {
console.log(e);
});
})
.allowPublicAcquisition('triggerSubmit', function (option) {
if (option[0] === "maximize" || option === "maximize") {
var gadget = this;
return RSVP.Queue()
.push(function () {
return maximize(gadget);
});
}
return this.props.element.querySelector('button').click();
})
.declareMethod('triggerSubmit', function (option) {
if (option[0] === "maximize" || option === "maximize") {
var gadget = this;
return RSVP.Queue()
.push(function () {
return maximize(gadget);
});
}
return this.props.element.querySelector('button').click();
})
.declareMethod("render", function (options) {
var gadget = this;
gadget.options = options;
gadget.options.doc.title = gadget.options.doc.title || "";
return new RSVP.Queue()
.push(function () {
return gadget.translateHtml(template(options.doc));
})
.push(function (html) {
gadget.props.element.innerHTML = html;
return gadget.updateHeader({
title: options.doc.title + " | Image",
save_action: true,
maximize_action: true,
maximized: gadget.options.doc.title !== ""
});
})
.push(function() {
return gadget.getAttachment(gadget.options.jio_key, "data");
})
.push(
function (blob_result) {
gadget.props.blob = blob_result;
return gadget.props.deferred.resolve();
}, function (error) {
if (error.status_code === 404) {
gadget.props.blob = new Blob([''], {type: 'image/png'});
return gadget.props.deferred.resolve();
}
throw new Error(error);
});
})
/////////////////////////////////////////
// Render text content gadget
/////////////////////////////////////////
.declareService(function () {
var gadget = this,
image_content_gadget;
return new RSVP.Queue()
.push(function () {
return gadget.props.deferred.promise;
})
.push(function () {
return gadget.declareGadget(
"rjsunsafe/gadget_image_editor.html",
{
scope: "my_text_content",
sandbox: "iframe",
element: gadget.props.element.querySelector(".document-content")
}
);
})
.push(function (image_gadget) {
image_content_gadget = image_gadget;
var iframe = gadget.props.element.querySelector('iframe');
iframe.setAttribute(
'style',
'width:100%; border: 0 none; height: 600px'
);
return jIO.util.readBlobAsDataURL(gadget.props.blob);
})
.push(function (f) {
return image_content_gadget.render({
"key": 'text_content',
"value": f.target.result,
"name": gadget.options.jio_key
});
})
.push(function () {
if (gadget.options.doc.title !== "") {
return gadget.triggerSubmit("maximize");
}
})
.push(undefined, function (error) {
var display_error_element;
if (error === "Timed out after 5000 ms") {
display_error_element =
gadget.props.element.querySelector(
"form div.ui-field-contain fieldset"
);
display_error_element.innerHTML =
'<br/><p style="color: red"></p><br/><br/>';
display_error_element.querySelector('p').textContent =
"TIMEOUT: The editor gadget is taking too long to load but is" +
" currently being cached, please wait for the page to load" +
" (check your browser loading icon) and then refresh.";
} else {
throw error;
}
});
})
/////////////////////////////////////////
// Form submit
/////////////////////////////////////////
.declareService(function () {
var gadget = this;
return new RSVP.Queue()
.push(function () {
return gadget.props.deferred.promise;
})
.push(function () {
return loopEventListener(
gadget.props.element.querySelector('form'),
'submit',
true,
function (event) {
return saveContent(gadget, event);
}
);
});
});
}(window, RSVP, rJS, Handlebars, loopEventListener, URL));
\ No newline at end of file
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>miniPaint</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
/**
* main config file
*
* @author ViliusL
*/
//canvas layers
var canvas_back = document.getElementById("canvas_back").getContext("2d"); //layer for grid/transparency
var canvas_front = document.getElementById("canvas_front").getContext("2d"); //tmp layer
var canvas_grid = document.getElementById("canvas_grid").getContext("2d"); //grid layer
var canvas_preview = document.getElementById("canvas_preview").getContext("2d"); //mini preview
//global settings
var VERSION = '3.2';
var WIDTH; //canvas midth
var HEIGHT; //canvas height
var COLOR = '#0000ff'; //active color
var ALPHA = 255; //active color alpha
var LANG = 'en'; //active language
var DRAW_TOOLS_CONFIG = [
{name: 'select_tool', title: 'Select object tool', icon: ['sprites.png', 0+7, 2], attributes: {} },
{name: 'select_square', title: 'Select area tool', icon: ['sprites.png', -50+4, 5], attributes: {} },
{name: 'magic_wand', title: 'Magic Wand Tool', icon: ['sprites.png', -150+1, -50+2], attributes: {power: 40, anti_aliasing: true} },
{name: 'erase', title: 'Erase', icon: ['sprites.png', -100+3, 4], attributes: {size: 30, circle: true, strict: true} },
{name: 'fill', title: 'Fill', icon: ['sprites.png', -150+3, 3], attributes: {power: 0, anti_aliasing: false} },
{name: 'pick_color', title: 'Pick Color', icon: ['sprites.png', -200+3, 3], attributes: {} },
{name: 'pencil', title: 'Pencil', icon: ['sprites.png', -250+3, 3], attributes: {} },
{name: 'line', title: 'Draw line', icon: ['sprites.png', -300+3, 3], attributes: {size: 1, type_values: ['Simple', 'Multi-line', 'Arrow', 'Curve'] } },
{name: 'letters', title: 'Draw letters', icon: ['sprites.png', -350+3, 4], attributes: {} },
{name: 'draw_square', title: 'Draw rectangle', icon: ['sprites.png', -400+3, 5], attributes: {fill: false, square: false} },
{name: 'draw_circle', title: 'Draw circle', icon: ['sprites.png', -450+3, 5], attributes: {fill: false, circle: false} },
{name: 'brush', title: 'Brush', icon: ['sprites.png', -500+6, 3], attributes: {type: 'Brush', type_values: ['Brush', 'BezierCurve', 'Chrome', 'Fur', 'Grouped', 'Shaded', 'Sketchy'], size: 10, anti_aliasing: false }, on_update: 'update_brush', },
{name: 'blur_tool', title: 'Blur tool', icon: ['sprites.png', -250+5, -50+2], attributes: {size: 30, power: 1} },
{name: 'sharpen_tool', title: 'Sharpen tool', icon: ['sprites.png', -300+5, -50+2], attributes: {size: 30 } },
{name: 'burn_dodge_tool', title: 'Burn/Dodge tool', icon: ['sprites.png', -500+3, -50+4], attributes: {burn: true, size: 30, power: 50} },
{name: 'desaturate_tool', title: 'Desaturate', icon: ['sprites.png', -550+3, -00+4], attributes: {size: 50, anti_aliasing: true} },
{name: 'bulge_pinch_tool',title: 'Bulge/Pinch tool', icon: ['sprites.png', -450+3, -100+3], attributes: {size: 50, radius: 80, bulge:true} },
{name: 'clone_tool', title: 'Clone tool', icon: ['sprites.png', -350+4, -50+3], attributes: {size: 30, anti_aliasing: true} },
{name: 'gradient_tool', title: 'Gradient', icon: ['sprites.png', -400+3, -50+4], attributes: {radial: false, power: 50} },
{name: 'crop_tool', title: 'Crop', icon: ['sprites.png', -450+2, -50+2], attributes: { } },
];
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>config.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>img</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>colorwheel.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>favicon.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>logo.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>preview.jpg</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/jpeg</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>right.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>sprites.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>js</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>draw_tools.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
/* global MAIN, POP, LAYER, DRAW, GUI */
/* global WIDTH, HEIGHT, canvas_active, canvas_front */
var EDIT = new EDIT_CLASS();
/**
* manages edit actions
*
* @author ViliusL
*/
function EDIT_CLASS() {
/**
* used to store internal copied objects data
*/
var PASTE_DATA = false;
/**
* latest 3 saved states of all layers for undo
*/
var layers_archive = [{}, {}, {}];
/**
* on undo, current data index in layers_archive array
*/
var undo_level = 0;
//undo
this.edit_undo = function () {
this.undo();
};
//cut
this.edit_cut = function () {
this.save_state();
if (DRAW.select_data != false) {
this.copy_to_clipboard();
canvas_active().clearRect(DRAW.select_data.x, DRAW.select_data.y, DRAW.select_data.w, DRAW.select_data.h);
DRAW.select_data = false;
canvas_front.clearRect(0, 0, WIDTH, HEIGHT);
}
};
//copy
this.edit_copy = function () {
if (DRAW.select_data != false) {
this.copy_to_clipboard();
}
};
//paste
this.edit_paste = function () {
this.save_state();
this.paste('menu');
};
//select all
this.edit_select = function () {
DRAW.select_data = {
x: 0,
y: 0,
w: WIDTH,
h: HEIGHT
};
canvas_front.clearRect(0, 0, WIDTH, HEIGHT);
GUI.draw_selected_area();
};
//clear selection
this.edit_clear = function () {
DRAW.select_data = false;
canvas_front.clearRect(0, 0, WIDTH, HEIGHT);
DRAW.select_square_action = '';
};
this.copy_to_clipboard = function () {
PASTE_DATA = false;
PASTE_DATA = document.createElement("canvas");
PASTE_DATA.width = DRAW.select_data.w;
PASTE_DATA.height = DRAW.select_data.h;
PASTE_DATA.getContext("2d").drawImage(canvas_active(true), DRAW.select_data.x, DRAW.select_data.y, DRAW.select_data.w, DRAW.select_data.h, 0, 0, DRAW.select_data.w, DRAW.select_data.h);
};
this.paste = function (type) {
if (PASTE_DATA == false) {
if (type == 'menu') {
POP.add({title: "Error:", value: 'Empty data'});
POP.add({title: "Notice:", value: 'To paste from clipboard, use Ctrl-V.'});
POP.show('Notice', '');
}
return false;
}
tmp = new Array();
var new_name = LAYER.generate_layer_name();
LAYER.create_canvas(new_name);
LAYER.layers.unshift({name: new_name, title: new_name, visible: true});
LAYER.layer_active = 0;
canvas_active().drawImage(PASTE_DATA, 0, 0);
LAYER.layer_renew();
EDIT.edit_clear();
};
this.save_state = function () {
undo_level = 0;
j = 0;
//move previous
layers_archive[2] = layers_archive[1];
layers_archive[1] = layers_archive[0];
//save last state
layers_archive[j] = {};
layers_archive[j].width = WIDTH;
layers_archive[j].height = HEIGHT;
//layers
layers_archive[j].layers = [];
for(var i = LAYER.layers.length-1; i >=0; i--){
var layer = {
name: LAYER.layers[i].name,
title: LAYER.layers[i].title,
visible: 1,
opacity: LAYER.layers[i].opacity,
};
if (LAYER.layers[i].visible == false)
layer.visible = 0;
layers_archive[j].layers.push(layer);
}
layers_archive[j].data = {};
for (var i in LAYER.layers) {
layers_archive[j].data[LAYER.layers[i].name] = document.createElement('canvas');
layers_archive[j].data[LAYER.layers[i].name].width = WIDTH;
layers_archive[j].data[LAYER.layers[i].name].height = HEIGHT;
layers_archive[j].data[LAYER.layers[i].name].getContext('2d').drawImage(document.getElementById(LAYER.layers[i].name), 0, 0);
}
};
//supports 3 levels undo system - more levels requires more memory
this.undo = function () {
if (layers_archive.length == 0){
//not saved yet
return false;
}
j = undo_level;
undo_level++;
if (layers_archive[j] == undefined || layers_archive[j].width == undefined){
//no such data
return false;
}
LAYER.remove_all_layers();
if (WIDTH != layers_archive[j].width || HEIGHT != layers_archive[j].height) {
WIDTH = layers_archive[j].width;
HEIGHT = layers_archive[j].height;
LAYER.set_canvas_size(true);
}
//add layers
for(var i in layers_archive[j].layers){
var layer = layers_archive[j].layers[i];
var name = layer.name;
var title = layer.title;
var visible = parseInt(layer.visible);
var opacity = parseInt(layer.opacity);
LAYER.layer_add(name);
//update attributes
LAYER.layers[LAYER.layer_active].title = title;
if (visible == 0)
LAYER.layer_visibility(LAYER.layer_active);
LAYER.layers[LAYER.layer_active].opacity = opacity;
}
LAYER.layer_renew();
//undo
for (var i = LAYER.layers.length-1; i >= 0; i--) {
//restore data
document.getElementById(LAYER.layers[i].name).getContext("2d").clearRect(0, 0, WIDTH, HEIGHT);
document.getElementById(LAYER.layers[i].name).getContext("2d").drawImage(layers_archive[j].data[LAYER.layers[i].name], 0, 0);
}
GUI.zoom();
};
}
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>edit.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>effects.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>elements.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>events.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>__name__</string> </key>
<value> <string>file.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
// https://github.com/eligrey/FileSaver.js - 1.3.2
var saveAs=saveAs||function(e){"use strict";if(typeof e==="undefined"||typeof navigator!=="undefined"&&/MSIE [1-9]\./.test(navigator.userAgent)){return}var t=e.document,n=function(){return e.URL||e.webkitURL||e},r=t.createElementNS("http://www.w3.org/1999/xhtml","a"),o="download"in r,i=function(e){var t=new MouseEvent("click");e.dispatchEvent(t)},a=/constructor/i.test(e.HTMLElement),f=/CriOS\/[\d]+/.test(navigator.userAgent),u=function(t){(e.setImmediate||e.setTimeout)(function(){throw t},0)},d="application/octet-stream",s=1e3*40,c=function(e){var t=function(){if(typeof e==="string"){n().revokeObjectURL(e)}else{e.remove()}};setTimeout(t,s)},l=function(e,t,n){t=[].concat(t);var r=t.length;while(r--){var o=e["on"+t[r]];if(typeof o==="function"){try{o.call(e,n||e)}catch(i){u(i)}}}},p=function(e){if(/^\s*(?:text\/\S*|application\/xml|\S*\/\S*\+xml)\s*;.*charset\s*=\s*utf-8/i.test(e.type)){return new Blob([String.fromCharCode(65279),e],{type:e.type})}return e},v=function(t,u,s){if(!s){t=p(t)}var v=this,w=t.type,m=w===d,y,h=function(){l(v,"writestart progress write writeend".split(" "))},S=function(){if((f||m&&a)&&e.FileReader){var r=new FileReader;r.onloadend=function(){var t=f?r.result:r.result.replace(/^data:[^;]*;/,"data:attachment/file;");var n=e.open(t,"_blank");if(!n)e.location.href=t;t=undefined;v.readyState=v.DONE;h()};r.readAsDataURL(t);v.readyState=v.INIT;return}if(!y){y=n().createObjectURL(t)}if(m){e.location.href=y}else{var o=e.open(y,"_blank");if(!o){e.location.href=y}}v.readyState=v.DONE;h();c(y)};v.readyState=v.INIT;if(o){y=n().createObjectURL(t);setTimeout(function(){r.href=y;r.download=u;i(r);h();c(y);v.readyState=v.DONE});return}S()},w=v.prototype,m=function(e,t,n){return new v(e,t||e.name||"download",n)};if(typeof navigator!=="undefined"&&navigator.msSaveOrOpenBlob){return function(e,t,n){t=t||e.name||"download";if(!n){e=p(e)}return navigator.msSaveOrOpenBlob(e,t)}}w.abort=function(){};w.readyState=w.INIT=0;w.WRITING=1;w.DONE=2;w.error=w.onwritestart=w.onprogress=w.onwrite=w.onabort=w.onerror=w.onwriteend=null;return m}(typeof self!=="undefined"&&self||typeof window!=="undefined"&&window||this.content);if(typeof module!=="undefined"&&module.exports){module.exports.saveAs=saveAs}else if(typeof define!=="undefined"&&define!==null&&define.amd!==null){define([],function(){return saveAs})}
\ No newline at end of file
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment