UNPKG

mobileoa-common-modules

Version:

移动办公平台前端公共功能模块

225 lines (204 loc) 7.05 kB
'use strict'; var angular = require('angular'); require('../modules'); require('./GestureScreenLayout'); var module = angular.module('gesturepassword.services'); module.factory('GestureScreenContext', function(GestureScreenLayout, $rootScope) { function GestureScreenContext(width, height, validator, setpassword, ctx) { this.setpassword = setpassword; this.ctx = ctx; this.firstpassword = ''; this.width = width; this.height = height; this.validator = validator || function() {return true;}; this.layout = new GestureScreenLayout(width, height).calc(); this.contentWidth = this.layout.content.width; this.contentHeight = this.layout.content.height; this.pointers = GestureScreenContext.generatePoints(this.layout.content); this.selectors = []; this.sceneState = GestureScreenContext.STATE_PRIMITIVE; this.addedSelectors = []; } GestureScreenContext.POINTER_NUMBER = 9; GestureScreenContext.STATE_PRIMITIVE = 0; GestureScreenContext.STATE_MOVING = 1; GestureScreenContext.STATE_OK = 2; GestureScreenContext.STATE_NO = 3; GestureScreenContext.POINTER_STATE_PRIMITIVE = 0; GestureScreenContext.POINTER_STATE_SELECTED = 1; GestureScreenContext.POINTER_STATE_OK = 2; GestureScreenContext.POINTER_STATE_NO = 3; /** * 产生九个点。 * * @param {ContentLayout} 内容区域布局对象 * @return {Array} 返回九个点。 */ GestureScreenContext.generatePoints = function(contentLayout) { var startX = contentLayout.gap, startY = contentLayout.topWhite, radius = contentLayout.radius, gap = contentLayout.gap, pointers = []; for (var i = 0; i < GestureScreenContext.POINTER_NUMBER; i++) { var relativeX = i % 3, relativeY = Math.floor(i / 3); pointers.push({ y: (startY + (2 * relativeY + 1) * radius + relativeY * gap + 0.5) | 0, x: (startX + (2 * relativeX + 1) * radius + relativeX * gap + 0.5) | 0, radius: radius, state: GestureScreenContext.STATE_PRIMITIVE }); } return pointers; }; GestureScreenContext.pointerInCircle = function(circle, pointer) { return Math.pow((circle.x - pointer.x), 2) + Math.pow(circle.y - pointer.y, 2) <= Math.pow(circle.radius, 2); }; /** * 矫正两点之间的两线,若之间还有点,应该连上 * @param {[Array]} selectors 已选择的点 * @param {[int]} selector 当前选择的点 * @return {[int]} 返回中间点索引 */ GestureScreenContext.makeLineCorrect = function(selectors, selector) { if (selectors.length <= 0) { return; } var array = [ '0,8,4','8,0,4','2,6,4','6,2,4','0,6,3','6,0,3','1,7,4','7,1,4', '2,8,5','8,2,5','0,2,1','2,0,1','3,5,4','5,3,4','6,8,7','8,6,7' ], linkSelector = selectors[selectors.length - 1] + ',' + selector, i; for (i = 0; i < array.length; i ++) { var currentGroup = array[i]; if (currentGroup.substring(0, 3) === linkSelector) { return parseInt(currentGroup.charAt(currentGroup.length - 1)); } } }; GestureScreenContext.prototype = { /** * 开始移动 * * @param {Number} x * @param {Number} y */ startMove: function() { if (this.sceneState === GestureScreenContext.STATE_PRIMITIVE) { this.setState(GestureScreenContext.STATE_MOVING); } else if (this.sceneState === GestureScreenContext.STATE_NO) { this.setState(GestureScreenContext.STATE_PRIMITIVE); this.setState(GestureScreenContext.STATE_MOVING); } }, /** * 移动中 * * @param {Number} x * @param {Number} y */ move: function(x, y) { if (this.sceneState === GestureScreenContext.STATE_MOVING) { this.movingPointer = { x: (x - this.layout.content.startX + 0.5) | 0, y: (y - this.layout.content.startY + 0.5) | 0 }; this.checkSelectors(); } }, /** * 移动结束 * * @return */ endMove: function() { var result = this.validate(), toState = result? GestureScreenContext.STATE_OK : GestureScreenContext.STATE_NO; delete this.movingPointer; this.setState(toState); return result; }, setState: function(state) { var stateChanged = this.sceneState !== state; this.sceneState = state; switch(state) { case GestureScreenContext.STATE_PRIMITIVE: this.reset(); break; case GestureScreenContext.STATE_MOVING: break; case GestureScreenContext.STATE_OK: this.changeSelectorPointersState(GestureScreenContext.POINTER_STATE_OK); break; case GestureScreenContext.STATE_NO: this.changeSelectorPointersState(GestureScreenContext.POINTER_STATE_NO); break; } if (stateChanged) { $rootScope.$broadcast('gesturepassword.statechange', this, state); $rootScope.$emit('gesturepassword.statechange', this, state); } }, changeSelectorPointersState: function(state) { var i, index, pointer; for (i = this.selectors.length; i--;) { index = this.selectors[i]; pointer = this.pointers[index]; pointer.state = state; } }, reset: function() { this.selectors = []; _.forEach(this.pointers, function(pointer) { pointer.state = GestureScreenContext.POINTER_STATE_PRIMITIVE; }); delete this.movingPointer; }, /** * */ checkSelectors: function () { var i, pointer, pointerMiddle; for (i = this.pointers.length; i--;) { pointer = this.pointers[i]; if (GestureScreenContext.pointerInCircle(pointer, this.movingPointer)) { if (pointer.state !== GestureScreenContext.POINTER_STATE_SELECTED) { pointer.state = GestureScreenContext.POINTER_STATE_SELECTED; var j = GestureScreenContext.makeLineCorrect(this.selectors, i); if(j >= 0) { pointerMiddle = this.pointers[j]; if (pointerMiddle.state !== GestureScreenContext.POINTER_STATE_SELECTED) { pointerMiddle.state = GestureScreenContext.POINTER_STATE_SELECTED; this.selectors.push(j); this.addedSelectors.push(j); } } this.selectors.push(i); this.addedSelectors.push(i); } return; } } }, /** * 移动结束后验证正确与否 */ validate: function() { return this.validator(this.selectors); }, /** * 传入第一次设置的密码,是缩略图在第一次成功设置密码时,把密码传入 */ setFirspassword: function(firstpassword) { this.firstpassword = firstpassword; }, destroy: function() { delete this.layout; delete this.ctx; delete this.validator; delete this.pointers; } }; return GestureScreenContext; });