mirror of
				http://git.whoc.org.uk/git/password-manager.git
				synced 2025-10-31 11:27:34 +01:00 
			
		
		
		
	Added a few feature based on actual subscription options
This commit is contained in:
		| @@ -33,6 +33,41 @@ Clipperz.PM.DataModel.User.AccountInfo = function(args) { | ||||
|  | ||||
| Clipperz.Base.extend(Clipperz.PM.DataModel.User.AccountInfo, Object, { | ||||
|  | ||||
| 	'status': function () { | ||||
| 		return this._attributes['currentSubscriptionType']; | ||||
| 	}, | ||||
|  | ||||
| 	'level': function () { | ||||
| 		var	result; | ||||
| 		 | ||||
| 		// -1.00 -> EARLY_ADOPTER | ||||
| 		//  2.00 -> FRIEND | ||||
| 		//  5.00 -> FAN | ||||
| 		// 10.00 -> DEVOTEE | ||||
| 		// 15.00 -> PATRON | ||||
| 		 | ||||
| 		if (this.status() == 'FRIEND') { | ||||
| 			result = 1; | ||||
| 		} else if (this.status() == 'FAN') { | ||||
| 			result = 2; | ||||
| 		} else if (this.status() == 'DEVOTEE') { | ||||
| 			result = 3; | ||||
| 		} else if (this.status() == 'PATRON') { | ||||
| 			result = 4; | ||||
| 		} else { | ||||
| 			result = 0; | ||||
| 		}; | ||||
| 		 | ||||
| 		return result; | ||||
| //		return this._attributes['latestActiveThreshold']; | ||||
| 	}, | ||||
|  | ||||
| 	'isExpiring': function () { | ||||
| 		return this._attributes['isExpiring']; | ||||
| 	}, | ||||
|  | ||||
| 	//............................................................................ | ||||
|  | ||||
| 	'features': function () { | ||||
| 		return this._attributes['features']; | ||||
| 	}, | ||||
| @@ -48,6 +83,12 @@ Clipperz.Base.extend(Clipperz.PM.DataModel.User.AccountInfo, Object, { | ||||
| 		}; | ||||
| 	}, | ||||
| 	 | ||||
| 	'isExpired': function () { | ||||
| 		return this._attributes['isExpired']; | ||||
| 	}, | ||||
| 	 | ||||
| 	 | ||||
|  | ||||
| 	//========================================================================= | ||||
| 	__syntaxFix__: "syntax fix" | ||||
| }); | ||||
|   | ||||
| @@ -29,7 +29,7 @@ Clipperz.PM.UI.Components.CardToolbar = React.createClass({ | ||||
| //		'style':			React.PropTypes.oneOf(['extra-short', 'narrow', 'wide', 'extra-wide']).isRequired, | ||||
| 		'style':			React.PropTypes.oneOf(Clipperz_PM_UI_availableStyles).isRequired, | ||||
| 		'enableSidePanels':	React.PropTypes.bool.isRequired, | ||||
| 		'accountStatus':	React.PropTypes.object.isRequired, | ||||
| 		'accountInfo':		React.PropTypes.object.isRequired, | ||||
| 		'messageBox':		React.PropTypes.object.isRequired, | ||||
| 		'filter':			React.PropTypes.object /*.isRequired */ | ||||
| 	}, | ||||
| @@ -99,7 +99,7 @@ Clipperz.PM.UI.Components.CardToolbar = React.createClass({ | ||||
| 		return	React.DOM.div({className:'cardToolbar ' + this.props['style']}, [ | ||||
| //			React.DOM.div({className:'header'}, this.props['enableSidePanels'] ? this.renderWithSidePanels() : this.renderWithoutSidePanels()), | ||||
| 			React.DOM.header({}, this.props['enableSidePanels'] ? this.renderWithSidePanels() : this.renderWithoutSidePanels()), | ||||
| 			Clipperz.PM.UI.Components.AccountStatus(this.props['accountStatus']), | ||||
| 			Clipperz.PM.UI.Components.AccountStatus(this.props['accountInfo']), | ||||
| 			Clipperz.PM.UI.Components.MessageBox(this.props['messageBox']), | ||||
| 		]); | ||||
| 	} | ||||
|   | ||||
| @@ -30,6 +30,7 @@ Clipperz.PM.UI.Components.Cards.List = React.createClass({ | ||||
|  | ||||
| 	propTypes: { | ||||
| 		'cards':		React.PropTypes.array, | ||||
| 		'featureSet':	React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL', 'OFFLINE']).isRequired, | ||||
| 		'selectedCard':	React.PropTypes.object | ||||
| 	}, | ||||
|  | ||||
| @@ -62,7 +63,8 @@ Clipperz.PM.UI.Components.Cards.List = React.createClass({ | ||||
| 		var	cards = this.props['cards'] ? this.props['cards'] : []; | ||||
| 		var	classes = { | ||||
| 			'cardList':		true, | ||||
| 			'loadingCard':	this.props['selectedCard'] && this.props['selectedCard']['_reference'] && this.props['selectedCard']['loading'] | ||||
| 			'loadingCard':	this.props['selectedCard'] && this.props['selectedCard']['_reference'] && this.props['selectedCard']['loading'], | ||||
| 			'EXPIRED':		this.props['featureSet'] == 'EXPIRED', | ||||
| 		};		 | ||||
| 		classes[this.props['style']] = true; | ||||
|  | ||||
|   | ||||
| @@ -26,7 +26,7 @@ Clipperz.Base.module('Clipperz.PM.UI.Components'); | ||||
| Clipperz.PM.UI.Components.ExpiredPanel = React.createClass({ | ||||
|  | ||||
| 	propTypes: { | ||||
| //		featureSet:			React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL']).isRequired, | ||||
| //		featureSet:			React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL', 'OFFLINE']).isRequired, | ||||
| //		'level':	React.PropTypes.oneOf(['hide', 'info', 'warning', 'error']).isRequired | ||||
| 	}, | ||||
|  | ||||
|   | ||||
| @@ -28,13 +28,14 @@ Clipperz.PM.UI.Components.Pages.MainPage = React.createClass({ | ||||
|  | ||||
| 	getDefaultProps: function () { | ||||
| 		return { | ||||
| 		} | ||||
| 			featureSet: 'FULL' | ||||
| 		}; | ||||
| 	}, | ||||
|  | ||||
| 	propTypes: { | ||||
| 		'messageBox':		React.PropTypes.object.isRequired, | ||||
| //		'featureSet':		React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL']), | ||||
| 		'accountStatus':	React.PropTypes.object.isRequired, | ||||
| 		'featureSet':		React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL', 'OFFLINE']).isRequired, | ||||
| 		'accountInfo':		React.PropTypes.object.isRequired, | ||||
| //		'mediaQueryStyle':	React.PropTypes.oneOf(['extra-short', 'narrow', 'wide', 'extra-wide']).isRequired, | ||||
| 		'style':			React.PropTypes.oneOf(Clipperz_PM_UI_availableStyles).isRequired, | ||||
| 		//		'cards':			React.PropTypes.deferred.isRequired | ||||
|   | ||||
| @@ -35,9 +35,31 @@ Clipperz.PM.UI.Components.Panels.ExtraFeaturesPanel = React.createClass({ | ||||
| 		MochiKit.Signal.signal(Clipperz.Signal.NotificationCenter, 'downloadOfflineCopy'); | ||||
| 	}, | ||||
|  | ||||
| 	propTypes: { | ||||
| 		'accountInfo':		React.PropTypes.object.isRequired, | ||||
| 	}, | ||||
|  | ||||
| 	getInitialState: function() { | ||||
| 		return { | ||||
| 			'account':		false, | ||||
| 			'subscription':	false, | ||||
| 			'data':			false, | ||||
| 		}; | ||||
| 	}, | ||||
|  | ||||
| 	toggleState: function (section) { | ||||
| 		return MochiKit.Base.bind(function () { | ||||
| 			var	newState = {}; | ||||
| 			 | ||||
| 			newState[section] = !this.state[section]; | ||||
| 			this.setState(newState); | ||||
| 		}, this); | ||||
| 	}, | ||||
|  | ||||
| 	//========================================================================= | ||||
|  | ||||
| 	render: function () { | ||||
| //console.log("ExtraFeaturesPanel props", this.props); | ||||
| 		var	classes = { | ||||
| 			'panel': true, | ||||
| 			'right': true, | ||||
| @@ -53,32 +75,93 @@ Clipperz.PM.UI.Components.Panels.ExtraFeaturesPanel = React.createClass({ | ||||
|  | ||||
| 			React.DOM.div({}, [ | ||||
| 				React.DOM.ul({}, [ | ||||
| 					React.DOM.li({}, [ | ||||
| 						React.DOM.h1({}, "Account"), | ||||
| 					React.DOM.li({'className':this.state['account'] ? 'open' : 'closed'}, [ | ||||
| 						React.DOM.h1({'onClick':this.toggleState('account')}, "Account"), | ||||
| 						React.DOM.ul({}, [ | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Passphrase"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "One Time Passwords"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Preferences"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Delete account"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]) | ||||
| 						]) | ||||
| 					]), | ||||
| 					React.DOM.li({}, [ | ||||
| 						React.DOM.h1({}, "Data"), | ||||
| 					React.DOM.li({'className':this.state['subscription'] ? 'open' : 'closed'}, [ | ||||
| 						React.DOM.h1({'onClick':this.toggleState('subscription')}, "Subscription"), | ||||
| 						React.DOM.ul({}, [ | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "x1"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "x2"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "x3"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "x4"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]) | ||||
| 						]) | ||||
| 					]), | ||||
| 					React.DOM.li({'className':this.state['data'] ? 'open' : 'closed'}, [ | ||||
| 						React.DOM.h1({'onClick':this.toggleState('data')}, "Data"), | ||||
| 						React.DOM.ul({}, [ | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Offline copy"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "With just one click you can dump all your encrypted data from Clipperz servers to your hard disk and create a read-only offline version of Clipperz to be used when you are not connected to the Internet."), | ||||
| 									React.DOM.a({'onClick':this.handleDownloadOfflineCopyLink}, "Download") | ||||
| 									React.DOM.a({'className':'button', 'onClick':this.handleDownloadOfflineCopyLink}, "Download") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Import"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Export"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Sharing"), | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Import"), | ||||
| 							]), | ||||
| 							React.DOM.li({}, [ | ||||
| 								React.DOM.h2({}, "Export"), | ||||
| 								React.DOM.div({}, [ | ||||
| 									React.DOM.p({}, "") | ||||
| 								]) | ||||
| 							]) | ||||
| 						]) | ||||
| 					]), | ||||
| 					React.DOM.li({}, [ | ||||
| 						React.DOM.h1({}, "Tools"), | ||||
| 					]) | ||||
| 				]) | ||||
| 			]) | ||||
|   | ||||
| @@ -30,16 +30,10 @@ Clipperz.PM.UI.Components.Panels.MainPanel = React.createClass({ | ||||
|  | ||||
| 	propTypes: { | ||||
| 		'messageBox':		React.PropTypes.object.isRequired, | ||||
| 		'featureSet':		React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL']).isRequired, | ||||
| 		'featureSet':		React.PropTypes.oneOf(['FULL', 'EXPIRED', 'TRIAL', 'OFFLINE']).isRequired, | ||||
| 		'style':			React.PropTypes.oneOf(Clipperz_PM_UI_availableStyles).isRequired, | ||||
| 	}, | ||||
|  | ||||
| 	getDefaultProps: function () { | ||||
| 		return { | ||||
| 			featureSet: 'FULL' | ||||
| 		}; | ||||
| 	}, | ||||
|  | ||||
| 	style: function () { | ||||
| 		return this.props['style']; | ||||
| 	}, | ||||
| @@ -66,7 +60,13 @@ Clipperz.PM.UI.Components.Panels.MainPanel = React.createClass({ | ||||
| 	}, | ||||
|  | ||||
| 	renderCardFrame: function (firstColumnComponents, secondColumnComponents) { | ||||
| 		var	addCardButton = React.DOM.div({'className': 'addCardButton', 'onClick':this.handleAddCardClick}, 'add card'); | ||||
| 		var	addCardButton; | ||||
|  | ||||
| 		if ((this.props['featureSet'] != 'EXPIRED') && (this.props['featureSet'] != 'OFFLINE')) { | ||||
| 			addCardButton = React.DOM.div({'className': 'addCardButton', 'onClick':this.handleAddCardClick}, 'add card'); | ||||
| 		} else { | ||||
| 			addCardButton = null; | ||||
| 		} | ||||
|  | ||||
| 		return React.DOM.div({'key':'cardContent', 'className':'cardContent'}, [ | ||||
| 			React.DOM.div({'className':'cardListColumn column'}, [addCardButton, firstColumnComponents]), | ||||
| @@ -82,7 +82,8 @@ Clipperz.PM.UI.Components.Panels.MainPanel = React.createClass({ | ||||
| 		cardToolbarProps = MochiKit.Base.merge(this.props, { | ||||
| 			'key':				'toolbar', | ||||
| 			'style':			this.style(), | ||||
| 			'enableSidePanels':	(this.props['featureSet'] != 'EXPIRED') | ||||
| //			'enableSidePanels':	(this.props['featureSet'] != 'EXPIRED') | ||||
| 			'enableSidePanels':	true, | ||||
| 		}); | ||||
| 		 | ||||
| 		return Clipperz.PM.UI.Components.CardToolbar(cardToolbarProps); | ||||
|   | ||||
| @@ -581,6 +581,7 @@ console.log("THE BROWSER IS OFFLINE"); | ||||
| 		var	fullFilterCriteria; | ||||
| 		var	selectedCardReference = this._selectedCardInfo ? this._selectedCardInfo['reference'] : null; | ||||
|  | ||||
| //console.log("updateSelectedCards - ACCOUNT INFO.featureSet", this.userAccountInfo()['featureSet']); | ||||
| 		if (aFilter['type'] == 'ALL') { | ||||
| 			filterCriteria = MochiKit.Base.operator.truth; | ||||
| 			sortCriteria = Clipperz.Base.caseInsensitiveKeyComparator('label'); | ||||
| @@ -884,7 +885,7 @@ console.log("THE BROWSER IS OFFLINE"); | ||||
| 		level = 'HIDE'; | ||||
| 		 | ||||
| //console.log("messageBox - this.user()", this.user()); | ||||
| 		if (this.user() != null && this.user().accountInfo() != null && this.user().accountInfo().featureSet() == 'EXPIRED') { | ||||
| 		if (this.userAccountInfo()['featureSet'] == 'EXPIRED') { | ||||
| 			message = "Exprired subscription"; | ||||
| 			level = 'ERROR'; | ||||
| 		} | ||||
| @@ -905,6 +906,7 @@ console.log("THE BROWSER IS OFFLINE"); | ||||
| 				'currentSubscriptionType', | ||||
| 				'expirationDate', | ||||
| 				'featureSet', | ||||
| 				'features', | ||||
| 				'isExpired', | ||||
| 				'isExpiring', | ||||
| 				'paymentVerificationPending' | ||||
| @@ -944,9 +946,10 @@ console.log("THE BROWSER IS OFFLINE"); | ||||
| 		} else if (aPageName == 'mainPage') { | ||||
| 			extraProperties = { | ||||
| 				'messageBox':					this.messageBoxContent(), | ||||
| 				'accountStatus':				this.userAccountInfo(), | ||||
| 				'accountInfo':					this.userAccountInfo(), | ||||
| 				'selectionPanelStatus':			this.isSelectionPanelOpen()	? 'OPEN' : 'CLOSED', | ||||
| 				'settingsPanelStatus':			this.isSettingsPanelOpen()	? 'OPEN' : 'CLOSED', | ||||
| 				'featureSet':					this.userAccountInfo()['featureSet'], | ||||
| //				'shouldIncludeArchivedCards':	this.shouldIncludeArchivedCards(), | ||||
| //				'cards':				…, | ||||
| //				'tags':					…, | ||||
| @@ -1135,9 +1138,15 @@ console.log("THE BROWSER IS OFFLINE"); | ||||
| 	}, | ||||
|  | ||||
| 	selectCard_handler: function (someInfo, shouldUpdateCardDetail) { | ||||
| 		this._selectedCardInfo = someInfo; | ||||
| 		this.refreshSelectedCards(); | ||||
| 		this.updateSelectedCard(someInfo, true, shouldUpdateCardDetail); | ||||
| 		if (this.userAccountInfo()['featureSet'] != 'EXPIRED') { | ||||
| 			this._selectedCardInfo = someInfo; | ||||
| 			this.refreshSelectedCards(); | ||||
| 			this.updateSelectedCard(someInfo, true, shouldUpdateCardDetail); | ||||
|  | ||||
| //			# TODO:	make the selected element visible;  | ||||
| //					this may not always be the case, as selection can also be changed using keys. | ||||
| //			MochiKit.Visual.ScrollTo(MochiKit.DOM.getElement("xxx")); | ||||
| 		} | ||||
| 	}, | ||||
|  | ||||
| 	refreshCardEditDetail_handler: function (aRecordReference) { | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 Giulio Cesare Solaroli
					Giulio Cesare Solaroli