From a362a03cbee88699798fac09880da9e404ac5270 Mon Sep 17 00:00:00 2001 From: Giulio Cesare Solaroli Date: Mon, 4 Aug 2014 18:33:37 +0200 Subject: [PATCH] Implemented the dialog to ask for confirmation when the user ask to delete a card No keyboard shortcut implemented, yet --- .../PM/UI/Components/Cards/Toolbar.js | 5 +- .../js/Clipperz/PM/UI/Components/DialogBox.js | 56 ++++- .../PM/UI/Components/Pages/MainPage.js | 6 +- .../delta/js/Clipperz/PM/UI/MainController.js | 17 +- .../delta/properties/delta.properties.json | 1 + frontend/delta/scss/clipperz.scss | 1 + frontend/delta/scss/core/layout.scss | 36 +++ frontend/delta/scss/style/dialogBox.scss | 28 +++ frontend/gamma/css/web.css | 228 ++++++++++++++++-- 9 files changed, 348 insertions(+), 30 deletions(-) create mode 100644 frontend/delta/scss/style/dialogBox.scss diff --git a/frontend/delta/js/Clipperz/PM/UI/Components/Cards/Toolbar.js b/frontend/delta/js/Clipperz/PM/UI/Components/Cards/Toolbar.js index 2e8b69a..5ee4895 100644 --- a/frontend/delta/js/Clipperz/PM/UI/Components/Cards/Toolbar.js +++ b/frontend/delta/js/Clipperz/PM/UI/Components/Cards/Toolbar.js @@ -73,7 +73,8 @@ Clipperz.PM.UI.Components.Cards.Toolbar = React.createClass({ }, selectCommandItem: function (anEvent) { - MochiKit.Signal.signal(Clipperz.Signal.NotificationCenter, anEvent.target.dataset['broadcastEvent'], {'reference':this.props['_reference']}); +//console.log("SELECT COMMAND ITEM", anEvent.currentTarget.dataset['broadcastEvent'], this.props['_reference']); + MochiKit.Signal.signal(Clipperz.Signal.NotificationCenter, anEvent.currentTarget.dataset['broadcastEvent'], {'reference':this.props['_reference']}); }, //---------------------------------------------------------------------------- @@ -82,7 +83,7 @@ Clipperz.PM.UI.Components.Cards.Toolbar = React.createClass({ var commandHandler = this.selectCommandItem; return React.DOM.ul({}, MochiKit.Base.map(function (aCommand) { - return React.DOM.li({}, [React.DOM.span({'onClick':commandHandler, 'data-broadcast-event':aCommand['broadcastEvent']}, aCommand['label'])]); + return React.DOM.li({'onClick':commandHandler, 'data-broadcast-event':aCommand['broadcastEvent']}, [React.DOM.span({}, aCommand['label'])]); }, MochiKit.Base.values(this.commands()))); }, diff --git a/frontend/delta/js/Clipperz/PM/UI/Components/DialogBox.js b/frontend/delta/js/Clipperz/PM/UI/Components/DialogBox.js index e071afe..61cc069 100644 --- a/frontend/delta/js/Clipperz/PM/UI/Components/DialogBox.js +++ b/frontend/delta/js/Clipperz/PM/UI/Components/DialogBox.js @@ -26,25 +26,67 @@ Clipperz.Base.module('Clipperz.PM.UI.Components'); Clipperz.PM.UI.Components.DialogBox = React.createClass({ propTypes: { - 'level': React.PropTypes.oneOf(['HIDE', 'INFO', 'WARNING', 'ERROR']).isRequired, - 'message': React.PropTypes.string.isRequired, + 'info': React.PropTypes.object.isRequired, + 'deferred': React.PropTypes.object.isRequired }, - +/* ask: function (someInfo) { var deferredResult; - + deferredResult = new Clipperz.Async.Deferred('DialogBox.ask', {trace:false}); - deferredResult.addCallback(someInfo.['possibleAnswers']['cancel']['answer']); + deferredResult.addCallback(someInfo['possibleAnswers']['cancel']['answer']); deferredResult.callback(); // deferredResult.cancel(); return deferredResult; }, - +*/ + + //------------------------------------------------------------------------- + + handleKeyDown: function (anEvent) { +console.log("DIALOG BOX - key DOWN", anEvent); + }, + + handleKeyPress: function (anEvent) { +console.log("DIALOG BOX - key PRESS", anEvent); + }, + + handleKeyUp: function (anEvent) { +console.log("DIALOG BOX - key UP", anEvent); + }, + + //------------------------------------------------------------------------- + + handleAnswerButton: function (anEvent) { +//console.log("HANDLE ANSWER BUTTON", anEvent.currentTarget.dataset['answerKey']); +//console.log("ANSWER INFO", this.props['info']['possibleAnswers'][anEvent.currentTarget.dataset['answerKey']]); +//console.log("<-- DEFERRED", this.props['deferred']); + this.props['info']['possibleAnswers'][anEvent.currentTarget.dataset['answerKey']]['answer'](this.props['deferred']); + }, + + renderAnswerButton: function (anAnswerInfoKey) { + var answerInfo = this.props['info']['possibleAnswers'][anAnswerInfoKey]; + var classes = { + 'button': true, + 'isDefault': answerInfo['isDefault'] + }; + + return React.DOM.div({'className':React.addons.classSet(classes), 'onClick':this.handleAnswerButton, 'data-answer-key':anAnswerInfoKey}, answerInfo['label']) + }, + //========================================================================= render: function () { - return React.DOM.div({className:'messageBox ' + this.props['level']}, this.props['message']); +//console.log("DIALOG BOX", this.props); +//console.log("--> DEFERRED", this.props['deferred']); + return React.DOM.div({'className':'dialogBox', 'onKeyDown':this.handleKeyDown, 'onKeyPress':this.handleKeyPress, 'onKeyUp':this.handleKeyUp}, [ + React.DOM.div({'className':'mask'}), + React.DOM.div({'className':'dialog'}, [ + React.DOM.h3({'className': 'message'}, this.props['info']['question']), + React.DOM.div({'className': 'answers'}, MochiKit.Base.map(this.renderAnswerButton, MochiKit.Base.keys(this.props['info']['possibleAnswers']))) + ]) + ]); } //========================================================================= diff --git a/frontend/delta/js/Clipperz/PM/UI/Components/Pages/MainPage.js b/frontend/delta/js/Clipperz/PM/UI/Components/Pages/MainPage.js index 0d258af..1effa5f 100644 --- a/frontend/delta/js/Clipperz/PM/UI/Components/Pages/MainPage.js +++ b/frontend/delta/js/Clipperz/PM/UI/Components/Pages/MainPage.js @@ -54,10 +54,12 @@ Clipperz.PM.UI.Components.Pages.MainPage = React.createClass({ }; classes[this.props['style']] = true; - return React.DOM.div({className:React.addons.classSet(classes)}, [ +//console.log("MAIN PAGE", this.props['ask']); + return React.DOM.div({'className':React.addons.classSet(classes)}, [ this.props['style'] != 'extra-wide' ? Clipperz.PM.UI.Components.Panels.SelectionPanel(this.props) : null, Clipperz.PM.UI.Components.Panels.MainPanel(this.props), - Clipperz.PM.UI.Components.Panels.ExtraFeaturesPanel(this.props) + Clipperz.PM.UI.Components.Panels.ExtraFeaturesPanel(this.props), + this.props['ask'] ? Clipperz.PM.UI.Components.DialogBox(this.props['ask']) : null ]); } diff --git a/frontend/delta/js/Clipperz/PM/UI/MainController.js b/frontend/delta/js/Clipperz/PM/UI/MainController.js index 65adce2..75042bd 100644 --- a/frontend/delta/js/Clipperz/PM/UI/MainController.js +++ b/frontend/delta/js/Clipperz/PM/UI/MainController.js @@ -328,7 +328,7 @@ console.log("THE BROWSER IS OFFLINE"); this.overlay().show("creating user"); this.pages()['registrationPage'].setProps({disabled:true}); - deferredResult = new Clipperz.Async.Deferred('MainController.registerNewUser', {trace:true}); + deferredResult = new Clipperz.Async.Deferred('MainController.registerNewUser', {trace:false}); deferredResult.addCallback(Clipperz.PM.DataModel.User.registerNewAccount, credentials['username'], MochiKit.Base.partial(MochiKit.Async.succeed, credentials['passphrase']) @@ -953,10 +953,14 @@ console.log("SET USER", aUser); ask: function (someInfo) { var deferredResult; - + var currentPage = this.pages()[this.currentPage()]; + deferredResult = new Clipperz.Async.Deferred('MainController.ask', {trace:false}); + currentPage.setProps({'ask': {'info': someInfo, 'deferred':deferredResult}}); - this.currentPage().setProps({'ask':someInfo, 'deferred':deferredResult}); +// deferredResult.addCallback(function (aResult) { console.log("ASK - OK", aResult); return aResult; }); +// deferredResult.addErrback(function (aResult) { console.log("ASK - FAIL", aResult); return aResult; }); + deferredResult.addBothPass(MochiKit.Base.method(currentPage, 'setProps', {'ask': null})); return deferredResult; }, @@ -968,15 +972,18 @@ console.log("ADD CARD CLICK"); }, deleteCard_handler: function (anEvent) { + var self = this; + return Clipperz.Async.callbacks("MainController.deleteCard_handler", [ // MochiKit.Base.method(this, 'askConfirmation', {'message':"Delete card?"}), - MochiKit.Base.method(this, 'ask', { + MochiKit.Base.method(self, 'ask', { 'question': "Delete card?", 'possibleAnswers':{ - 'cancel': {'label':"No", 'isDefault':true, 'answer':MochiKit.Base.methodcaller('cancel')}, + 'cancel': {'label':"No", 'isDefault':true, 'answer':MochiKit.Base.methodcaller('cancel', new MochiKit.Async.CancelledError())}, 'delete': {'label':"Yes", 'isDefault':false, 'answer':MochiKit.Base.methodcaller('callback')} } }), +//function (aValue) { console.log("<-- ASK", aValue); return aValue; }, MochiKit.Base.method(this.user(), 'getRecord', anEvent['reference']), MochiKit.Base.method(this.user(), 'deleteRecord'), MochiKit.Base.method(this.user(), 'saveChanges'), diff --git a/frontend/delta/properties/delta.properties.json b/frontend/delta/properties/delta.properties.json index 2a9ac38..fe3af51 100644 --- a/frontend/delta/properties/delta.properties.json +++ b/frontend/delta/properties/delta.properties.json @@ -137,6 +137,7 @@ "Clipperz/PM/UI/Components/Checkbox.js", "Clipperz/PM/UI/Components/CardToolbar.js", "Clipperz/PM/UI/Components/MessageBox.js", + "Clipperz/PM/UI/Components/DialogBox.js", "Clipperz/PM/UI/Components/Selections.js", "Clipperz/PM/UI/Components/TagIndexItem.js", diff --git a/frontend/delta/scss/clipperz.scss b/frontend/delta/scss/clipperz.scss index c2da631..40f8631 100644 --- a/frontend/delta/scss/clipperz.scss +++ b/frontend/delta/scss/clipperz.scss @@ -14,6 +14,7 @@ @import "style/settingsPanel"; @import "style/accountStatus"; @import "style/card"; +@import "style/dialogBox"; //---------------------------------------------------------------------------- diff --git a/frontend/delta/scss/core/layout.scss b/frontend/delta/scss/core/layout.scss index df1cfc4..851f99b 100644 --- a/frontend/delta/scss/core/layout.scss +++ b/frontend/delta/scss/core/layout.scss @@ -325,3 +325,39 @@ div.cardContent { cursor: pointer; } + +div.dialogBox { + @include mask(); + + @include flexbox(); + @include align-items(center); + @include justify-content(center); + + position: absolute; + left: 0px; + top: 0px; + width: 100%; + height: 100%; + + div.dialog { + @include flex(none); + z-index: 99999; + + h3.message { + } + + div.answers { + @include flexbox(); + @include flex-direction(row); + @include justify-content(flex-end); + + div.button { + @include flex(none); + cursor: pointer; + + &.isDefault { + } + } + } + } +} \ No newline at end of file diff --git a/frontend/delta/scss/style/dialogBox.scss b/frontend/delta/scss/style/dialogBox.scss new file mode 100644 index 0000000..42b4492 --- /dev/null +++ b/frontend/delta/scss/style/dialogBox.scss @@ -0,0 +1,28 @@ +div.dialog { + @include box-shadow(0px, 2px, 5px, rgba(50, 50, 50, 0.75)); + @include border-radius(8px); + + background-color: white; + padding: 30px; + + h3.message { + font-size: 18pt; + font-weight: bold; + padding-bottom: 20px; + } + + div.answers { + + div.button { + border: 1px solid black; + margin-left: 10px; + padding: 5px 10px; + + &.isDefault { + font-weight: bold; + color: white; + background-color: blue; + } + } + } +} diff --git a/frontend/gamma/css/web.css b/frontend/gamma/css/web.css index 7d1745b..7876428 100644 --- a/frontend/gamma/css/web.css +++ b/frontend/gamma/css/web.css @@ -266,9 +266,9 @@ div.tooltip.RIGHT div.tooltip_body div.tooltip_text { display: inline-block; height: 20px; cursor: pointer; - background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#ffa76f), to(#ff6622)); - background: -moz-linear-gradient(0% 100% 90deg, #ff6622, #ffa76f); - background: linear-gradient(0deg, #ff6622, #ffa76f); + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#ff6622), to(#ff6622)); + background: -moz-linear-gradient(0% 100% 90deg, #ff6622, #ff6622); + background: linear-gradient(0deg, #ff6622, #ff6622); border-radius: 5; -moz-border-radius: 5; -webkit-border-radius: 5; @@ -281,6 +281,9 @@ div.tooltip.RIGHT div.tooltip_body div.tooltip_text { font-weight: lighter; text-shadow: -1px -1px 1px #ff6622, 1px 1px 1px #ffa76f; text-decoration: none; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#ffa76f), to(#ff6622)); + background: -moz-linear-gradient(0% 100% 90deg, #ff6622, #ffa76f); + background: linear-gradient(0deg, #ff6622, #ffa76f); font-weight: normal; } .button.default:hover { @@ -292,9 +295,9 @@ div.tooltip.RIGHT div.tooltip_body div.tooltip_text { display: inline-block; height: 20px; cursor: pointer; - background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#bfbfbf), to(#999999)); - background: -moz-linear-gradient(0% 100% 90deg, #999999, #bfbfbf); - background: linear-gradient(0deg, #999999, #bfbfbf); + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#999999), to(#999999)); + background: -moz-linear-gradient(0% 100% 90deg, #999999, #999999); + background: linear-gradient(0deg, #999999, #999999); border-radius: 5; -moz-border-radius: 5; -webkit-border-radius: 5; @@ -307,6 +310,9 @@ div.tooltip.RIGHT div.tooltip_body div.tooltip_text { font-weight: lighter; text-shadow: -1px -1px 1px #999999, 1px 1px 1px #bfbfbf; text-decoration: none; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#bfbfbf), to(#999999)); + background: -moz-linear-gradient(0% 100% 90deg, #999999, #bfbfbf); + background: linear-gradient(0deg, #999999, #bfbfbf); } .button:hover { background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#ababab), to(#999999)); @@ -962,6 +968,7 @@ div.userInfoBox div.body div.accountInfo { margin-top: 6px; border-top: 1px solid white; border-color: #f4aa84; + min-height: 76px; } div.userInfoBox div.body div.accountInfo h5 { margin: 0px; @@ -1327,9 +1334,9 @@ div.subPanelContent ul li.selected { display: inline-block; height: 20px; cursor: pointer; - background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#59bc4c), to(#448833)); - background: -moz-linear-gradient(0% 100% 90deg, #448833, #59bc4c); - background: linear-gradient(0deg, #448833, #59bc4c); + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#448833), to(#448833)); + background: -moz-linear-gradient(0% 100% 90deg, #448833, #448833); + background: linear-gradient(0deg, #448833, #448833); border-radius: 5; -moz-border-radius: 5; -webkit-border-radius: 5; @@ -1342,12 +1349,64 @@ div.subPanelContent ul li.selected { font-weight: lighter; text-shadow: -1px -1px 1px #448833, 1px 1px 1px #59bc4c; text-decoration: none; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#59bc4c), to(#448833)); + background: -moz-linear-gradient(0% 100% 90deg, #448833, #59bc4c); + background: linear-gradient(0deg, #448833, #59bc4c); } .downloadOfflineCopy:hover { background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#49a23d), to(#448833)); background: -moz-linear-gradient(0% 100% 90deg, #448833, #49a23d); background: linear-gradient(0deg, #448833, #49a23d); } +.deleteAccountButton { + display: inline-block; + height: 20px; + cursor: pointer; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#a80700), to(#a80700)); + background: -moz-linear-gradient(0% 100% 90deg, #a80700, #a80700); + background: linear-gradient(0deg, #a80700, #a80700); + border-radius: 5; + -moz-border-radius: 5; + -webkit-border-radius: 5; + border: 1px solid #cc0800; + padding-top: 4px; + padding-left: 15px; + padding-right: 15px; + padding-bottom: 2px; + color: white; + font-weight: lighter; + text-shadow: -1px -1px 1px #a80700, 1px 1px 1px #f41f00; + text-decoration: none; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#f41f00), to(#a80700)); + background: -moz-linear-gradient(0% 100% 90deg, #a80700, #f41f00); + background: linear-gradient(0deg, #a80700, #f41f00); +} +.deleteAccountButton:hover { + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#cc1900), to(#a80700)); + background: -moz-linear-gradient(0% 100% 90deg, #a80700, #cc1900); + background: linear-gradient(0deg, #a80700, #cc1900); +} +.deleteAccountButton.disabled { + display: inline-block; + height: 20px; + cursor: pointer; + background: -webkit-gradient(linear, 0% 0%, 0% 100%, from(#a0a0a0), to(#a0a0a0)); + background: -moz-linear-gradient(0% 100% 90deg, #a0a0a0, #a0a0a0); + background: linear-gradient(0deg, #a0a0a0, #a0a0a0); + border-radius: 5; + -moz-border-radius: 5; + -webkit-border-radius: 5; + border: 1px solid #b2b2b2; + padding-top: 4px; + padding-left: 15px; + padding-right: 15px; + padding-bottom: 2px; + color: white; + font-weight: lighter; + text-shadow: -1px -1px 1px #a0a0a0, 1px 1px 1px #c6c6c6; + text-decoration: none; + cursor: default; +} div.SimpleMessagePanel { position: relative; left: -225px; @@ -1422,7 +1481,119 @@ div.SimpleMessagePanel div.passphrase input { div.SimpleMessagePanel div.progressBarWrapper { margin-left: 80px; } -/* @end */ +div.scrollable div.PaymentDialog { + top: 0px; +} +div.fixed div.PaymentDialog { + top: -166.66666666666666px; +} +div.PaymentDialog { + position: relative; + width: 600px; + left: -300px; + height: 500px; + background-color: red; + border-radius: 15px; + -moz-border-radius: 15px; + -webkit-border-radius: 15px; +} +div.PaymentDialog ul { + background-color: purple; +} +div.PaymentDialog ul li { + background-color: yellow; + display: inline-block; + width: 150px; + margin-right: 30px; + cursor: pointer; +} +div.PaymentDialog ul li.selected { + background-color: green; +} +/* +div.mainDialog { + position: relative; + left: -263px; + width: 525px; + height: 325px; +} +div.scrollable div.mainDialog { + top: 0px; +} +div.fixed div.mainDialog { + top: -118px; +} +div.mainDialog div.header { + height: 55px; + background: url(./images/old/cardDialog/background_header.png) no-repeat; +} +div.mainDialog div.header div.title { + padding-top: 16px; + padding-left: 20px; + padding-right: 20px; +} +div.mainDialog div.header div.title input { + width: 100%; + display: block; + font-size: 16pt; + margin: 0px; + border: 0px; + padding: 3px 10px; + color: #787872; + border: 1px solid #cccec0; + background-color: #cccec0; +} +div.mainDialog div.header div.title h3 { + display: block; + font-size: 16pt; + color: #787872; + margin: 0px; + border: 0px; + padding: 3px 10px; +} +div.mainDialog div.header div.title.selectedField input, div.mainDialog div.header div.title:hover input { + border: 1px solid #515247; + background-color: #b5b7ab; +} +div.mainDialog div.header div.title.disabled:hover input { + border: 1px solid #cccec0; + background-color: #cccec0; +} +div.mainDialog div.body { + padding-top: 0px; + padding-left: 10px; + padding-right: 9px; + min-height: 200px; + background: url(./images/old/cardDialog/background_body.png) repeat-y; +} +div.mainDialog div.body div.mask { + display: none; +} +div.mainDialog.loading div.body div.mask { + display: block; + position: absolute; + top: 55px; + left: 10px; + right: 9px; + bottom: 70px; + z-index: 1001; + background-color: white; + padding-left: 146px; + padding-right: 146px; + padding-top: 70px; +} +div.mainDialog.loading div.body .tabPanels { + display: none; +} +div.mainDialog.loading div.body div.mask h3.progressDescription { + margin: 0px; + text-align: center; + padding-bottom: 10px; + color: #cccec0; + font-size: 14pt; + font-weight: normal; +} +*//* @end */ /* @group Javascript Alert */ div#javaScriptAlert div.mask { position: fixed; @@ -2530,19 +2701,48 @@ div.mainPanels div.otherPanel div.body h1 { /* @end */ /* @group Account */ form.changePassphrase div.currentCredentials, -form.changePassphrase div.newPassphrase { +form.deleteAccount div.currentCredentials, +form.changePassphrase div.newPassphrase, +form.deleteAccount div.newPassphrase { float: left; padding: 10px 20px; } -form.changePassphrase label { +form.changePassphrase label, +form.deleteAccount label { display: inline-block; width: 150px; } -form.changePassphrase div.confirm { +form.changePassphrase input, +form.deleteAccount input { + width: 230px; + font-size: 13pt; + color: #787872; + height: 35px; + margin-left: 15px; + padding-left: 5px; +} +form.changePassphrase input.checkbox, +form.deleteAccount input.checkbox { + margin: 10px 8px 0px 0px; + height: auto; + width: auto; + border: 0px; +} +form.changePassphrase input.checkbox:hover, +form.deleteAccount input.checkbox:hover { + cursor: pointer; +} +form.changePassphrase div.field, +form.deleteAccount div.field { + padding-bottom: 5px; +} +form.changePassphrase div.confirm, +form.deleteAccount div.confirm { clear: both; padding: 10px 20px; } -form.changePassphrase div.confirm label { +form.changePassphrase div.confirm label, +form.deleteAccount div.confirm label { width: 500px; } div.accountPanel h3.manageOTP {