Merge pull request #22 from 0x0ade/master
Implement serialization, clipboard
This commit is contained in:
commit
e4ebf1e3d0
1
.gitignore
vendored
1
.gitignore
vendored
@ -1,2 +1,3 @@
|
||||
node_modules/
|
||||
builds/
|
||||
package-lock.json
|
||||
|
@ -9,6 +9,7 @@
|
||||
<script type="text/javascript" src="scripts/keyboard.js"></script>
|
||||
<script type="text/javascript" src="scripts/guide.js"></script>
|
||||
<script type="text/javascript" src="scripts/render.js"></script>
|
||||
<script type="text/javascript" src="scripts/serializer.js"></script>
|
||||
<script type="text/javascript" src="scripts/theme.js"></script>
|
||||
<script type="text/javascript" src="scripts/interface.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="links/reset.css"/>
|
||||
@ -31,6 +32,8 @@
|
||||
document.addEventListener('mousedown', function(e){ dotgrid.mouse_down(e); }, false);
|
||||
document.addEventListener('mousemove', function(e){ dotgrid.mouse_move(e); }, false);
|
||||
document.addEventListener('mouseup', function(e){ dotgrid.mouse_up(e);}, false);
|
||||
document.addEventListener('copy', function(e){ dotgrid.copy(e);}, false);
|
||||
document.addEventListener('paste', function(e){ dotgrid.paste(e);}, false);
|
||||
</script>
|
||||
</div>
|
||||
</body>
|
||||
|
@ -44,6 +44,7 @@ function Dotgrid(width,height,grid_x,grid_y,block_x,block_y,thickness = 3,lineca
|
||||
|
||||
this.guide = new Guide();
|
||||
this.render = new Render();
|
||||
this.serializer = new Serializer();
|
||||
|
||||
this.path = document.createElementNS("http://www.w3.org/2000/svg", "path");
|
||||
this.segments = [];
|
||||
@ -479,6 +480,47 @@ function Dotgrid(width,height,grid_x,grid_y,block_x,block_y,thickness = 3,lineca
|
||||
});
|
||||
}
|
||||
|
||||
this.copy = function(e)
|
||||
{
|
||||
if(this.segments.length == 0){ return; }
|
||||
this.scale = 1
|
||||
this.width = 300
|
||||
this.height = 300
|
||||
this.draw()
|
||||
var svg = this.svg_el.outerHTML
|
||||
|
||||
e.clipboardData.items.add(JSON.stringify({ dotgrid: this.serializer.serialize() }), "text/plain");
|
||||
|
||||
e.clipboardData.items.add(svg, "text/html");
|
||||
e.clipboardData.items.add(svg, "text/svg+xml");
|
||||
|
||||
// Right now, the following doesn't work and breaks "text/plain".
|
||||
// This seems to be a bug in Chromium as others around the web complain, too.
|
||||
/*
|
||||
e.clipboardData.items.add(new File([new Blob([svg], { type: "image/svg+xml" } )], "image.svg"));
|
||||
e.clipboardData.items.add(new File([new Blob([Uint8Array.from(dotgrid.render.buffer()).buffer], { type: "image/png" } ) ], "image.png"));
|
||||
*/
|
||||
|
||||
e.preventDefault();
|
||||
}
|
||||
|
||||
this.paste = function(e)
|
||||
{
|
||||
var data = e.clipboardData.getData("text/plain");
|
||||
try {
|
||||
data = JSON.parse(data.trim()).dotgrid;
|
||||
if (!data) throw null;
|
||||
} catch (err) {
|
||||
// Not a dotgrid JSON.
|
||||
return;
|
||||
}
|
||||
|
||||
this.serializer.deserialize(data);
|
||||
|
||||
this.resize();
|
||||
this.draw();
|
||||
}
|
||||
|
||||
// Normalizers
|
||||
|
||||
this.position_in_grid = function(pos)
|
||||
|
@ -1,5 +1,6 @@
|
||||
function Path_Arc(from,to,orientation,end)
|
||||
{
|
||||
this.__serialized_name__ = "Path_Arc";
|
||||
this.name = "arc";
|
||||
|
||||
this.from = from;
|
||||
|
@ -1,5 +1,6 @@
|
||||
function Path_Bezier(from,to,end)
|
||||
{
|
||||
this.__serialized_name__ = "Path_Bezier";
|
||||
this.name = "bezier";
|
||||
|
||||
this.from = from;
|
||||
|
@ -1,5 +1,6 @@
|
||||
function Path_Close()
|
||||
{
|
||||
this.__type_ = "Path_Close";
|
||||
this.name = "close";
|
||||
|
||||
this.to_segment = function(prev)
|
||||
|
@ -1,5 +1,6 @@
|
||||
function Path_Line(from,to,end = null)
|
||||
{
|
||||
this.__serialized_name__ = "Path_Line";
|
||||
this.name = "line";
|
||||
|
||||
this.from = from;
|
||||
|
@ -1,5 +1,6 @@
|
||||
function Pos(x,y)
|
||||
{
|
||||
this.__serialized_name__ = ".";
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
|
||||
@ -40,3 +41,7 @@ function Pos(x,y)
|
||||
|
||||
function clamp(v, min, max) { return v < min ? min : v > max ? max : v; }
|
||||
}
|
||||
|
||||
// This is ugly, but Pos.__serialized_name__ == ".";
|
||||
// Let's keep the character count low.
|
||||
window["."] = Pos;
|
91
sources/scripts/serializer.js
Normal file
91
sources/scripts/serializer.js
Normal file
@ -0,0 +1,91 @@
|
||||
function Serializer()
|
||||
{
|
||||
var __data_segments__ = 0;
|
||||
var __data_thickness__ = 1;
|
||||
var __data_linecap__ = 2;
|
||||
var __data_color__ = 3;
|
||||
var __data_mirror_index__ = 4;
|
||||
var __data_fill__ = 5;
|
||||
|
||||
this.serialize = function()
|
||||
{
|
||||
// Store the data in an array.
|
||||
// This keeps away the property names, which just clutter up everything.
|
||||
var data = [
|
||||
[],
|
||||
dotgrid.thickness,
|
||||
dotgrid.linecap,
|
||||
dotgrid.color,
|
||||
dotgrid.mirror_index,
|
||||
dotgrid.fill
|
||||
];
|
||||
|
||||
for (var id in dotgrid.segments) {
|
||||
data[__data_segments__][id] = this.serialize_segment(dotgrid.segments[id]);
|
||||
}
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
this.deserialize = function(data)
|
||||
{
|
||||
if (data[__data_segments__]) {
|
||||
for (var id in data[__data_segments__]) {
|
||||
data[__data_segments__][id] = this.deserialize_segment(data[__data_segments__][id]);
|
||||
}
|
||||
}
|
||||
|
||||
var d = (index, fallback) => index < data.length ? data[index] : fallback;
|
||||
|
||||
dotgrid.segments = d(__data_segments__, []);
|
||||
dotgrid.thickness = d(__data_thickness__, 10);
|
||||
dotgrid.linecap = d(__data_linecap__, "square");
|
||||
dotgrid.color = d(__data_color__, "#000000");
|
||||
dotgrid.mirror_index = d(__data_mirror_index__, 0);
|
||||
dotgrid.fill = d(__data_fill__, false);
|
||||
}
|
||||
|
||||
this.serialize_segment = function(s) {
|
||||
// Return falsy values (null, 0, false, "", ...) directly.
|
||||
if (!s) return s;
|
||||
|
||||
var data = [";"];
|
||||
// Get rid of non-serializable stuff (i.e. functions).
|
||||
s = JSON.parse(JSON.stringify(s));
|
||||
// Store everything in arrays instead of objects, saving characters.
|
||||
for (var id in s) {
|
||||
// Skip the non-serialzied path name.
|
||||
if (s.__serialized_name__ && id === "name")
|
||||
continue;
|
||||
|
||||
var prop = s[id];
|
||||
|
||||
if (typeof(prop) === "object") {
|
||||
prop = this.serialize_segment(prop);
|
||||
}
|
||||
|
||||
data.push(prop);
|
||||
}
|
||||
return data;
|
||||
}
|
||||
|
||||
this.deserialize_segment = function(data) {
|
||||
var name = data.splice(0, 2)[1];
|
||||
|
||||
// Unserialize anything that's serialized.
|
||||
for (var id in data) {
|
||||
var prop = data[id];
|
||||
|
||||
if (prop && typeof(prop) === "object" && prop.length && prop[0] === ";") {
|
||||
prop = this.deserialize_segment(prop);
|
||||
}
|
||||
|
||||
data[id] = prop;
|
||||
}
|
||||
|
||||
var s = {};
|
||||
window[name].apply(s, data);
|
||||
return s;
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user