Merge pull request #485 from code-dot-org/import-service

Extract import logic to ImportService
This commit is contained in:
Julian Descottes 2016-06-17 09:46:32 +01:00 committed by GitHub
commit b1fcc68924
4 changed files with 142 additions and 73 deletions

View File

@ -124,6 +124,8 @@
this.storageService = new pskl.service.storage.StorageService(this.piskelController); this.storageService = new pskl.service.storage.StorageService(this.piskelController);
this.storageService.init(); this.storageService.init();
this.importService = new pskl.service.ImportService(this.piskelController, this.previewController);
this.imageUploadService = new pskl.service.ImageUploadService(); this.imageUploadService = new pskl.service.ImageUploadService();
this.imageUploadService.init(); this.imageUploadService.init();

View File

@ -171,84 +171,26 @@
}; };
ns.ImportImageController.prototype.importImageToPiskel_ = function () { ns.ImportImageController.prototype.importImageToPiskel_ = function () {
var image = this.importedImage_; if (this.importedImage_) {
if (image) {
if (window.confirm('You are about to create a new Piskel, unsaved changes will be lost.')) { if (window.confirm('You are about to create a new Piskel, unsaved changes will be lost.')) {
var gifLoader = new window.SuperGif({ pskl.app.importService.newPiskelFromImage(
gif : image this.importedImage_,
}); {
importType: this.getImportType_(),
var resizeW = this.resizeWidth.val(); frameSizeX: this.getImportType_() === 'single' ?
var resizeH = this.resizeHeight.val(); this.resizeWidth.val() : this.sanitizeInputValue_(this.frameSizeX, 1),
frameSizeY: this.getImportType_() === 'single' ?
gifLoader.load({ this.resizeHeight.val() : this.sanitizeInputValue_(this.frameSizeY, 1),
success : function () { frameOffsetX: this.sanitizeInputValue_(this.frameOffsetX, 0),
var images = gifLoader.getFrames().map(function (frame) { frameOffsetY: this.sanitizeInputValue_(this.frameOffsetY, 0),
return pskl.utils.CanvasUtils.createFromImageData(frame.data); smoothing: !!this.smoothResize.prop('checked')
}); },
this.closeDialog.bind(this)
if (this.getImportType_() === 'single' || images.length > 1) { );
// Single image import or animated gif
this.createPiskelFromImages_(images, resizeW, resizeH);
} else {
// Spritesheet
this.createImagesFromSheet_(images[0]);
}
this.closeDialog();
}.bind(this),
error: function () {
if (this.getImportType_() === 'single') {
// Single image
this.createPiskelFromImages_([image], resizeW, resizeH);
} else {
// Spritesheet
this.createImagesFromSheet_(image);
}
this.closeDialog();
}.bind(this)
});
} }
} }
}; };
ns.ImportImageController.prototype.createImagesFromSheet_ = function (image) {
var x = this.sanitizeInputValue_(this.frameOffsetX, 0);
var y = this.sanitizeInputValue_(this.frameOffsetY, 0);
var w = this.sanitizeInputValue_(this.frameSizeX, 1);
var h = this.sanitizeInputValue_(this.frameSizeY, 1);
var images = pskl.utils.CanvasUtils.createFramesFromImage(
image,
x,
y,
w,
h,
/*useHorizonalStrips=*/ true,
/*ignoreEmptyFrames=*/ true);
this.createPiskelFromImages_(images, w, h);
};
ns.ImportImageController.prototype.createFramesFromImages_ = function (images, w, h) {
var smoothing = !!this.smoothResize.prop('checked');
var frames = images.map(function (image) {
var resizedImage = pskl.utils.ImageResizer.resize(image, w, h, smoothing);
return pskl.utils.FrameUtils.createFromImage(resizedImage);
});
return frames;
};
ns.ImportImageController.prototype.createPiskelFromImages_ = function (images, w, h) {
var frames = this.createFramesFromImages_(images, w, h);
var layer = pskl.model.Layer.fromFrames('Layer 1', frames);
var descriptor = new pskl.model.piskel.Descriptor('Imported piskel', '');
var piskel = pskl.model.Piskel.fromLayers([layer], descriptor);
pskl.app.piskelController.setPiskel(piskel);
pskl.app.previewController.setFPS(Constants.DEFAULT.FPS);
};
ns.ImportImageController.prototype.drawFrameGrid_ = function (frameX, frameY, frameW, frameH) { ns.ImportImageController.prototype.drawFrameGrid_ = function (frameX, frameY, frameW, frameH) {
if (!this.importedImage_) { if (!this.importedImage_) {
return; return;

View File

@ -0,0 +1,124 @@
/* @file Image and Animation import service supporting the import dialog. */
(function () {
var ns = $.namespace('pskl.service');
/**
* Image an animation import service supporting the import dialog.
* @param {!PiskelController} piskelController
* @param {!PreviewController} previewController
* @constructor
*/
ns.ImportService =
function (piskelController, previewController) {
this.piskelController_ = piskelController;
this.previewController_ = previewController;
};
/**
* Given an image object and some options, create a new Piskel and open it
* for editing.
* @param {!Image} image
* @param {!Object} options
* @param {!string} options.importType - 'single' if not spritesheet
* @param {!number} options.frameSizeX
* @param {!number} options.frameSizeY
* @param {number} [options.frameOffsetX] only used in spritesheet imports.
* @param {number} [options.frameOffsetY] only used in spritesheet imports.
* @param {!boolean} options.smoothing
* @param {function} [onComplete]
*/
ns.ImportService.prototype.newPiskelFromImage = function (image, options, onComplete) {
onComplete = onComplete || Constants.EMPTY_FUNCTION;
var importType = options.importType;
var frameSizeX = options.frameSizeX;
var frameSizeY = options.frameSizeY;
var frameOffsetX = options.frameOffsetX;
var frameOffsetY = options.frameOffsetY;
var gifLoader = new window.SuperGif({
gif: image
});
gifLoader.load({
success: function () {
var images = gifLoader.getFrames().map(function (frame) {
return pskl.utils.CanvasUtils.createFromImageData(frame.data);
});
if (importType === 'single' || images.length > 1) {
// Single image import or animated gif
this.createPiskelFromImages_(images, frameSizeX, frameSizeY, options.smoothing);
} else {
// Spritesheet
var frameImages = this.createImagesFromSheet_(images[0]);
this.createPiskelFromImages_(frameImages, frameSizeX, frameSizeY, options.smoothing);
}
onComplete();
}.bind(this),
error: function () {
if (importType === 'single') {
// Single image
this.createPiskelFromImages_([image], frameSizeX, frameSizeY, options.smoothing);
} else {
// Spritesheet
var frameImages = this.createImagesFromSheet_(image, frameSizeX, frameSizeY, frameOffsetX, frameOffsetY);
this.createPiskelFromImages_(frameImages, frameSizeX, frameSizeY, options.smoothing);
}
onComplete();
}.bind(this)
});
};
/**
* @param {!Image} image
* @param {!number} frameSizeX
* @param {!number} frameSizeY
* @param {!number} frameOffsetX
* @param {!number} frameOffsetY
* @returns {canvas[]}
* @private
*/
ns.ImportService.prototype.createImagesFromSheet_ = function (image,
frameSizeX, frameSizeY, frameOffsetX, frameOffsetY) {
return pskl.utils.CanvasUtils.createFramesFromImage(
image,
frameOffsetX,
frameOffsetY,
frameSizeX,
frameSizeY,
/*useHorizonalStrips=*/ true,
/*ignoreEmptyFrames=*/ true);
};
/**
* @param {canvas[]} images
* @param {!number} frameSizeX
* @param {!number} frameSizeY
* @param {!boolean} smoothing
* @private
*/
ns.ImportService.prototype.createPiskelFromImages_ = function (images,
frameSizeX, frameSizeY, smoothing) {
var frames = this.createFramesFromImages_(images, frameSizeX, frameSizeY, smoothing);
var layer = pskl.model.Layer.fromFrames('Layer 1', frames);
var descriptor = new pskl.model.piskel.Descriptor('Imported piskel', '');
var piskel = pskl.model.Piskel.fromLayers([layer], descriptor);
this.piskelController_.setPiskel(piskel);
this.previewController_.setFPS(Constants.DEFAULT.FPS);
};
/**
* @param {!canvas[]} images
* @param {!number} frameSizeX
* @param {!number} frameSizeY
* @param {!boolean} smoothing
* @returns {pskl.model.Frame[]}
* @private
*/
ns.ImportService.prototype.createFramesFromImages_ = function (images, frameSizeX, frameSizeY, smoothing) {
return images.map(function (image) {
var resizedImage = pskl.utils.ImageResizer.resize(image, frameSizeX, frameSizeY, smoothing);
return pskl.utils.FrameUtils.createFromImage(resizedImage);
});
};
})();

View File

@ -169,6 +169,7 @@
"js/service/keyboard/Shortcut.js", "js/service/keyboard/Shortcut.js",
"js/service/keyboard/Shortcuts.js", "js/service/keyboard/Shortcuts.js",
"js/service/keyboard/ShortcutService.js", "js/service/keyboard/ShortcutService.js",
"js/service/ImportService.js",
"js/service/ImageUploadService.js", "js/service/ImageUploadService.js",
"js/service/CurrentColorsService.js", "js/service/CurrentColorsService.js",
"js/service/FileDropperService.js", "js/service/FileDropperService.js",