OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 /** | 5 /** |
6 * ImageEditor is the top level object that holds together and connects | 6 * ImageEditor is the top level object that holds together and connects |
7 * everything needed for image editing. | 7 * everything needed for image editing. |
8 * | 8 * |
9 * @param {!Viewport} viewport The viewport. | 9 * @param {!Viewport} viewport The viewport. |
10 * @param {!ImageView} imageView The ImageView containing the images to edit. | 10 * @param {!ImageView} imageView The ImageView containing the images to edit. |
(...skipping 501 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
512 ImageEditor.Mode.prototype.markUpdated = function() { | 512 ImageEditor.Mode.prototype.markUpdated = function() { |
513 this.updated_ = true; | 513 this.updated_ = true; |
514 }; | 514 }; |
515 | 515 |
516 /** | 516 /** |
517 * @return {boolean} True if the mode controls changed. | 517 * @return {boolean} True if the mode controls changed. |
518 */ | 518 */ |
519 ImageEditor.Mode.prototype.isUpdated = function() { return this.updated_; }; | 519 ImageEditor.Mode.prototype.isUpdated = function() { return this.updated_; }; |
520 | 520 |
521 /** | 521 /** |
| 522 * @return {boolean} True if a key event should be consumed by the mode. |
| 523 */ |
| 524 ImageEditor.Mode.prototype.isConsumingKeyEvents = function() { return false; }; |
| 525 |
| 526 /** |
522 * Resets the mode to a clean state. | 527 * Resets the mode to a clean state. |
523 */ | 528 */ |
524 ImageEditor.Mode.prototype.reset = function() { | 529 ImageEditor.Mode.prototype.reset = function() { |
525 this.editor_.modeToolbar_.reset(); | 530 this.editor_.modeToolbar_.reset(); |
526 this.updated_ = false; | 531 this.updated_ = false; |
527 }; | 532 }; |
528 | 533 |
529 /** | 534 /** |
530 * @return {Command} Command. | 535 * @return {Command} Command. |
531 */ | 536 */ |
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
607 | 612 |
608 /** | 613 /** |
609 * Set up the new editing mode. | 614 * Set up the new editing mode. |
610 * | 615 * |
611 * @param {!ImageEditor.Mode} mode The mode. | 616 * @param {!ImageEditor.Mode} mode The mode. |
612 * @private | 617 * @private |
613 */ | 618 */ |
614 ImageEditor.prototype.setUpMode_ = function(mode) { | 619 ImageEditor.prototype.setUpMode_ = function(mode) { |
615 this.currentTool_ = mode.button_; | 620 this.currentTool_ = mode.button_; |
616 this.currentMode_ = mode; | 621 this.currentMode_ = mode; |
| 622 this.rootContainer_.setAttribute('editor-mode', mode.name); |
617 | 623 |
618 // Activate toggle ripple if button is toggleable. | 624 // Activate toggle ripple if button is toggleable. |
619 var filesToggleRipple = | 625 var filesToggleRipple = |
620 this.currentTool_.querySelector('files-toggle-ripple'); | 626 this.currentTool_.querySelector('files-toggle-ripple'); |
621 if (filesToggleRipple) { | 627 if (filesToggleRipple) { |
622 // Current mode must NOT be instant for toggleable button. | 628 // Current mode must NOT be instant for toggleable button. |
623 assert(!this.currentMode_.instant); | 629 assert(!this.currentMode_.instant); |
624 filesToggleRipple.activated = true; | 630 filesToggleRipple.activated = true; |
625 } | 631 } |
626 | 632 |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
672 /** | 678 /** |
673 * The user clicked on 'OK' or 'Cancel' or on a different mode button. | 679 * The user clicked on 'OK' or 'Cancel' or on a different mode button. |
674 * @param {boolean} commit True if commit is required. | 680 * @param {boolean} commit True if commit is required. |
675 * @param {boolean} leaveToSwitchMode True if it leaves to change mode. | 681 * @param {boolean} leaveToSwitchMode True if it leaves to change mode. |
676 * @private | 682 * @private |
677 */ | 683 */ |
678 ImageEditor.prototype.leaveModeInternal_ = function(commit, leaveToSwitchMode) { | 684 ImageEditor.prototype.leaveModeInternal_ = function(commit, leaveToSwitchMode) { |
679 if (!this.currentMode_) | 685 if (!this.currentMode_) |
680 return; | 686 return; |
681 | 687 |
| 688 // If the current mode is 'Resize', and commit is required, |
| 689 // leaving mode should be stopped when an input value is not valid. |
| 690 if(commit && this.currentMode_.name === 'resize') { |
| 691 var resizeMode = /** @type {!ImageEditor.Mode.Resize} */ |
| 692 (this.currentMode_); |
| 693 if(!resizeMode.isInputValid()) { |
| 694 resizeMode.showAlertDialog(); |
| 695 return; |
| 696 } |
| 697 } |
| 698 |
682 this.modeToolbar_.show(false); | 699 this.modeToolbar_.show(false); |
| 700 this.rootContainer_.removeAttribute('editor-mode'); |
683 | 701 |
684 // If it leaves to switch mode, do not restore screen size since the next mode | 702 // If it leaves to switch mode, do not restore screen size since the next mode |
685 // might change screen size. We should avoid to show intermediate animation | 703 // might change screen size. We should avoid to show intermediate animation |
686 // which tries to restore screen size. | 704 // which tries to restore screen size. |
687 if (!leaveToSwitchMode) { | 705 if (!leaveToSwitchMode) { |
688 this.getViewport().setScreenTop(ImageEditor.Toolbar.HEIGHT); | 706 this.getViewport().setScreenTop(ImageEditor.Toolbar.HEIGHT); |
689 this.getViewport().setScreenBottom(ImageEditor.Toolbar.HEIGHT); | 707 this.getViewport().setScreenBottom(ImageEditor.Toolbar.HEIGHT); |
690 this.getImageView().applyViewportChange(); | 708 this.getImageView().applyViewportChange(); |
691 } | 709 } |
692 | 710 |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
741 } | 759 } |
742 console.error('Mode "' + name + '" not found.'); | 760 console.error('Mode "' + name + '" not found.'); |
743 }; | 761 }; |
744 | 762 |
745 /** | 763 /** |
746 * Key down handler. | 764 * Key down handler. |
747 * @param {!Event} event The keydown event. | 765 * @param {!Event} event The keydown event. |
748 * @return {boolean} True if handled. | 766 * @return {boolean} True if handled. |
749 */ | 767 */ |
750 ImageEditor.prototype.onKeyDown = function(event) { | 768 ImageEditor.prototype.onKeyDown = function(event) { |
| 769 if (this.currentMode_ && this.currentMode_.isConsumingKeyEvents()) |
| 770 return false; |
| 771 |
751 switch (util.getKeyModifiers(event) + event.key) { | 772 switch (util.getKeyModifiers(event) + event.key) { |
752 case 'Escape': | 773 case 'Escape': |
753 case 'Enter': | 774 case 'Enter': |
754 if (this.getMode()) { | 775 if (this.getMode()) { |
755 this.leaveModeInternal_(event.key === 'Enter', | 776 this.leaveModeInternal_(event.key === 'Enter', |
756 false /* not to switch mode */); | 777 false /* not to switch mode */); |
757 return true; | 778 return true; |
758 } | 779 } |
759 break; | 780 break; |
760 | 781 |
(...skipping 530 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1291 */ | 1312 */ |
1292 ImageEditor.Toolbar.prototype.addButton = function( | 1313 ImageEditor.Toolbar.prototype.addButton = function( |
1293 title, type, handler, opt_class) { | 1314 title, type, handler, opt_class) { |
1294 var button = ImageEditor.Toolbar.createButton_( | 1315 var button = ImageEditor.Toolbar.createButton_( |
1295 title, type, handler, opt_class); | 1316 title, type, handler, opt_class); |
1296 this.add(button); | 1317 this.add(button); |
1297 return button; | 1318 return button; |
1298 }; | 1319 }; |
1299 | 1320 |
1300 /** | 1321 /** |
| 1322 * Add a input field. |
| 1323 * |
| 1324 * @param {string} name Input name |
| 1325 * @param {string} title Input title |
| 1326 * @param {function(Event)} handler onInput and onChange handler |
| 1327 * @param {string|number} value Default value |
| 1328 * @param {string=} opt_unit Unit for an input field |
| 1329 * @return {!HTMLElement} Input Element |
| 1330 */ |
| 1331 ImageEditor.Toolbar.prototype.addInput = function( |
| 1332 name, title, handler, value, opt_unit) { |
| 1333 |
| 1334 var input = /** @type {!HTMLElement} */ (document.createElement('div')); |
| 1335 input.classList.add('input', name); |
| 1336 |
| 1337 var text = document.createElement('paper-input'); |
| 1338 text.setAttribute('label', strf(title)); |
| 1339 text.classList.add('text', name); |
| 1340 text.value = value; |
| 1341 |
| 1342 // We should listen to not only 'change' event, but also 'input' because we |
| 1343 // want to update values as soon as the user types characters. |
| 1344 text.addEventListener('input', handler, false); |
| 1345 text.addEventListener('change', handler, false); |
| 1346 input.appendChild(text); |
| 1347 |
| 1348 if(opt_unit) { |
| 1349 var unit_label = document.createElement('span'); |
| 1350 unit_label.textContent = opt_unit; |
| 1351 unit_label.classList.add('unit_label'); |
| 1352 input.appendChild(unit_label); |
| 1353 } |
| 1354 |
| 1355 input.name = name; |
| 1356 input.getValue = function(text) { |
| 1357 return text.value; |
| 1358 }.bind(this, text); |
| 1359 input.setValue = function(text, value) { |
| 1360 text.value = value; |
| 1361 }.bind(this, text); |
| 1362 |
| 1363 this.add(input); |
| 1364 |
| 1365 return input; |
| 1366 }; |
| 1367 |
| 1368 /** |
1301 * Add a range control (scalar value picker). | 1369 * Add a range control (scalar value picker). |
1302 * | 1370 * |
1303 * @param {string} name An option name. | 1371 * @param {string} name An option name. |
1304 * @param {string} title An option title. | 1372 * @param {string} title An option title. |
1305 * @param {number} min Min value of the option. | 1373 * @param {number} min Min value of the option. |
1306 * @param {number} value Default value of the option. | 1374 * @param {number} value Default value of the option. |
1307 * @param {number} max Max value of the options. | 1375 * @param {number} max Max value of the options. |
1308 * @param {number=} opt_scale A number to multiply by when setting | 1376 * @param {number=} opt_scale A number to multiply by when setting |
1309 * min/value/max in DOM. | 1377 * min/value/max in DOM. |
1310 * @param {boolean=} opt_showNumeric True if numeric value should be displayed. | 1378 * @param {boolean=} opt_showNumeric True if numeric value should be displayed. |
(...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1528 | 1596 |
1529 /** | 1597 /** |
1530 * Hide the prompt. | 1598 * Hide the prompt. |
1531 */ | 1599 */ |
1532 ImageEditor.Prompt.prototype.hide = function() { | 1600 ImageEditor.Prompt.prototype.hide = function() { |
1533 if (!this.prompt_) return; | 1601 if (!this.prompt_) return; |
1534 this.prompt_.setAttribute('state', 'fadeout'); | 1602 this.prompt_.setAttribute('state', 'fadeout'); |
1535 // Allow some time for the animation to play out. | 1603 // Allow some time for the animation to play out. |
1536 this.setTimer(this.reset.bind(this), 500); | 1604 this.setTimer(this.reset.bind(this), 500); |
1537 }; | 1605 }; |
OLD | NEW |