This topic provides the complete code sample used in Quickstart: Manipulation gestures.
This topic contains these sections:
Download location
This sample is not available for download.
Technologies
| Programming languages | C++ |
|---|---|
| Programming models | Windows Runtime |
Requirements
| Minimum supported client | Windows 8 |
|---|---|
| Minimum supported server | Windows Server 2012 |
| Minimum required SDK | Microsoft Visual Studio Express 2012 for Windows 8 |
View the code ()
default.css
body {
/*
A manipulation-blocking element is defined as an element that explicitly
blocks direct manipulation via declarative markup, and instead fires gesture
events such as MSGestureStart, MSGestureChange, and MSGestureEnd.
*/
overflow: hidden;
position: absolute;
font-family: 'Segoe UI';
font-size: small;
-ms-touch-action: none;
background-color: black;
}
div #targetContainer {
position: relative;
height: fill-available;
width: fill-available;
}
div #inputBox {
position: relative;
width: 640px;
height: 640px;
color: black;
overflow: hidden;
background-color: darkgrey;
margin: 0px;
padding: 0px;
border-width: 1px;
border-color: white;
border-style: solid;
}
div #instructions {
position: relative;
width: 100%;
height: fit-content;
color: black;
background-color: white;
visibility: visible;
}
div #questions {
position: relative;
width: 100%;
height: fit-content;
color: white;
background-color: black;
visibility: visible;
}
div #answers {
position: relative;
width: 100%;
height: fit-content;
color: white;
background-color: black;
visibility: visible;
}
div #clues {
position: relative;
width: 100%;
height: 100%;
background-color: DimGray;
}
div #timerBox {
background-color: red;
color: black;
position: absolute;
width: 100%;
bottom: 0px;
height: 20px;
text-align: center;
}
div #answerFloater {
position: absolute;
visibility: hidden;
top: 0px;
left: 0px;
background-color: blue;
}
div #eventLog {
font-size: xx-small;
position: absolute;
left: 0px;
top: 0px;
width: 640px;
height: 50px;
overflow: auto;
overflow-style: auto;
}
default.html
<html> <head> <meta charset="utf-8" /> <title>Manipulation Gestures</title> <!-- WinJS references --> <link rel="stylesheet" href="//Microsoft.WinJS.1.0/css/ui-light.css" /> <script src="//Microsoft.WinJS.1.0/js/base.js"></script> <script src="//Microsoft.WinJS.1.0/js/ui.js"></script> <!-- BasicGesture references --> <link href="/css/default.css" rel="stylesheet" /> <script src="/js/InputProcessor.js"></script> <script src="/js/ManipulationManager.js"></script> <script src="/js/default.js"></script> </head> <body> <div class="Container" id="Container"> <div id="targetTitle">Manipulation gestures (rotation)</div> <div class="TargetContainer" id="targetContainer"> <div id="target" draggable="false"></div> </div> <div id="targetFooter"> </div> </div> </body> </html>
default.js
(function () { "use strict"; /// <summary> /// Initializes the target and manipulation handling. /// </summary> function initialize() { var container = document.getElementById("targetContainer"); var target = document.getElementById("target"); var title = document.getElementById("targetTitle"); var footer = document.getElementById("targetFooter"); // Set the height of the target container for initial positioning of the target. var containerHeight = window.innerHeight - title.clientHeight - footer.clientHeight; container.style.height = containerHeight + "px"; // Set the initial position of the target. target.style.msTransform = (new MSCSSMatrix()). translate((container.clientWidth - parseInt(target.clientWidth)) / 2.0, (containerHeight - parseInt(target.clientHeight)) / 2.0); // Configure manipulation handling. var manipulable = new Manipulator.ManipulationManager(); // The configuration function can support all manipulations. // For this example, we limit manipulation support to rotation with inertia. manipulable.configure(false, true, // Rotation. false, true, // Inertia. 1, 0, { x: (container.clientWidth - parseInt(target.clientWidth)) / 2.0, y: (containerHeight - parseInt(target.clientHeight)) / 2.0 }); manipulable.setElement(target); manipulable.setParent(container); // Handler for transforms related to the manipulation. manipulable.registerMoveHandler({ x: (container.clientWidth / 2.0), y: (containerHeight / 2.0) }, Manipulator.ManipulationManager.FixPivot.MoveHandler); } document.addEventListener("DOMContentLoaded", initialize, false); })();
InputProcessor.js
/// <summary> /// InputProcessor is a thin wrapper for pointer event handling and gesture detection. /// Defines an InputProcessor class that takes all pointer event data and feeds it to /// a GestureRecognizer for processing of the manipulation gestures /// as configured in ManipulationManager.js. /// </summary> (function () { "use strict"; WinJS.Namespace.define("Manipulator", { InputProcessor: WinJS.Class.define(function () { // Constructor. this._gestureRecognizer = new Windows.UI.Input.GestureRecognizer(); this._downPoint = null; this._lastState = null; }, { // Instance members. element: { /// <summary> /// The manipulable element. /// </summary> get: function () { if (!this._element) { return null; } return this._element; }, set: function (value) { this._element = value; this._setupElement(); } }, parent: { /// <summary> /// The container that defines the coordinate space used /// for transformations during manipulation of the target. /// </summary> get: function () { if (!this._parent) { return null; } return this._parent; }, set: function (value) { this._parent = value; } }, getRecognizer: function () { /// <summary> /// The gesture recognition object. /// </summary> return this._gestureRecognizer; }, getDown: function () { /// <summary> /// The pointer data for the MSPointerDown event. /// </summary> return this._downPoint; }, _setupElement: function () { /// <summary> /// Declare the event listeners for the pointer events on the target. /// </summary> var that = this; this._element.addEventListener("MSPointerDown", function (evt) { Manipulator.InputProcessor._handleDown(that, evt); }, false); this._element.addEventListener("MSPointerMove", function (evt) { Manipulator.InputProcessor._handleMove(that, evt); }, false); this._element.addEventListener("MSPointerUp", function (evt) { Manipulator.InputProcessor._handleUp(that, evt); }, false); this._element.addEventListener("MSPointerCancel", function (evt) { Manipulator.InputProcessor._handleCancel(that, evt); }, false); this._element.addEventListener("wheel", function (evt) { Manipulator.InputProcessor._handleMouse(that, evt); }, false); } }, { // Static members. _handleDown: function (that, evt) { /// <summary> /// Handler for the MSPointerDown event. /// </summary> /// <param name="that" type="Object"> /// The InputProcessor object handling this event. /// </param> /// <param name="evt" type="Event"> /// The event object. /// </param> var pp = evt.getCurrentPoint(that._parent); that._element.msSetPointerCapture(pp.pointerId); that._gestureRecognizer.processDownEvent(pp); // Prevent propagation of this event to additional event handlers. evt.stopImmediatePropagation(); // Capture the pointer location for this event. that._downPoint = { x: pp.position.x, y: pp.position.y }; }, _handleMove: function (that, evt) { /// <summary> /// Handler for the MSPointerMove event. /// </summary> /// <param name="that" type="Object"> /// The InputProcessor object handling this event. /// </param> /// <param name="evt" type="Event"> /// The event object. /// </param> var pps = evt.getIntermediatePoints(that._parent); that._gestureRecognizer.processMoveEvents(pps); // Prevent propagation of this event to additional event handlers. evt.stopImmediatePropagation(); }, _handleUp: function (that, evt) { /// <summary> /// Handler for the MSPointerUp event. /// </summary> /// <param name="that" type="Object"> /// The InputProcessor object handling this event. /// </param> /// <param name="evt" type="Event"> /// The event object. /// </param> var pp = evt.getCurrentPoint(that._parent); that._gestureRecognizer.processUpEvent(pp); // Prevent propagation of this event to additional event handlers. evt.stopImmediatePropagation(); }, _handleCancel: function (that, evt) { /// <summary> /// Handler for the MSPointerCancel event. /// </summary> /// <param name="that" type="Object"> /// The InputProcessor object handling this event. /// </param> /// <param name="evt" type="Event"> /// The event object. /// </param> that._gestureRecognizer.completeGesture(); // Prevent propagation of this event to additional event handlers. evt.stopImmediatePropagation(); }, _handleMouse: function (that, evt) { /// <summary> /// Handler for the mouse wheel event. /// </summary> /// <param name="that" type="Object"> /// The InputProcessor object handling this event. /// </param> /// <param name="evt" type="Event"> /// The event object. /// </param> var pp = evt.getCurrentPoint(that._parent); that._gestureRecognizer.processMouseWheelEvent(pp, evt.shiftKey, evt.ctrlKey); // Prevent propagation of this event to additional event handlers. evt.stopImmediatePropagation(); evt.preventDefault(); } }) }); })();
ManipulationManager.js
/// <summary> /// ManipulationManager is the manipulation processing engine for the /// GestureRecognizer object defined in InputProcessor.js. /// Different components and behaviors of manipulation (rotate, translate, zoom, /// and inertia) can be enabled, disabled, and customized as required. /// </summary> (function () { "use strict"; WinJS.Namespace.define("Manipulator", { ManipulationManager: WinJS.Class.define(function () { // Constructor. // Create an input processor. this._inputProcessor = new Manipulator.InputProcessor(); // Initialize the manipulation movement and end handlers. this._endHandler = null; this._moveHandler = null; // Create the transform matrices used for manipulating // and resetting the target. this._currentTransform = new MSCSSMatrix(); this._initialTransform = new MSCSSMatrix(); // Initialize the transform matrices values. this._initialTransformParams = { translation: { x: 0, y: 0 }, rotation: 0, scale: 1 }; this._currentTransformParams = { translation: { x: 0, y: 0 }, rotation: 0, scale: 1 }; }, { // Instance members. configure: function (scale, rotate, translate, inertia, initialScale, initialRotate, initialTranslate) { /// <summary> /// Define the behaviors of the ManipulationManager object. /// </summary> /// <param name="scale" type="Boolean"> /// True if scaling is enabled. /// </param> /// <param name="rotate" type="Boolean"> /// True if rotation is enabled. /// </param> /// <param name="translate" type="Boolean"> /// True if translation is enabled. /// </param> /// <param name="inertia" type="Boolean"> /// True if inertia is enabled. /// </param> /// <param name="initialScale" type="Number"> /// The initial scale factor. /// </param> /// <param name="initialRotate" type="Number"> /// The initial rotation value. /// </param> /// <param name="initialTranslate" type="Object"> /// The initial translation values (x,y). /// </param> // Get the GestureRecognizer associated with this manipulation manager. var gr = this._inputProcessor.getRecognizer(); // Set the manipulations supported by the GestureRecognizer if the // interaction is not already being processed. if (!gr.isActive) { var settings = 0; if (scale) { settings |= Windows.UI.Input.GestureSettings.manipulationScale; if (inertia) { settings |= Windows.UI.Input.GestureSettings.manipulationScaleInertia; } } if (rotate) { settings |= Windows.UI.Input.GestureSettings.manipulationRotate; if (inertia) { settings |= Windows.UI.Input.GestureSettings.manipulationRotateInertia; } } if (translate) { settings |= Windows.UI.Input.GestureSettings.manipulationTranslateX | Windows.UI.Input.GestureSettings.manipulationTranslateY; if (inertia) { settings |= Windows.UI.Input.GestureSettings.manipulationTranslateInertia; } } // Cache a reference to the current object. var that = this; // If any manipulation is supported, declare the manipulation event listeners. if (scale || rotate || translate) { gr.addEventListener('manipulationstarted', function (evt) { Manipulator.ManipulationManager._manipulationStarted(that, evt); }, false); gr.addEventListener('manipulationupdated', function (evt) { Manipulator.ManipulationManager._manipulationUpdated(that, evt); }, false); gr.addEventListener('manipulationended', function (evt) { Manipulator.ManipulationManager._manipulationEnded(that, evt); }, false); } gr.gestureSettings = settings; // Initialize the transform matrices. this._currentTransformParams.scale = initialScale; this._currentTransformParams.rotation = initialRotate; this._currentTransformParams.translation = initialTranslate; this._initialTransformParams.scale = initialScale; this._initialTransformParams.rotation = initialRotate; this._initialTransformParams.translation = initialTranslate; // Set the transformation values. if (initialRotate) { this._initialTransform = this._initialTransform.rotate(initialRotate); } else { this._currentTransformParams.rotation = 0; this._initialTransformParams.rotation = 0; } if (initialTranslate) { this._initialTransform = this._initialTransform.translate(initialTranslate.x, initialTranslate.y); } else { this._currentTransformParams.translation = { x: 0, y: 0 }; this._initialTransformParams.translation = { x: 0, y: 0 }; } if (initialScale) { this._initialTransform = this._initialTransform.scale(initialScale); } else { this._currentTransformParams.scale = 1; this._initialTransformParams.scale = 1; } this._currentTransform = this._initialTransform; } }, setElement: function (elm) { /// <summary> /// Set the manipulable object. /// </summary> /// <param name="elm" type="Object"> /// The object that supports manipulation. /// </param> this._inputProcessor.element = elm; // Set the transform origin for rotation and scale manipulations. this._inputProcessor.element.style.msTransformOrigin = "0 0"; }, setParent: function (elm) { /// <summary> /// Set the parent of the manipulable object. /// </summary> /// <param name="elm" type="Object"> /// The parent of the object that supports manipulation. /// </param> this._inputProcessor.parent = elm; }, registerEndHandler: function (handler) { /// <summary> /// Register handler to be called after the manipulation is complete. /// </summary> /// <param name="handler" type="Function"> /// The manipulationended event handler. /// </param> this._endHandler = handler; }, registerMoveHandler: function (arg, handler) { /// <summary> /// Register handler to be called when manipulation is under way. /// </summary> /// <param name="args"> /// Arguments passed to the move handler function. /// </param> /// <param name="handler" type="Function"> /// The manipulationupdated event handler. /// </param> this._moveHandlerArg = arg; this._moveHandler = handler; }, resetAllTransforms: function () { /// <summary> /// Reset the ManipulationManager object to its initial state. /// </summary> // Check that the element has been registered before before attempting to reset. if (this._inputProcessor.element) { // Reapply the initial transform this._inputProcessor.element.style.transform = this._initialTransform.toString(); this._currentTransform = this._initialTransform; // Reset the current transform parameters to their initial values. this._currentTransformParams.translation = this._initialTransformParams.translation; this._currentTransformParams.rotation = this._initialTransformParams.rotation; this._currentTransformParams.scale = this._initialTransformParams.scale; } }, _applyMotion: function (pivot, translation, rotation, scaling) { /// <summary> /// Apply the manipulation transform to the target. /// </summary> /// <param name="pivot" type="Object"> /// The X,Y values for the rotation and scaling pivot point. /// </param> /// <param name="translation" type="Object"> /// The X,Y values for the translation delta. /// </param> /// <param name="rotation" type="Number"> /// The angle of rotation. /// </param> /// <param name="scaling" type="Number"> /// The scaling factor. /// </param> // Create the transform, apply parameters, and multiply by the current transform matrix. var transform = new MSCSSMatrix().translate(pivot.x, pivot.y). translate(translation.x, translation.y). rotate(rotation). scale(scaling). translate(-pivot.x, -pivot.y).multiply(this._currentTransform); this._inputProcessor.element.style.transform = transform.toString(); this._currentTransform = transform; }, _updateTransformParams: function (delta) { /// <summary> /// Update the current transformation parameters based on the new delta. /// </summary> /// <param name="that" type="Object"> /// The change in rotation, scaling, and translation. /// </param> this._currentTransformParams.translation.x = this._currentTransformParams.translation.x + delta.translation.x; this._currentTransformParams.translation.y = this._currentTransformParams.translation.y + delta.translation.y; this._currentTransformParams.rotation = this._currentTransformParams.rotation + delta.rotation; this._currentTransformParams.scale = this._currentTransformParams.scale * delta.scale; } }, { // Static members. _manipulationStarted: function (that, evt) { /// <summary> /// The manipulationstarted event handler. /// </summary> /// <param name="that" type="Object"> /// ManipulationManager object on which the event was performed. /// </param> /// <param name="evt" type="Event"> /// The event data. /// </param> Manipulator.ManipulationManager._manipulationHelper(that, evt); }, _manipulationUpdated: function (that, evt) { /// <summary> /// The manipulationupdated event handler. /// </summary> /// <param name="that" type="Object"> /// ManipulationManager object on which the event was performed. /// </param> /// <param name="evt" type="Event"> /// The event data. /// </param> Manipulator.ManipulationManager._manipulationHelper(that, evt); }, _manipulationEnded: function (that, evt) { /// <summary> /// The manipulationended event handler. /// </summary> /// <param name="that" type="Object"> /// ManipulationManager object on which the event was performed. /// </param> /// <param name="evt" type="Event"> /// The event data. /// </param> // Pass the event to the manipulation helper function. Manipulator.ManipulationManager._manipulationHelper(that, evt); // Call the manipulationended handler, if registered. if (that._endHandler) { that._endHandler(); } }, _manipulationHelper: function (that, evt) { /// <summary> /// Helper function for calculating and applying the transformation parameter deltas. /// </summary> /// <param name="that" type="Object"> /// ManipulationManager object on which the event was performed. /// </param> /// <param name="evt" type="Event"> /// The event data. /// </param> if (evt.delta) { // Rotation/scaling pivot point. var pivot = { x: evt.position.x, y: evt.position.y }; // Translation values. var translation = { x: evt.delta.translation.x, y: evt.delta.translation.y }; // Rotation angle. var rotation = evt.delta.rotation; // Scale factor. var scale = evt.delta.scale; // Group the transformation parameter deltas. var delta = { pivot: pivot, translation: translation, rotation: rotation, scale: scale }; // Apply the manipulation movement constraints. if (that._moveHandler) { delta = that._moveHandler(that._moveHandlerArg, delta, that._currentTransformParams, that._currentTransform); } // Update the transformation parameters with fresh deltas. that._updateTransformParams(delta); // Apply the transformation. that._applyMotion(delta.pivot, delta.translation, delta.rotation, delta.scale); } }, FixPivot: WinJS.Class.define(function () { /// <summary> /// Constrain the center of manipulation (or pivot point) to a set of X,Y coordinates, /// instead of the centroid of the pointers associated with the manipulation. /// <param name="pivot" type="Object"> /// The pivot coordinates for the ManipulationManager object. /// </param> /// <param name="delta" type="Object"> /// The transformation parameter deltas (pivot, delta, rotation, scale). /// </param> /// </summary> }, { }, { MoveHandler: function (pivot, delta) { delta.pivot = pivot; return delta; } }), }) }); })();
Build date: 11/29/2012