Input.h revision 771526c88f5cc4b56a41cb12aa06a28d377a07d5
1/* 2 * Copyright (C) 2010 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17#ifndef _ANDROIDFW_INPUT_H 18#define _ANDROIDFW_INPUT_H 19 20/** 21 * Native input event structures. 22 */ 23 24#include <android/input.h> 25#include <utils/Vector.h> 26#include <utils/KeyedVector.h> 27#include <utils/Timers.h> 28#include <utils/RefBase.h> 29#include <utils/String8.h> 30#include <utils/BitSet.h> 31 32#ifdef HAVE_ANDROID_OS 33class SkMatrix; 34#endif 35 36/* 37 * Additional private constants not defined in ndk/ui/input.h. 38 */ 39enum { 40 /* Private control to determine when an app is tracking a key sequence. */ 41 AKEY_EVENT_FLAG_START_TRACKING = 0x40000000, 42 43 /* Key event is inconsistent with previously sent key events. */ 44 AKEY_EVENT_FLAG_TAINTED = 0x80000000, 45}; 46 47enum { 48 /* Motion event is inconsistent with previously sent motion events. */ 49 AMOTION_EVENT_FLAG_TAINTED = 0x80000000, 50}; 51 52enum { 53 /* 54 * Indicates that an input device has switches. 55 * This input source flag is hidden from the API because switches are only used by the system 56 * and applications have no way to interact with them. 57 */ 58 AINPUT_SOURCE_SWITCH = 0x80000000, 59}; 60 61/* 62 * SystemUiVisibility constants from View. 63 */ 64enum { 65 ASYSTEM_UI_VISIBILITY_STATUS_BAR_VISIBLE = 0, 66 ASYSTEM_UI_VISIBILITY_STATUS_BAR_HIDDEN = 0x00000001, 67}; 68 69/* 70 * Maximum number of pointers supported per motion event. 71 * Smallest number of pointers is 1. 72 * (We want at least 10 but some touch controllers obstensibly configured for 10 pointers 73 * will occasionally emit 11. There is not much harm making this constant bigger.) 74 */ 75#define MAX_POINTERS 16 76 77/* 78 * Maximum pointer id value supported in a motion event. 79 * Smallest pointer id is 0. 80 * (This is limited by our use of BitSet32 to track pointer assignments.) 81 */ 82#define MAX_POINTER_ID 31 83 84/* 85 * Declare a concrete type for the NDK's input event forward declaration. 86 */ 87struct AInputEvent { 88 virtual ~AInputEvent() { } 89}; 90 91/* 92 * Declare a concrete type for the NDK's input device forward declaration. 93 */ 94struct AInputDevice { 95 virtual ~AInputDevice() { } 96}; 97 98 99namespace android { 100 101#ifdef HAVE_ANDROID_OS 102class Parcel; 103#endif 104 105/* 106 * Flags that flow alongside events in the input dispatch system to help with certain 107 * policy decisions such as waking from device sleep. 108 * 109 * These flags are also defined in frameworks/base/core/java/android/view/WindowManagerPolicy.java. 110 */ 111enum { 112 /* These flags originate in RawEvents and are generally set in the key map. 113 * NOTE: If you edit these flags, also edit labels in KeycodeLabels.h. */ 114 115 POLICY_FLAG_WAKE = 0x00000001, 116 POLICY_FLAG_WAKE_DROPPED = 0x00000002, 117 POLICY_FLAG_SHIFT = 0x00000004, 118 POLICY_FLAG_CAPS_LOCK = 0x00000008, 119 POLICY_FLAG_ALT = 0x00000010, 120 POLICY_FLAG_ALT_GR = 0x00000020, 121 POLICY_FLAG_MENU = 0x00000040, 122 POLICY_FLAG_LAUNCHER = 0x00000080, 123 POLICY_FLAG_VIRTUAL = 0x00000100, 124 POLICY_FLAG_FUNCTION = 0x00000200, 125 126 POLICY_FLAG_RAW_MASK = 0x0000ffff, 127 128 /* These flags are set by the input dispatcher. */ 129 130 // Indicates that the input event was injected. 131 POLICY_FLAG_INJECTED = 0x01000000, 132 133 // Indicates that the input event is from a trusted source such as a directly attached 134 // input device or an application with system-wide event injection permission. 135 POLICY_FLAG_TRUSTED = 0x02000000, 136 137 // Indicates that the input event has passed through an input filter. 138 POLICY_FLAG_FILTERED = 0x04000000, 139 140 // Disables automatic key repeating behavior. 141 POLICY_FLAG_DISABLE_KEY_REPEAT = 0x08000000, 142 143 /* These flags are set by the input reader policy as it intercepts each event. */ 144 145 // Indicates that the screen was off when the event was received and the event 146 // should wake the device. 147 POLICY_FLAG_WOKE_HERE = 0x10000000, 148 149 // Indicates that the screen was dim when the event was received and the event 150 // should brighten the device. 151 POLICY_FLAG_BRIGHT_HERE = 0x20000000, 152 153 // Indicates that the event should be dispatched to applications. 154 // The input event should still be sent to the InputDispatcher so that it can see all 155 // input events received include those that it will not deliver. 156 POLICY_FLAG_PASS_TO_USER = 0x40000000, 157}; 158 159/* 160 * Describes the basic configuration of input devices that are present. 161 */ 162struct InputConfiguration { 163 enum { 164 TOUCHSCREEN_UNDEFINED = 0, 165 TOUCHSCREEN_NOTOUCH = 1, 166 TOUCHSCREEN_STYLUS = 2, 167 TOUCHSCREEN_FINGER = 3 168 }; 169 170 enum { 171 KEYBOARD_UNDEFINED = 0, 172 KEYBOARD_NOKEYS = 1, 173 KEYBOARD_QWERTY = 2, 174 KEYBOARD_12KEY = 3 175 }; 176 177 enum { 178 NAVIGATION_UNDEFINED = 0, 179 NAVIGATION_NONAV = 1, 180 NAVIGATION_DPAD = 2, 181 NAVIGATION_TRACKBALL = 3, 182 NAVIGATION_WHEEL = 4 183 }; 184 185 int32_t touchScreen; 186 int32_t keyboard; 187 int32_t navigation; 188}; 189 190/* 191 * Pointer coordinate data. 192 */ 193struct PointerCoords { 194 enum { MAX_AXES = 14 }; // 14 so that sizeof(PointerCoords) == 64 195 196 // Bitfield of axes that are present in this structure. 197 uint64_t bits; 198 199 // Values of axes that are stored in this structure packed in order by axis id 200 // for each axis that is present in the structure according to 'bits'. 201 float values[MAX_AXES]; 202 203 inline void clear() { 204 bits = 0; 205 } 206 207 float getAxisValue(int32_t axis) const; 208 status_t setAxisValue(int32_t axis, float value); 209 210 void scale(float scale); 211 void lerp(const PointerCoords& a, const PointerCoords& b, float alpha); 212 213 inline float getX() const { 214 return getAxisValue(AMOTION_EVENT_AXIS_X); 215 } 216 217 inline float getY() const { 218 return getAxisValue(AMOTION_EVENT_AXIS_Y); 219 } 220 221#ifdef HAVE_ANDROID_OS 222 status_t readFromParcel(Parcel* parcel); 223 status_t writeToParcel(Parcel* parcel) const; 224#endif 225 226 bool operator==(const PointerCoords& other) const; 227 inline bool operator!=(const PointerCoords& other) const { 228 return !(*this == other); 229 } 230 231 void copyFrom(const PointerCoords& other); 232 233private: 234 void tooManyAxes(int axis); 235}; 236 237/* 238 * Pointer property data. 239 */ 240struct PointerProperties { 241 // The id of the pointer. 242 int32_t id; 243 244 // The pointer tool type. 245 int32_t toolType; 246 247 inline void clear() { 248 id = -1; 249 toolType = 0; 250 } 251 252 bool operator==(const PointerProperties& other) const; 253 inline bool operator!=(const PointerProperties& other) const { 254 return !(*this == other); 255 } 256 257 void copyFrom(const PointerProperties& other); 258}; 259 260/* 261 * Input events. 262 */ 263class InputEvent : public AInputEvent { 264public: 265 virtual ~InputEvent() { } 266 267 virtual int32_t getType() const = 0; 268 269 inline int32_t getDeviceId() const { return mDeviceId; } 270 271 inline int32_t getSource() const { return mSource; } 272 273 inline void setSource(int32_t source) { mSource = source; } 274 275protected: 276 void initialize(int32_t deviceId, int32_t source); 277 void initialize(const InputEvent& from); 278 279 int32_t mDeviceId; 280 int32_t mSource; 281}; 282 283/* 284 * Key events. 285 */ 286class KeyEvent : public InputEvent { 287public: 288 virtual ~KeyEvent() { } 289 290 virtual int32_t getType() const { return AINPUT_EVENT_TYPE_KEY; } 291 292 inline int32_t getAction() const { return mAction; } 293 294 inline int32_t getFlags() const { return mFlags; } 295 296 inline int32_t getKeyCode() const { return mKeyCode; } 297 298 inline int32_t getScanCode() const { return mScanCode; } 299 300 inline int32_t getMetaState() const { return mMetaState; } 301 302 inline int32_t getRepeatCount() const { return mRepeatCount; } 303 304 inline nsecs_t getDownTime() const { return mDownTime; } 305 306 inline nsecs_t getEventTime() const { return mEventTime; } 307 308 // Return true if this event may have a default action implementation. 309 static bool hasDefaultAction(int32_t keyCode); 310 bool hasDefaultAction() const; 311 312 // Return true if this event represents a system key. 313 static bool isSystemKey(int32_t keyCode); 314 bool isSystemKey() const; 315 316 void initialize( 317 int32_t deviceId, 318 int32_t source, 319 int32_t action, 320 int32_t flags, 321 int32_t keyCode, 322 int32_t scanCode, 323 int32_t metaState, 324 int32_t repeatCount, 325 nsecs_t downTime, 326 nsecs_t eventTime); 327 void initialize(const KeyEvent& from); 328 329protected: 330 int32_t mAction; 331 int32_t mFlags; 332 int32_t mKeyCode; 333 int32_t mScanCode; 334 int32_t mMetaState; 335 int32_t mRepeatCount; 336 nsecs_t mDownTime; 337 nsecs_t mEventTime; 338}; 339 340/* 341 * Motion events. 342 */ 343class MotionEvent : public InputEvent { 344public: 345 virtual ~MotionEvent() { } 346 347 virtual int32_t getType() const { return AINPUT_EVENT_TYPE_MOTION; } 348 349 inline int32_t getAction() const { return mAction; } 350 351 inline int32_t getActionMasked() const { return mAction & AMOTION_EVENT_ACTION_MASK; } 352 353 inline int32_t getActionIndex() const { 354 return (mAction & AMOTION_EVENT_ACTION_POINTER_INDEX_MASK) 355 >> AMOTION_EVENT_ACTION_POINTER_INDEX_SHIFT; 356 } 357 358 inline void setAction(int32_t action) { mAction = action; } 359 360 inline int32_t getFlags() const { return mFlags; } 361 362 inline void setFlags(int32_t flags) { mFlags = flags; } 363 364 inline int32_t getEdgeFlags() const { return mEdgeFlags; } 365 366 inline void setEdgeFlags(int32_t edgeFlags) { mEdgeFlags = edgeFlags; } 367 368 inline int32_t getMetaState() const { return mMetaState; } 369 370 inline void setMetaState(int32_t metaState) { mMetaState = metaState; } 371 372 inline int32_t getButtonState() const { return mButtonState; } 373 374 inline float getXOffset() const { return mXOffset; } 375 376 inline float getYOffset() const { return mYOffset; } 377 378 inline float getXPrecision() const { return mXPrecision; } 379 380 inline float getYPrecision() const { return mYPrecision; } 381 382 inline nsecs_t getDownTime() const { return mDownTime; } 383 384 inline void setDownTime(nsecs_t downTime) { mDownTime = downTime; } 385 386 inline size_t getPointerCount() const { return mPointerProperties.size(); } 387 388 inline const PointerProperties* getPointerProperties(size_t pointerIndex) const { 389 return &mPointerProperties[pointerIndex]; 390 } 391 392 inline int32_t getPointerId(size_t pointerIndex) const { 393 return mPointerProperties[pointerIndex].id; 394 } 395 396 inline int32_t getToolType(size_t pointerIndex) const { 397 return mPointerProperties[pointerIndex].toolType; 398 } 399 400 inline nsecs_t getEventTime() const { return mSampleEventTimes[getHistorySize()]; } 401 402 const PointerCoords* getRawPointerCoords(size_t pointerIndex) const; 403 404 float getRawAxisValue(int32_t axis, size_t pointerIndex) const; 405 406 inline float getRawX(size_t pointerIndex) const { 407 return getRawAxisValue(AMOTION_EVENT_AXIS_X, pointerIndex); 408 } 409 410 inline float getRawY(size_t pointerIndex) const { 411 return getRawAxisValue(AMOTION_EVENT_AXIS_Y, pointerIndex); 412 } 413 414 float getAxisValue(int32_t axis, size_t pointerIndex) const; 415 416 inline float getX(size_t pointerIndex) const { 417 return getAxisValue(AMOTION_EVENT_AXIS_X, pointerIndex); 418 } 419 420 inline float getY(size_t pointerIndex) const { 421 return getAxisValue(AMOTION_EVENT_AXIS_Y, pointerIndex); 422 } 423 424 inline float getPressure(size_t pointerIndex) const { 425 return getAxisValue(AMOTION_EVENT_AXIS_PRESSURE, pointerIndex); 426 } 427 428 inline float getSize(size_t pointerIndex) const { 429 return getAxisValue(AMOTION_EVENT_AXIS_SIZE, pointerIndex); 430 } 431 432 inline float getTouchMajor(size_t pointerIndex) const { 433 return getAxisValue(AMOTION_EVENT_AXIS_TOUCH_MAJOR, pointerIndex); 434 } 435 436 inline float getTouchMinor(size_t pointerIndex) const { 437 return getAxisValue(AMOTION_EVENT_AXIS_TOUCH_MINOR, pointerIndex); 438 } 439 440 inline float getToolMajor(size_t pointerIndex) const { 441 return getAxisValue(AMOTION_EVENT_AXIS_TOOL_MAJOR, pointerIndex); 442 } 443 444 inline float getToolMinor(size_t pointerIndex) const { 445 return getAxisValue(AMOTION_EVENT_AXIS_TOOL_MINOR, pointerIndex); 446 } 447 448 inline float getOrientation(size_t pointerIndex) const { 449 return getAxisValue(AMOTION_EVENT_AXIS_ORIENTATION, pointerIndex); 450 } 451 452 inline size_t getHistorySize() const { return mSampleEventTimes.size() - 1; } 453 454 inline nsecs_t getHistoricalEventTime(size_t historicalIndex) const { 455 return mSampleEventTimes[historicalIndex]; 456 } 457 458 const PointerCoords* getHistoricalRawPointerCoords( 459 size_t pointerIndex, size_t historicalIndex) const; 460 461 float getHistoricalRawAxisValue(int32_t axis, size_t pointerIndex, 462 size_t historicalIndex) const; 463 464 inline float getHistoricalRawX(size_t pointerIndex, size_t historicalIndex) const { 465 return getHistoricalRawAxisValue( 466 AMOTION_EVENT_AXIS_X, pointerIndex, historicalIndex); 467 } 468 469 inline float getHistoricalRawY(size_t pointerIndex, size_t historicalIndex) const { 470 return getHistoricalRawAxisValue( 471 AMOTION_EVENT_AXIS_Y, pointerIndex, historicalIndex); 472 } 473 474 float getHistoricalAxisValue(int32_t axis, size_t pointerIndex, size_t historicalIndex) const; 475 476 inline float getHistoricalX(size_t pointerIndex, size_t historicalIndex) const { 477 return getHistoricalAxisValue( 478 AMOTION_EVENT_AXIS_X, pointerIndex, historicalIndex); 479 } 480 481 inline float getHistoricalY(size_t pointerIndex, size_t historicalIndex) const { 482 return getHistoricalAxisValue( 483 AMOTION_EVENT_AXIS_Y, pointerIndex, historicalIndex); 484 } 485 486 inline float getHistoricalPressure(size_t pointerIndex, size_t historicalIndex) const { 487 return getHistoricalAxisValue( 488 AMOTION_EVENT_AXIS_PRESSURE, pointerIndex, historicalIndex); 489 } 490 491 inline float getHistoricalSize(size_t pointerIndex, size_t historicalIndex) const { 492 return getHistoricalAxisValue( 493 AMOTION_EVENT_AXIS_SIZE, pointerIndex, historicalIndex); 494 } 495 496 inline float getHistoricalTouchMajor(size_t pointerIndex, size_t historicalIndex) const { 497 return getHistoricalAxisValue( 498 AMOTION_EVENT_AXIS_TOUCH_MAJOR, pointerIndex, historicalIndex); 499 } 500 501 inline float getHistoricalTouchMinor(size_t pointerIndex, size_t historicalIndex) const { 502 return getHistoricalAxisValue( 503 AMOTION_EVENT_AXIS_TOUCH_MINOR, pointerIndex, historicalIndex); 504 } 505 506 inline float getHistoricalToolMajor(size_t pointerIndex, size_t historicalIndex) const { 507 return getHistoricalAxisValue( 508 AMOTION_EVENT_AXIS_TOOL_MAJOR, pointerIndex, historicalIndex); 509 } 510 511 inline float getHistoricalToolMinor(size_t pointerIndex, size_t historicalIndex) const { 512 return getHistoricalAxisValue( 513 AMOTION_EVENT_AXIS_TOOL_MINOR, pointerIndex, historicalIndex); 514 } 515 516 inline float getHistoricalOrientation(size_t pointerIndex, size_t historicalIndex) const { 517 return getHistoricalAxisValue( 518 AMOTION_EVENT_AXIS_ORIENTATION, pointerIndex, historicalIndex); 519 } 520 521 ssize_t findPointerIndex(int32_t pointerId) const; 522 523 void initialize( 524 int32_t deviceId, 525 int32_t source, 526 int32_t action, 527 int32_t flags, 528 int32_t edgeFlags, 529 int32_t metaState, 530 int32_t buttonState, 531 float xOffset, 532 float yOffset, 533 float xPrecision, 534 float yPrecision, 535 nsecs_t downTime, 536 nsecs_t eventTime, 537 size_t pointerCount, 538 const PointerProperties* pointerProperties, 539 const PointerCoords* pointerCoords); 540 541 void copyFrom(const MotionEvent* other, bool keepHistory); 542 543 void addSample( 544 nsecs_t eventTime, 545 const PointerCoords* pointerCoords); 546 547 void offsetLocation(float xOffset, float yOffset); 548 549 void scale(float scaleFactor); 550 551#ifdef HAVE_ANDROID_OS 552 void transform(const SkMatrix* matrix); 553 554 status_t readFromParcel(Parcel* parcel); 555 status_t writeToParcel(Parcel* parcel) const; 556#endif 557 558 static bool isTouchEvent(int32_t source, int32_t action); 559 inline bool isTouchEvent() const { 560 return isTouchEvent(mSource, mAction); 561 } 562 563 // Low-level accessors. 564 inline const PointerProperties* getPointerProperties() const { 565 return mPointerProperties.array(); 566 } 567 inline const nsecs_t* getSampleEventTimes() const { return mSampleEventTimes.array(); } 568 inline const PointerCoords* getSamplePointerCoords() const { 569 return mSamplePointerCoords.array(); 570 } 571 572protected: 573 int32_t mAction; 574 int32_t mFlags; 575 int32_t mEdgeFlags; 576 int32_t mMetaState; 577 int32_t mButtonState; 578 float mXOffset; 579 float mYOffset; 580 float mXPrecision; 581 float mYPrecision; 582 nsecs_t mDownTime; 583 Vector<PointerProperties> mPointerProperties; 584 Vector<nsecs_t> mSampleEventTimes; 585 Vector<PointerCoords> mSamplePointerCoords; 586}; 587 588/* 589 * Input event factory. 590 */ 591class InputEventFactoryInterface { 592protected: 593 virtual ~InputEventFactoryInterface() { } 594 595public: 596 InputEventFactoryInterface() { } 597 598 virtual KeyEvent* createKeyEvent() = 0; 599 virtual MotionEvent* createMotionEvent() = 0; 600}; 601 602/* 603 * A simple input event factory implementation that uses a single preallocated instance 604 * of each type of input event that are reused for each request. 605 */ 606class PreallocatedInputEventFactory : public InputEventFactoryInterface { 607public: 608 PreallocatedInputEventFactory() { } 609 virtual ~PreallocatedInputEventFactory() { } 610 611 virtual KeyEvent* createKeyEvent() { return & mKeyEvent; } 612 virtual MotionEvent* createMotionEvent() { return & mMotionEvent; } 613 614private: 615 KeyEvent mKeyEvent; 616 MotionEvent mMotionEvent; 617}; 618 619/* 620 * An input event factory implementation that maintains a pool of input events. 621 */ 622class PooledInputEventFactory : public InputEventFactoryInterface { 623public: 624 PooledInputEventFactory(size_t maxPoolSize = 20); 625 virtual ~PooledInputEventFactory(); 626 627 virtual KeyEvent* createKeyEvent(); 628 virtual MotionEvent* createMotionEvent(); 629 630 void recycle(InputEvent* event); 631 632private: 633 const size_t mMaxPoolSize; 634 635 Vector<KeyEvent*> mKeyEventPool; 636 Vector<MotionEvent*> mMotionEventPool; 637}; 638 639/* 640 * Calculates the velocity of pointer movements over time. 641 */ 642class VelocityTracker { 643public: 644 // Default polynomial degree. (used by getVelocity) 645 static const uint32_t DEFAULT_DEGREE = 2; 646 647 // Default sample horizon. (used by getVelocity) 648 // We don't use too much history by default since we want to react to quick 649 // changes in direction. 650 static const nsecs_t DEFAULT_HORIZON = 100 * 1000000; // 100 ms 651 652 struct Position { 653 float x, y; 654 }; 655 656 struct Estimator { 657 static const size_t MAX_DEGREE = 2; 658 659 // Polynomial coefficients describing motion in X and Y. 660 float xCoeff[MAX_DEGREE + 1], yCoeff[MAX_DEGREE + 1]; 661 662 // Polynomial degree (number of coefficients), or zero if no information is 663 // available. 664 uint32_t degree; 665 666 // Confidence (coefficient of determination), between 0 (no fit) and 1 (perfect fit). 667 float confidence; 668 669 inline void clear() { 670 degree = 0; 671 confidence = 0; 672 for (size_t i = 0; i <= MAX_DEGREE; i++) { 673 xCoeff[i] = 0; 674 yCoeff[i] = 0; 675 } 676 } 677 }; 678 679 VelocityTracker(); 680 681 // Resets the velocity tracker state. 682 void clear(); 683 684 // Resets the velocity tracker state for specific pointers. 685 // Call this method when some pointers have changed and may be reusing 686 // an id that was assigned to a different pointer earlier. 687 void clearPointers(BitSet32 idBits); 688 689 // Adds movement information for a set of pointers. 690 // The idBits bitfield specifies the pointer ids of the pointers whose positions 691 // are included in the movement. 692 // The positions array contains position information for each pointer in order by 693 // increasing id. Its size should be equal to the number of one bits in idBits. 694 void addMovement(nsecs_t eventTime, BitSet32 idBits, const Position* positions); 695 696 // Adds movement information for all pointers in a MotionEvent, including historical samples. 697 void addMovement(const MotionEvent* event); 698 699 // Gets the velocity of the specified pointer id in position units per second. 700 // Returns false and sets the velocity components to zero if there is 701 // insufficient movement information for the pointer. 702 bool getVelocity(uint32_t id, float* outVx, float* outVy) const; 703 704 // Gets a quadratic estimator for the movements of the specified pointer id. 705 // Returns false and clears the estimator if there is no information available 706 // about the pointer. 707 bool getEstimator(uint32_t id, uint32_t degree, nsecs_t horizon, 708 Estimator* outEstimator) const; 709 710 // Gets the active pointer id, or -1 if none. 711 inline int32_t getActivePointerId() const { return mActivePointerId; } 712 713 // Gets a bitset containing all pointer ids from the most recent movement. 714 inline BitSet32 getCurrentPointerIdBits() const { return mMovements[mIndex].idBits; } 715 716private: 717 // Number of samples to keep. 718 static const uint32_t HISTORY_SIZE = 20; 719 720 struct Movement { 721 nsecs_t eventTime; 722 BitSet32 idBits; 723 Position positions[MAX_POINTERS]; 724 725 inline const Position& getPosition(uint32_t id) const { 726 return positions[idBits.getIndexOfBit(id)]; 727 } 728 }; 729 730 uint32_t mIndex; 731 Movement mMovements[HISTORY_SIZE]; 732 int32_t mActivePointerId; 733}; 734 735 736/* 737 * Specifies parameters that govern pointer or wheel acceleration. 738 */ 739struct VelocityControlParameters { 740 // A scale factor that is multiplied with the raw velocity deltas 741 // prior to applying any other velocity control factors. The scale 742 // factor should be used to adapt the input device resolution 743 // (eg. counts per inch) to the output device resolution (eg. pixels per inch). 744 // 745 // Must be a positive value. 746 // Default is 1.0 (no scaling). 747 float scale; 748 749 // The scaled speed at which acceleration begins to be applied. 750 // This value establishes the upper bound of a low speed regime for 751 // small precise motions that are performed without any acceleration. 752 // 753 // Must be a non-negative value. 754 // Default is 0.0 (no low threshold). 755 float lowThreshold; 756 757 // The scaled speed at which maximum acceleration is applied. 758 // The difference between highThreshold and lowThreshold controls 759 // the range of speeds over which the acceleration factor is interpolated. 760 // The wider the range, the smoother the acceleration. 761 // 762 // Must be a non-negative value greater than or equal to lowThreshold. 763 // Default is 0.0 (no high threshold). 764 float highThreshold; 765 766 // The acceleration factor. 767 // When the speed is above the low speed threshold, the velocity will scaled 768 // by an interpolated value between 1.0 and this amount. 769 // 770 // Must be a positive greater than or equal to 1.0. 771 // Default is 1.0 (no acceleration). 772 float acceleration; 773 774 VelocityControlParameters() : 775 scale(1.0f), lowThreshold(0.0f), highThreshold(0.0f), acceleration(1.0f) { 776 } 777 778 VelocityControlParameters(float scale, float lowThreshold, 779 float highThreshold, float acceleration) : 780 scale(scale), lowThreshold(lowThreshold), 781 highThreshold(highThreshold), acceleration(acceleration) { 782 } 783}; 784 785/* 786 * Implements mouse pointer and wheel speed control and acceleration. 787 */ 788class VelocityControl { 789public: 790 VelocityControl(); 791 792 /* Sets the various parameters. */ 793 void setParameters(const VelocityControlParameters& parameters); 794 795 /* Resets the current movement counters to zero. 796 * This has the effect of nullifying any acceleration. */ 797 void reset(); 798 799 /* Translates a raw movement delta into an appropriately 800 * scaled / accelerated delta based on the current velocity. */ 801 void move(nsecs_t eventTime, float* deltaX, float* deltaY); 802 803private: 804 // If no movements are received within this amount of time, 805 // we assume the movement has stopped and reset the movement counters. 806 static const nsecs_t STOP_TIME = 500 * 1000000; // 500 ms 807 808 VelocityControlParameters mParameters; 809 810 nsecs_t mLastMovementTime; 811 VelocityTracker::Position mRawPosition; 812 VelocityTracker mVelocityTracker; 813}; 814 815} // namespace android 816 817#endif // _ANDROIDFW_INPUT_H 818