Improve opening files and error handling
Use URL.createObjectURL() instead of creating a FileReader and reading as a data URL Add a bunch of error handling around opening files Make GIF rendering errors use new show_error_message function Remove some old bits from intending to use Web Intentsmain
parent
2175e94397
commit
aa4364ddf9
|
@ -39,7 +39,6 @@
|
|||
<link rel="icon" href="images/icons/128.png" sizes="128x128" type="image/png">
|
||||
<link rel="icon" href="images/icons/windows.ico" sizes="16x16,32x32,48x48" type="image/icon">
|
||||
<meta name="viewport" content="width=device-width, user-scalable=no">
|
||||
<intent action="http://webintents.org/edit" type="image/*"></intent>
|
||||
</head>
|
||||
<body>
|
||||
<script src="lib/jquery.min.js"></script>
|
||||
|
|
|
@ -121,7 +121,7 @@ function $ColorBox(){
|
|||
$c.edit_last_color = function(){
|
||||
// Edit the last color cell that's been selected as the foreground color.
|
||||
create_and_trigger_input({type: "color"}, function(input){
|
||||
console.log(input, input.value);
|
||||
// console.log(input, input.value);
|
||||
$last_fg_color_button.trigger({type: "pointerdown", ctrlKey: false, button: 0});
|
||||
$last_fg_color_button.find("input").val(input.value).triggerHandler("change");
|
||||
})
|
||||
|
|
|
@ -83,8 +83,6 @@ reset_magnification();
|
|||
|
||||
if(window.file_entry){
|
||||
open_from_FileEntry(window.file_entry);
|
||||
}else if(window.intent){
|
||||
open_from_URI(window.intent.data);
|
||||
}
|
||||
|
||||
$canvas.on("user-resized", function(e, _x, _y, width, height){
|
||||
|
@ -150,7 +148,11 @@ $("body").on("dragover dragenter", function(e){
|
|||
e.preventDefault();
|
||||
var dt = e.originalEvent.dataTransfer;
|
||||
if(dt && dt.files && dt.files.length){
|
||||
open_from_FileList(dt.files);
|
||||
open_from_FileList(dt.files, function(err){
|
||||
if(err){
|
||||
show_error_message("Failed to open file:", err);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -2,15 +2,15 @@
|
|||
(function(){
|
||||
|
||||
var may_be_changed = function(){
|
||||
console.log("change may have occured");
|
||||
window.console && console.log("change may have occured");
|
||||
$canvas.triggerHandler("change");
|
||||
};
|
||||
|
||||
var debug_event = function(e, synthetic){
|
||||
if(synthetic){
|
||||
console.debug(e.type + " (synthetic)");
|
||||
window.console && console.debug && console.debug(e.type + " (synthetic)");
|
||||
}else{
|
||||
console.debug(e.type + " (not synthetic)");
|
||||
window.console && console.debug && console.debug(e.type + " (not synthetic)");
|
||||
}
|
||||
};
|
||||
|
||||
|
|
114
src/functions.js
114
src/functions.js
|
@ -65,7 +65,7 @@ function get_FileList(callback){
|
|||
});
|
||||
}
|
||||
|
||||
function open_from_Image(img, callback){
|
||||
function open_from_Image(img, callback, canceled){
|
||||
are_you_sure(function(){
|
||||
this_ones_a_frame_changer();
|
||||
|
||||
|
@ -79,40 +79,54 @@ function open_from_Image(img, callback){
|
|||
$canvas_area.trigger("resize");
|
||||
|
||||
callback && callback();
|
||||
});
|
||||
}, canceled);
|
||||
}
|
||||
function open_from_URI(uri, callback){
|
||||
function open_from_URI(uri, callback, canceled){
|
||||
var img = new Image();
|
||||
img.onload = function(){
|
||||
open_from_Image(img, callback);
|
||||
if(!this.complete || typeof this.naturalWidth == "undefined" || this.naturalWidth == 0){
|
||||
return callback() && callback(new Error("Image failed to load; naturalWidth == " + this.naturalWidth));
|
||||
}
|
||||
open_from_Image(img, callback, canceled);
|
||||
};
|
||||
img.onerror = function(){
|
||||
callback && callback(new Error("Image failed to load"));
|
||||
};
|
||||
img.src = uri;
|
||||
}
|
||||
function open_from_File(file, callback){
|
||||
// @TODO: use URL.createObjectURL(file) when available
|
||||
// use URL.revokeObjectURL() too
|
||||
var reader = new FileReader();
|
||||
reader.onload = function(e){
|
||||
open_from_URI(e.target.result, function(){
|
||||
file_name = file.name;
|
||||
update_title();
|
||||
saved = true;
|
||||
callback && callback();
|
||||
});
|
||||
};
|
||||
reader.readAsDataURL(file);
|
||||
var url = URL.createObjectURL(file);
|
||||
open_from_URI(url, function(err){
|
||||
console.log("opened or error, revokeObjectURL");
|
||||
URL.revokeObjectURL(file);
|
||||
if(err){ return callback && callback(err); }
|
||||
file_name = file.name;
|
||||
update_title();
|
||||
saved = true;
|
||||
callback && callback();
|
||||
}, function(){
|
||||
console.log("canceled, revokeObjectURL");
|
||||
URL.revokeObjectURL(file);
|
||||
});
|
||||
}
|
||||
function open_from_FileList(files, callback){
|
||||
$.each(files, function(i, file){
|
||||
if(file.type.match(/image/)){
|
||||
for(var i=0; i<files.length; i++){
|
||||
var file = files[i];
|
||||
if(file.type.match(/^image/)){
|
||||
open_from_File(file, callback);
|
||||
return false;
|
||||
return;
|
||||
}
|
||||
});
|
||||
}
|
||||
if(files.length > 1){
|
||||
callback(new Error("None of the given files appear to be images"));
|
||||
}else{
|
||||
callback(new Error("File does not appear to be an image"));
|
||||
}
|
||||
}
|
||||
function open_from_FileEntry(entry, callback){
|
||||
entry.file(function(file){
|
||||
open_from_File(file, function(){
|
||||
open_from_File(file, function(err){
|
||||
if(err){ return callback && callback(err); }
|
||||
file_entry = entry;
|
||||
callback && callback();
|
||||
});
|
||||
|
@ -146,6 +160,11 @@ function file_new(){
|
|||
}
|
||||
|
||||
function file_open(){
|
||||
var callback = function(err){
|
||||
if(err){
|
||||
show_error_message("Failed to open file:", err);
|
||||
}
|
||||
};
|
||||
if(window.chrome && chrome.fileSystem && chrome.fileSystem.chooseEntry){
|
||||
chrome.fileSystem.chooseEntry({
|
||||
type: "openFile",
|
||||
|
@ -155,10 +174,12 @@ function file_open(){
|
|||
if(chrome.runtime.lastError){
|
||||
return console.error(chrome.runtime.lastError.message);
|
||||
}
|
||||
open_from_FileEntry(entry);
|
||||
open_from_FileEntry(entry, callback);
|
||||
});
|
||||
}else{
|
||||
get_FileList(open_from_FileList);
|
||||
get_FileList(function(files){
|
||||
open_from_FileList(files, callback);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -202,7 +223,7 @@ function file_save_as(){
|
|||
}
|
||||
|
||||
|
||||
function are_you_sure(action){
|
||||
function are_you_sure(action, canceled){
|
||||
if(saved){
|
||||
action();
|
||||
}else{
|
||||
|
@ -220,11 +241,37 @@ function are_you_sure(action){
|
|||
});
|
||||
$w.$Button("Cancel", function(){
|
||||
$w.close();
|
||||
canceled && canceled();
|
||||
});
|
||||
$w.$x.on("click", function(){
|
||||
canceled && canceled();
|
||||
});
|
||||
$w.center();
|
||||
}
|
||||
}
|
||||
|
||||
function show_error_message(message, error){
|
||||
$w = $FormWindow().title("Error").addClass("jspaint-dialogue-window");
|
||||
$w.$main.text(message);
|
||||
$(E("pre"))
|
||||
.appendTo($w.$main)
|
||||
.text(error.stack || error.toString())
|
||||
.css({
|
||||
background: "white",
|
||||
color: "#333",
|
||||
// background: "#A00",
|
||||
// color: "white",
|
||||
fontFamily: "monospace",
|
||||
width: "500px",
|
||||
overflow: "auto",
|
||||
});
|
||||
$w.$Button("OK", function(){
|
||||
$w.close();
|
||||
});
|
||||
console.error(message, error);
|
||||
}
|
||||
|
||||
|
||||
function paste_file(blob){
|
||||
var reader = new FileReader();
|
||||
reader.onload = function(e){
|
||||
|
@ -232,6 +279,7 @@ function paste_file(blob){
|
|||
img.onload = function(){
|
||||
paste(img);
|
||||
};
|
||||
// TODO: error handling
|
||||
img.src = e.target.result;
|
||||
};
|
||||
reader.readAsDataURL(blob);
|
||||
|
@ -357,21 +405,9 @@ function render_history_as_gif(){
|
|||
});
|
||||
gif.render();
|
||||
|
||||
}catch(e){
|
||||
$output.empty().append(
|
||||
$(E("p")).text("Failed to render GIF:\n").append(
|
||||
$(E("pre")).text(e.stack).css({
|
||||
background: "#A00",
|
||||
color: "white",
|
||||
fontFamily: "monospace",
|
||||
width: "500px",
|
||||
overflow: "auto",
|
||||
})
|
||||
)
|
||||
);
|
||||
$win.title("Error Rendering GIF");
|
||||
$win.center();
|
||||
console.error("Failed to render GIF:\n", e);
|
||||
}catch(err){
|
||||
$win.close();
|
||||
show_error_message("Failed to render GIF:", err);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -18,15 +18,14 @@
|
|||
|
||||
storage.get(lsid, function(err, uri){
|
||||
if(err){
|
||||
$w = $FormWindow().title("Error").addClass("jspaint-dialogue-window");
|
||||
$w.$main.text("Error retrieving image from localStorage:");
|
||||
$(E("pre")).text(err.toString()).appendTo($w.$main);
|
||||
$w.$Button("OK", function(){
|
||||
$w.close();
|
||||
});
|
||||
show_error_message("Error retrieving image from localStorage:", err);
|
||||
}else if(uri){
|
||||
open_from_URI(uri, function(){
|
||||
saved = false; // it's safe, sure, but you haven't "Saved" it
|
||||
open_from_URI(uri, function(err){
|
||||
if(err){
|
||||
show_error_message("Error opening image from localStorage:", err);
|
||||
}else{
|
||||
saved = false; // it may be safe, sure, but you haven't "Saved" it
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
|
@ -273,7 +272,7 @@
|
|||
// and other options will be established)
|
||||
|
||||
// Playback recorded in-progress pointer operations
|
||||
console.log("playback", pointer_operations);
|
||||
window.console && console.log("playback", pointer_operations);
|
||||
for(var i=0; i<pointer_operations.length; i++){
|
||||
var e = pointer_operations[i];
|
||||
// Trigger the event at each place it is listened for
|
||||
|
|
Loading…
Reference in New Issue