/// <summary>
        /// StylusPointCollection
        /// </summary>
        /// <param name="stylusPoints">stylusPoints</param>
        public StylusPointCollection(IEnumerable <StylusPoint> stylusPoints)
        //: this() //don't call the base ctor, we want to use the first sp
        {
            if (stylusPoints == null)
            {
                throw new ArgumentNullException("stylusPoints");
            }

            List <StylusPoint> points = new List <StylusPoint>(stylusPoints);

            if (points.Count == 0)
            {
                throw new ArgumentException(SR.Get(SRID.InvalidStylusPointConstructionZeroLengthCollection), "stylusPoints");
            }

            //
            // set our packet description to the first in the array
            //
            _stylusPointDescription = points[0].Description;

            ((List <StylusPoint>) this.Items).Capacity = points.Count;
            for (int x = 0; x < points.Count; x++)
            {
                this.Add(points[x]);
            }
        }
        /// <summary>
        /// Adds the StylusPoints in the StylusPointCollection to this StylusPointCollection
        /// </summary>
        /// <param name="stylusPoints">stylusPoints</param>
        public void Add(StylusPointCollection stylusPoints)
        {
            //note that we don't raise an exception if stylusPoints.Count == 0
            if (null == stylusPoints)
            {
                throw new ArgumentNullException("stylusPoints");
            }
            if (!StylusPointDescription.AreCompatible(stylusPoints.Description,
                                                      _stylusPointDescription))
            {
                throw new ArgumentException(SR.Get(SRID.IncompatibleStylusPointDescriptions), "stylusPoints");
            }

            // cache count outside of the loop, so if this SPC is ever passed
            // we don't loop forever
            int count = stylusPoints.Count;

            for (int x = 0; x < count; x++)
            {
                StylusPoint stylusPoint = stylusPoints[x];
                stylusPoint.Description = _stylusPointDescription;
                //this does not go through our protected virtuals
                ((List <StylusPoint>) this.Items).Add(stylusPoint);
            }

            if (stylusPoints.Count > 0)
            {
                OnChanged(EventArgs.Empty);
            }
        }
        internal Point GetLastTabletPoint()
        {
            int packetLength = StylusPointDescription.GetInputArrayLengthPerPoint();
            int lastXIndex   = _data.Length - packetLength;

            return(new Point(_data[lastXIndex], _data[lastXIndex + 1]));
        }
        /// <summary>
        /// Private clone implementation
        /// </summary>
        private StylusPointCollection Clone(GeneralTransform transform, StylusPointDescription descriptionToUse, int count)
        {
            Debug.Assert(count <= this.Count);
            //
            // We don't need to copy our _stylusPointDescription because it is immutable
            // and we don't need to copy our StylusPoints, because they are structs.
            //
            StylusPointCollection newCollection =
                new StylusPointCollection(descriptionToUse, count);

            bool isIdentity = (transform is Transform) ? ((Transform)transform).IsIdentity : false;

            for (int x = 0; x < count; x++)
            {
                if (isIdentity)
                {
                    ((List <StylusPoint>)newCollection.Items).Add(this[x]);
                }
                else
                {
                    Point       point       = new Point();
                    StylusPoint stylusPoint = this[x];
                    point.X = stylusPoint.X;
                    point.Y = stylusPoint.Y;
                    transform.TryTransform(point, out point);
                    stylusPoint.X = point.X;
                    stylusPoint.Y = point.Y;
                    ((List <StylusPoint>)newCollection.Items).Add(stylusPoint);
                }
            }
            return(newCollection);
        }
Exemple #5
0
        internal RawStylusInputReport(
            InputMode mode,
            int timestamp,
            PresentationSource inputSource,
            RawStylusActions actions,
            StylusPointDescription mousePointDescription,
            int[] mouseData)
            : base(inputSource, InputType.Stylus, mode, timestamp)
        {
            // Validate parameters
            if (!RawStylusActionsHelper.IsValid(actions))
            {
                throw new InvalidEnumArgumentException(SR.Get(SRID.Enum_Invalid, "actions"));
            }
            if (mouseData == null)
            {
                throw new ArgumentNullException("mouseData");
            }

            _penContext            = new SecurityCriticalDataClass <PenContext>(null);
            _actions               = actions;
            _tabletDeviceId        = 0;
            _stylusDeviceId        = 0;
            _data                  = mouseData;
            _isSynchronize         = false;
            _mousePointDescription = mousePointDescription;
            _isMouseInput          = true;
        }
        /// <summary>
        /// Internal ctor called by input with a raw int[]
        /// </summary>
        /// <param name="stylusPointDescription">stylusPointDescription</param>
        /// <param name="rawPacketData">rawPacketData</param>
        /// <param name="tabletToView">tabletToView</param>
        /// <param name="tabletToViewMatrix">tabletToView</param>
        internal StylusPointCollection(StylusPointDescription stylusPointDescription, int[] rawPacketData, GeneralTransform tabletToView, Matrix tabletToViewMatrix)
        {
            if (null == stylusPointDescription)
            {
                throw new ArgumentNullException("stylusPointDescription");
            }
            _stylusPointDescription = stylusPointDescription;

            int lengthPerPoint    = stylusPointDescription.GetInputArrayLengthPerPoint();
            int logicalPointCount = rawPacketData.Length / lengthPerPoint;

            Debug.Assert(0 == rawPacketData.Length % lengthPerPoint, "Invalid assumption about packet length, there shouldn't be any remainder");

            //
            // set our capacity and validate
            //
            ((List <StylusPoint>) this.Items).Capacity = logicalPointCount;
            for (int count = 0, i = 0; count < logicalPointCount; count++, i += lengthPerPoint)
            {
                //first, determine the x, y values by xf-ing them
                Point p = new Point(rawPacketData[i], rawPacketData[i + 1]);
                if (tabletToView != null)
                {
                    tabletToView.TryTransform(p, out p);
                }
                else
                {
                    p = tabletToViewMatrix.Transform(p);
                }

                int  startIndex           = 2;
                bool containsTruePressure = stylusPointDescription.ContainsTruePressure;
                if (containsTruePressure)
                {
                    //don't copy pressure in the int[] for extra data
                    startIndex++;
                }

                int[] data       = null;
                int   dataLength = lengthPerPoint - startIndex;
                if (dataLength > 0)
                {
                    //copy the rest of the data
                    var rawArrayStartIndex = i + startIndex;
                    data = rawPacketData.AsSpan(rawArrayStartIndex, dataLength).ToArray();
                }

                StylusPoint newPoint = new StylusPoint(p.X, p.Y, StylusPoint.DefaultPressure, _stylusPointDescription, data, false, false);
                if (containsTruePressure)
                {
                    //use the algorithm to set pressure in StylusPoint
                    int pressure = rawPacketData[i + 2];
                    newPoint.SetPropertyValue(StylusPointProperties.NormalPressure, pressure);
                }

                //this does not go through our protected virtuals
                ((List <StylusPoint>) this.Items).Add(newPoint);
            }
        }
 /// <summary>
 /// StylusPointCollection
 /// </summary>
 /// <param name="stylusPointDescription">stylusPointDescription</param>
 public StylusPointCollection(StylusPointDescription stylusPointDescription)
 {
     if (null == stylusPointDescription)
     {
         throw new ArgumentNullException();
     }
     _stylusPointDescription = stylusPointDescription;
 }
 /// <summary>
 /// StylusPointCollection
 /// </summary>
 /// <param name="stylusPointDescription">stylusPointDescription</param>
 /// <param name="initialCapacity">initialCapacity</param>
 public StylusPointCollection(StylusPointDescription stylusPointDescription, int initialCapacity)
     : this(stylusPointDescription)
 {
     if (initialCapacity < 0)
     {
         throw new ArgumentException(SR.Get(SRID.InvalidStylusPointConstructionZeroLengthCollection), "initialCapacity");
     }
     ((List <StylusPoint>) this.Items).Capacity = initialCapacity;
 }
Exemple #9
0
        /// <summary>
        /// Compares two StylusPoint instances for exact equality.
        /// Note that double values can acquire error when operated upon, such that
        /// an exact comparison between two values which are logically equal may fail.
        /// Furthermore, using this equality operator, Double.NaN is not equal to itself.
        /// Descriptions must match for equality to succeed and additional values must match
        /// </summary>
        /// <returns>
        /// bool - true if the two Stylus instances are exactly equal, false otherwise
        /// </returns>
        /// <param name='stylusPoint1'>The first StylusPoint to compare</param>
        /// <param name='stylusPoint2'>The second StylusPoint to compare</param>
        public static bool Equals(StylusPoint stylusPoint1, StylusPoint stylusPoint2)
        {
            //
            // do the cheap comparison first
            //
            bool membersEqual =
                stylusPoint1._x == stylusPoint2._x &&
                stylusPoint1._y == stylusPoint2._y &&
                stylusPoint1._pressureFactor == stylusPoint2._pressureFactor;

            if (!membersEqual)
            {
                return(false);
            }

            //
            // before we go checking the descriptions... check to see if both additionalData's are null
            // we can infer that the SPD's are just X,Y,P and that they are compatible.
            //
            if (stylusPoint1._additionalValues == null &&
                stylusPoint2._additionalValues == null)
            {
                Debug.Assert(StylusPointDescription.AreCompatible(stylusPoint1.Description, stylusPoint2.Description));
                return(true);
            }

            //
            // ok, the members are equal.  compare the description and then additional data
            //
            if (object.ReferenceEquals(stylusPoint1.Description, stylusPoint2.Description) ||
                StylusPointDescription.AreCompatible(stylusPoint1.Description, stylusPoint2.Description))
            {
                //
                // descriptions match and there are equal numbers of additional values
                // let's check the values
                //
                for (int x = 0; x < stylusPoint1._additionalValues.Length; x++)
                {
                    if (stylusPoint1._additionalValues[x] != stylusPoint2._additionalValues[x])
                    {
                        return(false);
                    }
                }

                //
                // Ok, ok already, we're equal
                //
                return(true);
            }

            return(false);
        }
        /// <summary>
        /// called by base class Collection&lt;T&gt; when an item is set in list;
        /// raises a CollectionChanged event to any listeners
        /// </summary>
        protected override sealed void SetItem(int index, StylusPoint stylusPoint)
        {
            if (!StylusPointDescription.AreCompatible(stylusPoint.Description,
                                                      _stylusPointDescription))
            {
                throw new ArgumentException(SR.Get(SRID.IncompatibleStylusPointDescriptions), "stylusPoint");
            }

            stylusPoint.Description = _stylusPointDescription;
            base.SetItem(index, stylusPoint);

            OnChanged(EventArgs.Empty);
        }
        /// <summary>
        /// Returns a new StylusPointDescription with the common StylusPointProperties from both
        /// </summary>
        /// <param name="stylusPointDescription">stylusPointDescription</param>
        /// <param name="stylusPointDescriptionPreserveInfo">stylusPointDescriptionPreserveInfo</param>
        /// <remarks>The StylusPointProperties from stylusPointDescriptionPreserveInfo will be returned in the new StylusPointDescription</remarks>
        public static StylusPointDescription GetCommonDescription(StylusPointDescription stylusPointDescription, StylusPointDescription stylusPointDescriptionPreserveInfo)
        {
            if (stylusPointDescription == null)
            {
                throw new ArgumentNullException("stylusPointDescription");
            }
            if (stylusPointDescriptionPreserveInfo == null)
            {
                throw new ArgumentNullException("stylusPointDescriptionPreserveInfo");
            }


            #pragma warning disable 6506 // if a StylusPointDescription is not null, then _stylusPointPropertyInfos is not null.
            //
            // ignore X, Y, Pressure - they are guaranteed to be the first3 members
            //
            Debug.Assert(stylusPointDescription._stylusPointPropertyInfos.Length >= 3 &&
                         stylusPointDescription._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                         stylusPointDescription._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                         stylusPointDescription._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);

            Debug.Assert(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos.Length >= 3 &&
                         stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                         stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                         stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);


            //add x, y, p
            List <StylusPointPropertyInfo> commonProperties = new List <StylusPointPropertyInfo>();
            commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[0]);
            commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[1]);
            commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[2]);

            //add common properties
            for (int x = RequiredCountOfProperties; x < stylusPointDescription._stylusPointPropertyInfos.Length; x++)
            {
                for (int y = RequiredCountOfProperties; y < stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos.Length; y++)
                {
                    if (StylusPointPropertyInfo.AreCompatible(stylusPointDescription._stylusPointPropertyInfos[x],
                                                              stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[y]))
                    {
                        commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[y]);
                    }
                }
            }
            #pragma warning restore 6506

            return(new StylusPointDescription(commonProperties));
        }
Exemple #12
0
        internal void UpdateSizeDeltas(StylusPointDescription description, StylusLogic stylusLogic)
        {
            if (_doubleTapSize.IsEmpty || _cancelSize.IsEmpty || _forceUpdateSizeDeltas)
            {
                // Query default settings for mouse drag and double tap (with minimum of 1x1 size).
                Size mouseDragDefault = new Size(Math.Max(1, SafeSystemMetrics.DragDeltaX / 2),
                                                 Math.Max(1, SafeSystemMetrics.DragDeltaY / 2));
                Size mouseDoubleTapDefault = new Size(Math.Max(1, SafeSystemMetrics.DoubleClickDeltaX / 2),
                                                      Math.Max(1, SafeSystemMetrics.DoubleClickDeltaY / 2));

                StylusPointPropertyInfo xProperty = description.GetPropertyInfo(StylusPointProperties.X);
                StylusPointPropertyInfo yProperty = description.GetPropertyInfo(StylusPointProperties.Y);

                uint dwXValue = GetPropertyValue(xProperty);
                uint dwYValue = GetPropertyValue(yProperty);

                if (dwXValue != 0 && dwYValue != 0)
                {
                    _cancelSize = new Size((int)Math.Round((ScreenSize.Width * stylusLogic.CancelDelta) / dwXValue),
                                           (int)Math.Round((ScreenSize.Height * stylusLogic.CancelDelta) / dwYValue));

                    // Make sure we return whole numbers (pixels are whole numbers) and take the maximum
                    // value between mouse and stylus settings to be safe.
                    _cancelSize.Width  = Math.Max(mouseDragDefault.Width, _cancelSize.Width);
                    _cancelSize.Height = Math.Max(mouseDragDefault.Height, _cancelSize.Height);

                    _doubleTapSize = new Size((int)Math.Round((ScreenSize.Width * stylusLogic.DoubleTapDelta) / dwXValue),
                                              (int)Math.Round((ScreenSize.Height * stylusLogic.DoubleTapDelta) / dwYValue));

                    // Make sure we return whole numbers (pixels are whole numbers) and take the maximum
                    // value between mouse and stylus settings to be safe.
                    _doubleTapSize.Width  = Math.Max(mouseDoubleTapDefault.Width, _doubleTapSize.Width);
                    _doubleTapSize.Height = Math.Max(mouseDoubleTapDefault.Height, _doubleTapSize.Height);
                }
                else
                {
                    // If no info to do the calculation then use the mouse settings for the default.
                    _doubleTapSize = mouseDoubleTapDefault;
                    _cancelSize    = mouseDragDefault;
                }

                _forceUpdateSizeDeltas = false;
            }
        }
Exemple #13
0
        /// <summary>
        /// Loads a stroke from the stream based on Stroke Descriptor, StylusPointDescription, Drawing Attributes, Stroke IDs, transform and GuidList
        /// </summary>
        /// <param name="stream"></param>
        /// <param name="size"></param>
        /// <param name="guidList"></param>
        /// <param name="strokeDescriptor"></param>
        /// <param name="stylusPointDescription"></param>
        /// <param name="drawingAttributes"></param>
        /// <param name="transform"></param>
        /// <param name="stroke">Newly decoded stroke</param>
#endif
        internal static uint DecodeStroke(Stream stream,
                                 uint size,
                                 GuidList guidList,
                                 StrokeDescriptor strokeDescriptor,
                                 StylusPointDescription stylusPointDescription,
                                 DrawingAttributes drawingAttributes,
                                 Matrix transform,
#if OLD_ISF
                                 Compressor compressor,
#endif
                                 out Stroke stroke)
        {
            ExtendedPropertyCollection extendedProperties;
            StylusPointCollection stylusPoints;

            uint cb = DecodeISFIntoStroke(
#if OLD_ISF
                compressor, 
#endif 
                stream, 
                size, 
                guidList, 
                strokeDescriptor, 
                stylusPointDescription, 
                transform, 
                out stylusPoints, 
                out extendedProperties);

            if (cb != size)
            {
                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Stroke size (" +
                    cb.ToString(System.Globalization.CultureInfo.InvariantCulture) + ") != expected (" + 
                    size.ToString(System.Globalization.CultureInfo.InvariantCulture) + ")"));
            }

            stroke = new Stroke(stylusPoints, drawingAttributes, extendedProperties);

            return cb;
        }
 /// <summary>
 /// Returns true if this StylusPointDescription is a subset
 /// of the StylusPointDescription passed in
 /// </summary>
 /// <param name="stylusPointDescriptionSuperset">stylusPointDescriptionSuperset</param>
 /// <returns></returns>
 public bool IsSubsetOf(StylusPointDescription stylusPointDescriptionSuperset)
 {
     if (null == stylusPointDescriptionSuperset)
     {
         throw new ArgumentNullException("stylusPointDescriptionSuperset");
     }
     if (stylusPointDescriptionSuperset._stylusPointPropertyInfos.Length < _stylusPointPropertyInfos.Length)
     {
         return(false);
     }
     //
     // iterate through our local properties and make sure that the
     // superset contains them
     //
     for (int x = 0; x < _stylusPointPropertyInfos.Length; x++)
     {
         Guid id = _stylusPointPropertyInfos[x].Id;
         if (-1 == stylusPointDescriptionSuperset.IndexOf(id))
         {
             return(false);
         }
     }
     return(true);
 }
        /// <summary>
        /// Returns true if the two StylusPointDescriptions have the same StylusPointProperties.  Metrics are ignored.
        /// </summary>
        /// <param name="stylusPointDescription1">stylusPointDescription1</param>
        /// <param name="stylusPointDescription2">stylusPointDescription2</param>
        public static bool AreCompatible(StylusPointDescription stylusPointDescription1, StylusPointDescription stylusPointDescription2)
        {
            if (stylusPointDescription1 == null || stylusPointDescription2 == null)
            {
                throw new ArgumentNullException("stylusPointDescription");
            }

            #pragma warning disable 6506 // if a StylusPointDescription is not null, then _stylusPointPropertyInfos is not null.
            //
            // ignore X, Y, Pressure - they are guaranteed to be the first3 members
            //
            Debug.Assert(stylusPointDescription1._stylusPointPropertyInfos.Length >= RequiredCountOfProperties &&
                         stylusPointDescription1._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                         stylusPointDescription1._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                         stylusPointDescription1._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);

            Debug.Assert(stylusPointDescription2._stylusPointPropertyInfos.Length >= RequiredCountOfProperties &&
                         stylusPointDescription2._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                         stylusPointDescription2._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                         stylusPointDescription2._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);

            if (stylusPointDescription1._stylusPointPropertyInfos.Length != stylusPointDescription2._stylusPointPropertyInfos.Length)
            {
                return(false);
            }
            for (int x = RequiredCountOfProperties; x < stylusPointDescription1._stylusPointPropertyInfos.Length; x++)
            {
                if (!StylusPointPropertyInfo.AreCompatible(stylusPointDescription1._stylusPointPropertyInfos[x], stylusPointDescription2._stylusPointPropertyInfos[x]))
                {
                    return(false);
                }
            }
            #pragma warning restore 6506

            return(true);
        }
 public StylusPoint(double x, double y, float pressureFactor, StylusPointDescription stylusPointDescription, int[] additionalValues)
 {
 }
Exemple #17
0
        internal RawStylusInputReport(
            InputMode mode,
            int timestamp,
            PresentationSource inputSource,
            RawStylusActions actions,
            StylusPointDescription mousePointDescription,
            int[] mouseData)
            : base(inputSource, InputType.Stylus, mode, timestamp)
        {
            // Validate parameters
            if (!RawStylusActionsHelper.IsValid(actions))
            {
                throw new InvalidEnumArgumentException(SR.Get(SRID.Enum_Invalid, "actions"));
            }
            if (mouseData == null)
            {
                throw new ArgumentNullException("mouseData");
            }

            _penContext     = new SecurityCriticalDataClass<PenContext>(null);
            _actions        = actions;
            _tabletDeviceId = 0;
            _stylusDeviceId = 0;
            _data           = mouseData;
            _isSynchronize  = false;
            _mousePointDescription = mousePointDescription;
            _isMouseInput = true;
        }
 public StylusPointCollection GetStylusPoints(System.Windows.IInputElement relativeTo, StylusPointDescription subsetToReformatTo)
 {
   return default(StylusPointCollection);
 }
 /// <summary>
 /// Returns true if this StylusPointDescription is a subset 
 /// of the StylusPointDescription passed in
 /// </summary>
 /// <param name="stylusPointDescriptionSuperset">stylusPointDescriptionSuperset</param>
 /// <returns></returns>
 public bool IsSubsetOf(StylusPointDescription stylusPointDescriptionSuperset)
 {
     if (null == stylusPointDescriptionSuperset)
     {
         throw new ArgumentNullException("stylusPointDescriptionSuperset");
     }
     if (stylusPointDescriptionSuperset._stylusPointPropertyInfos.Length < _stylusPointPropertyInfos.Length)
     {
         return false;
     }
     //
     // iterate through our local properties and make sure that the 
     // superset contains them
     //
     for (int x = 0; x < _stylusPointPropertyInfos.Length; x++)
     {
         Guid id = _stylusPointPropertyInfos[x].Id;
         if (-1 == stylusPointDescriptionSuperset.IndexOf(id))
         {
             return false;
         }
     }
     return true;
 }
 /// <summary>
 /// Reformat
 /// </summary>
 /// <param name="subsetToReformatTo">subsetToReformatTo</param>
 public StylusPointCollection Reformat(StylusPointDescription subsetToReformatTo)
 {
     return(Reformat(subsetToReformatTo, System.Windows.Media.Transform.Identity));
 }
Exemple #21
0
        /// <summary>
        /// This functions loads a stroke from a memory stream based on the descriptor and GuidList. It returns
        /// the no of bytes it has read from the stream to correctly load the stream, which should be same as
        /// the value of the size parameter. If they are unequal throws ArgumentException. Stroke descriptor is
        /// used to load the packetproperty as well as ExtendedPropertyCollection on this stroke. Compressor is used
        /// to decompress the data.
        /// </summary>
        /// <param name="stream"></param>
        /// <param name="totalBytesInStrokeBlockOfIsfStream"></param>
        /// <param name="guidList"></param>
        /// <param name="strokeDescriptor"></param>
        /// <param name="stylusPointDescription"></param>
        /// <param name="transform"></param>
        /// <param name="stylusPoints"></param>
        /// <param name="extendedProperties"></param>
#endif
        static uint DecodeISFIntoStroke(
#if OLD_ISF
            Compressor compressor, 
#endif
            Stream stream, 
            uint totalBytesInStrokeBlockOfIsfStream, 
            GuidList guidList, 
            StrokeDescriptor strokeDescriptor,
            StylusPointDescription stylusPointDescription,
            Matrix transform,
            out StylusPointCollection stylusPoints, 
            out ExtendedPropertyCollection extendedProperties)
        {
            stylusPoints = null;
            extendedProperties = null;

            // We do allow a stroke with no packet data
            if (0 == totalBytesInStrokeBlockOfIsfStream)
            {
                return 0;
            }
             
            uint locallyDecodedBytes;
            uint remainingBytesInStrokeBlock = totalBytesInStrokeBlockOfIsfStream;

            // First try to load any packet data
            locallyDecodedBytes = LoadPackets(  stream, 
                                                remainingBytesInStrokeBlock, 
#if OLD_ISF
                                                compressor, 
#endif
                                                stylusPointDescription, 
                                                transform, 
                                                out stylusPoints);

            if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Packet buffer overflowed the ISF stream"));

            remainingBytesInStrokeBlock -= locallyDecodedBytes;
            if (0 == remainingBytesInStrokeBlock)
            {
                return locallyDecodedBytes;
            }

            // Now read the extended propertes
            for (int iTag = 1; iTag < strokeDescriptor.Template.Count && remainingBytesInStrokeBlock > 0; iTag++)
            {
                KnownTagCache.KnownTagIndex tag = strokeDescriptor.Template[iTag - 1];

                switch (tag)
                {
                    case MS.Internal.Ink.InkSerializedFormat.KnownTagCache.KnownTagIndex.StrokePropertyList:
                        {
                            // we've found the stroke extended properties. Load them now.
                            while (iTag < strokeDescriptor.Template.Count && remainingBytesInStrokeBlock > 0)
                            {
                                tag = strokeDescriptor.Template[iTag];

                                object data;
                                Guid guid = guidList.FindGuid(tag);
                                if (guid == Guid.Empty)
                                {
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Stroke Custom Attribute tag embedded in ISF stream does not match guid table"));
                                }

                                // load the extended property data from the stream (and decode the type)
                                locallyDecodedBytes = ExtendedPropertySerializer.DecodeAsISF(stream, remainingBytesInStrokeBlock, guidList, tag, ref guid, out data);

                                // add the guid/data pair into the property collection (don't redecode the type)
                                if (extendedProperties == null)
                                {
                                    extendedProperties = new ExtendedPropertyCollection();
                                }
                                extendedProperties[guid] = data;
                                if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                                remainingBytesInStrokeBlock -= locallyDecodedBytes;
                                iTag++;
                            }
                        }
                        break;

                    case MS.Internal.Ink.InkSerializedFormat.KnownTagCache.KnownTagIndex.Buttons:
                        {
                            // Next tag is count of buttons and the tags for the button guids
                            iTag += (int)((uint)strokeDescriptor.Template[iTag]) + 1;
                        }
                        break;

                    // ignore any tags embedded in the Stroke block that this
                    //      version of the ISF decoder doesn't understand
                    default:
                        {
                            System.Diagnostics.Trace.WriteLine("Ignoring unhandled stroke tag in ISF stroke descriptor");
                        }
                        break;
                }
            }

            // Now try to load any tagged property data or point property data
            while (remainingBytesInStrokeBlock > 0)
            {
                // Read the tag first
                KnownTagCache.KnownTagIndex tag;
                uint uiTag;

                locallyDecodedBytes = SerializationHelper.Decode(stream, out uiTag);
                tag = (KnownTagCache.KnownTagIndex)uiTag;
                if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                remainingBytesInStrokeBlock -= locallyDecodedBytes;

                // if it is a point property block
                switch (tag)
                {
                    case MS.Internal.Ink.InkSerializedFormat.KnownTagCache.KnownTagIndex.PointProperty:
                        {
                            // First load the totalBytesInStrokeBlockOfIsfStream of the point property block
                            uint cbsize;

                            locallyDecodedBytes = SerializationHelper.Decode(stream, out cbsize);
                            if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                            remainingBytesInStrokeBlock -= locallyDecodedBytes;
                            while (remainingBytesInStrokeBlock > 0)
                            {
                                // First read the tag corresponding to the property
                                locallyDecodedBytes = SerializationHelper.Decode(stream, out uiTag);
                                tag = (KnownTagCache.KnownTagIndex)uiTag;
                                if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                                remainingBytesInStrokeBlock -= locallyDecodedBytes;

                                // Now read the packet index for which the property will apply
                                uint propindex;

                                locallyDecodedBytes = SerializationHelper.Decode(stream, out propindex);
                                if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                                remainingBytesInStrokeBlock -= locallyDecodedBytes;

                                uint propsize;

                                locallyDecodedBytes = SerializationHelper.Decode(stream, out propsize);
                                if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                                remainingBytesInStrokeBlock -= locallyDecodedBytes;

                                // Compressed data totalBytesInStrokeBlockOfIsfStream
                                propsize += 1;

                                // Make sure we have enough data to read
                                if (propsize > remainingBytesInStrokeBlock)
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                                byte[] in_buffer = new byte[propsize];

                                uint bytesRead = StrokeCollectionSerializer.ReliableRead(stream, in_buffer, propsize);
                                if (propsize != bytesRead)
                                {
                                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Read different size from stream then expected"));
                                }

                                byte[] out_buffer = Compressor.DecompressPropertyData(in_buffer);

                                System.Diagnostics.Debug.Assert(false, "ExtendedProperties for points are not supported");

                                // skip the bytes in both success & failure cases
                                // Note: Point ExtendedProperties are discarded
                                remainingBytesInStrokeBlock -= propsize;
                            }
                        }
                        break;

                    default:
                        {
                            object data;
                            Guid guid = guidList.FindGuid(tag);
                            if (guid == Guid.Empty)
                            {
                                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Stroke Custom Attribute tag embedded in ISF stream does not match guid table"));
                            }

                            // load the extended property data from the stream (and decode the type)
                            locallyDecodedBytes = ExtendedPropertySerializer.DecodeAsISF(stream, remainingBytesInStrokeBlock, guidList, tag, ref guid, out data);

                            // add the guid/data pair into the property collection (don't redecode the type)
                            if (extendedProperties == null)
                            {
                                extendedProperties = new ExtendedPropertyCollection();
                            }
                            extendedProperties[guid] = data;
                            if (locallyDecodedBytes > remainingBytesInStrokeBlock)
                            {
                                throw new InvalidOperationException(StrokeCollectionSerializer.ISFDebugMessage("ExtendedProperty decoded totalBytesInStrokeBlockOfIsfStream exceeded ISF stream totalBytesInStrokeBlockOfIsfStream"));
                            }

                            remainingBytesInStrokeBlock -= locallyDecodedBytes;
                        }
                        break;
                }
            }

            if (0 != remainingBytesInStrokeBlock)
                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

            return totalBytesInStrokeBlockOfIsfStream;
        }
Exemple #22
0
 public StylusPointCollection(StylusPointDescription stylusPointDescription, int initialCapacity)
 {
 }
Exemple #23
0
 public StylusPointCollection(StylusPointDescription stylusPointDescription)
 {
 }
Exemple #24
0
 public System.Windows.Input.StylusPointCollection Reformat(StylusPointDescription subsetToReformatTo)
 {
     return(default(System.Windows.Input.StylusPointCollection));
 }
        internal void UpdateSizeDeltas(StylusPointDescription description, StylusLogic stylusLogic)
        {
            if (_doubleTapSize.IsEmpty || _cancelSize.IsEmpty || _forceUpdateSizeDeltas)
            {
                // Query default settings for mouse drag and double tap (with minimum of 1x1 size).
                Size mouseDragDefault = new Size(Math.Max(1, SafeSystemMetrics.DragDeltaX / 2),
                                               Math.Max(1, SafeSystemMetrics.DragDeltaY / 2));
                Size mouseDoubleTapDefault = new Size(Math.Max(1, SafeSystemMetrics.DoubleClickDeltaX / 2),
                                               Math.Max(1, SafeSystemMetrics.DoubleClickDeltaY / 2));
               
                StylusPointPropertyInfo xProperty = description.GetPropertyInfo(StylusPointProperties.X);
                StylusPointPropertyInfo yProperty = description.GetPropertyInfo(StylusPointProperties.Y);

                uint dwXValue = GetPropertyValue(xProperty);
                uint dwYValue = GetPropertyValue(yProperty);

                if (dwXValue != 0 && dwYValue != 0)
                {
                    _cancelSize = new Size((int)Math.Round((ScreenSize.Width * stylusLogic.CancelDelta) / dwXValue),
                                           (int)Math.Round((ScreenSize.Height * stylusLogic.CancelDelta) / dwYValue));
                    
                    // Make sure we return whole numbers (pixels are whole numbers) and take the maximum
                    // value between mouse and stylus settings to be safe.
                    _cancelSize.Width = Math.Max(mouseDragDefault.Width, _cancelSize.Width);
                    _cancelSize.Height = Math.Max(mouseDragDefault.Height, _cancelSize.Height);

                    _doubleTapSize = new Size((int)Math.Round((ScreenSize.Width * stylusLogic.DoubleTapDelta) / dwXValue),
                                              (int)Math.Round((ScreenSize.Height * stylusLogic.DoubleTapDelta) / dwYValue));
                    
                    // Make sure we return whole numbers (pixels are whole numbers) and take the maximum
                    // value between mouse and stylus settings to be safe.
                    _doubleTapSize.Width = Math.Max(mouseDoubleTapDefault.Width, _doubleTapSize.Width);
                    _doubleTapSize.Height = Math.Max(mouseDoubleTapDefault.Height, _doubleTapSize.Height);
                }
                else
                {
                    // If no info to do the calculation then use the mouse settings for the default.
                    _doubleTapSize = mouseDoubleTapDefault;
                    _cancelSize = mouseDragDefault;
                }
                
                _forceUpdateSizeDeltas = false;
            }
        }
        private void InitStylusPointDescription()
        {
            int cProps;
            int cButtons;
            int pressureIndex = -1;

            // Make sure we are never called on the application thread when we need to talk
            // to penimc or else we can cause reentrancy!
            Debug.Assert(!_contexts._inputSource.Value.CheckAccess());

            // We should always have a valid IPimcContext interface pointer.
            Debug.Assert(_pimcContext != null && _pimcContext.Value != null);
            
            _pimcContext.Value.GetPacketDescriptionInfo(out cProps, out cButtons); // Calls Unmanaged code - SecurityCritical with SUC.

            List<StylusPointPropertyInfo> propertyInfos = new List<StylusPointPropertyInfo>(cProps + cButtons + 3);
            for (int i = 0; i < cProps; i++)
            {
                Guid guid;
                int min, max;
                int units;
                float res;
                _pimcContext.Value.GetPacketPropertyInfo(i, out guid, out min, out max, out units, out res); // Calls Unmanaged code - SecurityCritical with SUC.

                if (pressureIndex == -1 && guid == StylusPointPropertyIds.NormalPressure)
                {
                    pressureIndex = i;
                }
                
                if (_statusPropertyIndex == -1 && guid == StylusPointPropertyIds.PacketStatus)
                {
                    _statusPropertyIndex = i;
                }

                StylusPointPropertyInfo propertyInfo = new StylusPointPropertyInfo(new StylusPointProperty(guid, false), min, max, (StylusPointPropertyUnit)units, res);
                
                propertyInfos.Add(propertyInfo);
            }

            Debug.Assert(_statusPropertyIndex != -1);  // We should always see this.
            
            // Make sure we actually created propertyInfos OK
            if (propertyInfos != null)
            {
                for (int i = 0; i < cButtons; i++)
                {
                    Guid buttonGuid;
                    _pimcContext.Value.GetPacketButtonInfo(i, out buttonGuid); // Calls Unmanaged code - SecurityCritical with SUC.

                    StylusPointProperty buttonProperty = new StylusPointProperty(buttonGuid, true);
                    StylusPointPropertyInfo buttonInfo = new StylusPointPropertyInfo(buttonProperty);
                    propertyInfos.Add(buttonInfo);
                }

                //validate we can never get X, Y at index != 0, 1
                Debug.Assert(propertyInfos[StylusPointDescription.RequiredXIndex /*0*/].Id == StylusPointPropertyIds.X, "X isn't where we expect it! Fix PenImc to ask for X at index 0");
                Debug.Assert(propertyInfos[StylusPointDescription.RequiredYIndex /*0*/].Id == StylusPointPropertyIds.Y, "Y isn't where we expect it! Fix PenImc to ask for Y at index 1");
                Debug.Assert(pressureIndex == -1 || pressureIndex == StylusPointDescription.RequiredPressureIndex /*2*/, 
                    "Fix PenImc to ask for NormalPressure at index 2!");
                if (pressureIndex == -1)
                {
                    //pressure wasn't found.  Add it
                    propertyInfos.Insert(StylusPointDescription.RequiredPressureIndex /*2*/, StylusPointPropertyInfoDefaults.NormalPressure);
                }
                _infoX = propertyInfos[0];
                _infoY = propertyInfos[1];
                
                _stylusPointDescription = new StylusPointDescription(propertyInfos, pressureIndex);
            }

        }
 /// <summary>
 /// Clone with a transform, used by input
 /// </summary>
 internal StylusPointCollection Clone(GeneralTransform transform, StylusPointDescription descriptionToUse)
 {
     return(this.Clone(transform, descriptionToUse, this.Count));
 }
Exemple #28
0
 /// <summary>
 ///     Returns a StylusPointCollection object for processing the data in the packet.
 ///     This method creates a new StylusPointCollection and copies the data.
 /// </summary>
 public StylusPointCollection GetStylusPoints(IInputElement relativeTo, StylusPointDescription subsetToReformatTo)
 {
     return(StylusDeviceImpl.GetStylusPoints(relativeTo, subsetToReformatTo));
 }
 /// <summary>
 /// StylusPointCollection
 /// </summary>
 public StylusPointCollection()
 {
     _stylusPointDescription = new StylusPointDescription();
 }
 public StylusPointCollection GetStylusPoints(System.Windows.IInputElement relativeTo, StylusPointDescription subsetToReformatTo)
 {
     return(default(StylusPointCollection));
 }
        /// <summary>
        /// Helper that transforms and scales in one go
        /// </summary>
        internal StylusPointCollection Reformat(StylusPointDescription subsetToReformatTo, GeneralTransform transform)
        {
            if (!subsetToReformatTo.IsSubsetOf(this.Description))
            {
                throw new ArgumentException(SR.Get(SRID.InvalidStylusPointDescriptionSubset), "subsetToReformatTo");
            }

            StylusPointDescription subsetToReformatToWithCurrentMetrics =
                StylusPointDescription.GetCommonDescription(subsetToReformatTo,
                                                            this.Description); //preserve metrics from this spd

            if (StylusPointDescription.AreCompatible(this.Description, subsetToReformatToWithCurrentMetrics) &&
                (transform is Transform) && ((Transform)transform).IsIdentity)
            {
                //subsetToReformatTo might have different x, y, p metrics
                return(this.Clone(transform, subsetToReformatToWithCurrentMetrics));
            }

            //
            // we really need to reformat this...
            //
            StylusPointCollection newCollection = new StylusPointCollection(subsetToReformatToWithCurrentMetrics, this.Count);
            int additionalDataCount             = subsetToReformatToWithCurrentMetrics.GetExpectedAdditionalDataCount();

            ReadOnlyCollection <StylusPointPropertyInfo> properties
                = subsetToReformatToWithCurrentMetrics.GetStylusPointProperties();
            bool isIdentity = (transform is Transform) ? ((Transform)transform).IsIdentity : false;

            for (int i = 0; i < this.Count; i++)
            {
                StylusPoint stylusPoint = this[i];

                double xCoord   = stylusPoint.X;
                double yCoord   = stylusPoint.Y;
                float  pressure = stylusPoint.GetUntruncatedPressureFactor();

                if (!isIdentity)
                {
                    Point p = new Point(xCoord, yCoord);
                    transform.TryTransform(p, out p);
                    xCoord = p.X;
                    yCoord = p.Y;
                }

                int[] newData = null;
                if (additionalDataCount > 0)
                {
                    //don't init, we'll do that below
                    newData = new int[additionalDataCount];
                }

                StylusPoint newStylusPoint =
                    new StylusPoint(xCoord, yCoord, pressure, subsetToReformatToWithCurrentMetrics, newData, false, false);

                //start at 3, skipping x, y, pressure
                for (int x = StylusPointDescription.RequiredCountOfProperties /*3*/; x < properties.Count; x++)
                {
                    int value = stylusPoint.GetPropertyValue(properties[x]);
                    newStylusPoint.SetPropertyValue(properties[x], value, false /*copy on write*/);
                }
                //bypass validation
                ((List <StylusPoint>)newCollection.Items).Add(newStylusPoint);
            }
            return(newCollection);
        }
        /// <summary>
        /// Returns a new StylusPointDescription with the common StylusPointProperties from both
        /// </summary>
        /// <param name="stylusPointDescription">stylusPointDescription</param>
        /// <param name="stylusPointDescriptionPreserveInfo">stylusPointDescriptionPreserveInfo</param>
        /// <remarks>The StylusPointProperties from stylusPointDescriptionPreserveInfo will be returned in the new StylusPointDescription</remarks>
        public static StylusPointDescription GetCommonDescription(StylusPointDescription stylusPointDescription, StylusPointDescription stylusPointDescriptionPreserveInfo)
        {
            if (stylusPointDescription == null)
            {
                throw new ArgumentNullException("stylusPointDescription");
            }
            if (stylusPointDescriptionPreserveInfo == null)
            {
                throw new ArgumentNullException("stylusPointDescriptionPreserveInfo");
            }


            #pragma warning disable 6506 // if a StylusPointDescription is not null, then _stylusPointPropertyInfos is not null.
            //
            // ignore X, Y, Pressure - they are guaranteed to be the first3 members
            //
            Debug.Assert(stylusPointDescription._stylusPointPropertyInfos.Length >= 3 &&
                            stylusPointDescription._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                            stylusPointDescription._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                            stylusPointDescription._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);

            Debug.Assert(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos.Length >= 3 &&
                            stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                            stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                            stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);


            //add x, y, p
            List<StylusPointPropertyInfo> commonProperties = new List<StylusPointPropertyInfo>();
            commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[0]);
            commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[1]);
            commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[2]);

            //add common properties
            for (int x = RequiredCountOfProperties; x < stylusPointDescription._stylusPointPropertyInfos.Length; x++)
            {
                for (int y = RequiredCountOfProperties; y < stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos.Length; y++)
                {
                    if (StylusPointPropertyInfo.AreCompatible(  stylusPointDescription._stylusPointPropertyInfos[x], 
                                                            stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[y]))
                    {
                        commonProperties.Add(stylusPointDescriptionPreserveInfo._stylusPointPropertyInfos[y]);
                    }
                }
            }
            #pragma warning restore 6506
            
            return new StylusPointDescription(commonProperties);
        }
Exemple #33
0
 public StylusPointCollection GetStylusPoints(IInputElement relativeTo,
                                              StylusPointDescription subsetReformatTo)
 {
     throw new NotImplementedException();
 }
Exemple #34
0
        /// <summary>
        /// Loads packets from the input stream.  For example, packets are all of the x's in a stroke
        /// </summary>
#endif
        static uint LoadPackets(Stream inputStream, 
                                uint totalBytesInStrokeBlockOfIsfStream, 
#if OLD_ISF
                                Compressor compressor, 
#endif
                                StylusPointDescription stylusPointDescription, 
                                Matrix transform, 
                                out StylusPointCollection stylusPoints)
        {
            stylusPoints = null;

            if (0 == totalBytesInStrokeBlockOfIsfStream)
                return 0;

            uint locallyDecodedBytesRemaining = totalBytesInStrokeBlockOfIsfStream;
            uint localBytesRead;

            // First read the no of packets
            uint pointCount;

            localBytesRead = SerializationHelper.Decode(inputStream, out pointCount);
            if (locallyDecodedBytesRemaining < localBytesRead)
                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

            locallyDecodedBytesRemaining -= localBytesRead;
            if (0 == locallyDecodedBytesRemaining)
                return localBytesRead;

            // Allocate packet properties
            int intsPerPoint = stylusPointDescription.GetInputArrayLengthPerPoint();
            int buttonCount = stylusPointDescription.ButtonCount;
            int buttonIntsPerPoint = (buttonCount > 0 ? 1 : 0);
            int valueIntsPerPoint = intsPerPoint - buttonIntsPerPoint;
            //add one int per point for button data if it exists
            int[] rawPointData = new int[pointCount * intsPerPoint];
            int[] packetDataSet = new int[pointCount];
            

            // copy the rest of the data from the stroke data
            byte[] inputBuffer = new byte[locallyDecodedBytesRemaining];

            // Read the input data into the byte array
            uint bytesRead = StrokeCollectionSerializer.ReliableRead(inputStream, inputBuffer, locallyDecodedBytesRemaining);

            if ( bytesRead != locallyDecodedBytesRemaining )
            {
                // Make sure the bytes read are expected. If not, we should bail out.
                // An exception will be thrown.
                throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));
            }

            // at this point, we have read all of the bytes remaining in the input
            //      stream's packet block, and while we will keep the bytes remaining
            //      variable for positioning within the local byte buffer, we should
            //      not read from the stream again, or we risk reading into another
            //      ISF tag's block.
            int originalPressureIndex = stylusPointDescription.OriginalPressureIndex;
            for (int i = 0; i < valueIntsPerPoint && locallyDecodedBytesRemaining > 0; i++)
            {
                localBytesRead = locallyDecodedBytesRemaining;
                Compressor.DecompressPacketData(
#if OLD_ISF
                        compressor, 
#endif
                        inputBuffer, 
                        ref localBytesRead, 
                        packetDataSet);

                if (localBytesRead > locallyDecodedBytesRemaining)
                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Invalid ISF data"));

                //
                // packetDataSet is like this:
                // -------------
                // |X|X|X|X|X|X|
                // -------------
                //
                // we need to copy into rawPointData at
                //
                // -------------
                // |X| |X| |X| |
                // -------------
                //
                // additionally, for NormalPressure, if it exists and was 
                // reordered in the StylusPointDescription, we need to account for that here
                //
                int tempi = i;
                if (tempi > 1 && 
                    originalPressureIndex != -1 && 
                    originalPressureIndex != StylusPointDescription.RequiredPressureIndex/*2*/)
                {
                    //
                    // NormalPressure exists in the packet stream and was not at index 2
                    // StylusPointDescription enforces that NormalPressure is at index 2
                    // so we need to copy packet data beyond X and Y into a different location
                    //
                    // take the example of the original StylusPointDescription
                    //  |X|Y|XTilt|YTilt|NormalPressure|Rotation|
                    //
                    // originalPressureIndex is 4, and we know it is now 2
                    // which means that everything before index 4 has been shifted one
                    // and everything after index 4 is still good.  Index 4 should be copied to index 2
                    if (tempi == originalPressureIndex)
                    {
                        tempi = 2;
                    }
                    else if (tempi < originalPressureIndex)
                    {
                        tempi++;
                    }
                }

                locallyDecodedBytesRemaining -= localBytesRead;
                for (int j = 0, x = 0; j < pointCount; j++, x += intsPerPoint)
                {

                    rawPointData[x + tempi] = packetDataSet[j];
                }

                // Move the array elements to point to next set of compressed data
                for (uint u = 0; u < locallyDecodedBytesRemaining; u++)
                {
                    inputBuffer[u] = inputBuffer[u + (int)localBytesRead];
                }
            }

            // Now that we've read packet data, we must read button data if it is there
            byte[] buttonData = null;
            // since the button state is a simple bit value (either down or up), the button state
            // for a series of packets is packed into an array of bits rather than integers
            // For example, if there are 16 packets, and 2 buttons, then 32 bits can be used (e.g. 1 32-bit integer)
            if (0 != locallyDecodedBytesRemaining && buttonCount > 0)
            {
                    // calculate the number of full bytes used for buttons per packet
                    //   Example: 10 buttons would require 1 full byte
                int fullBytesForButtonsPerPacket = buttonCount / Native.BitsPerByte;
                    // calculate the number of bits that spill beyond the full byte boundary
                    //   Example: 10 buttons would require 2 extra bits (8 fit in a full byte)
                int partialBitsForButtonsPerPacket = buttonCount % Native.BitsPerByte;

                // Now figure out how many bytes we need to read for the button data
                localBytesRead = (uint)((buttonCount * pointCount + 7) / Native.BitsPerByte);
                if (localBytesRead > locallyDecodedBytesRemaining)
                {
                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Buffer range is smaller than expected expected size"));
                }
                locallyDecodedBytesRemaining -= localBytesRead;

                int buttonSizeInBytes = (buttonCount + 7)/Native.BitsPerByte;
                buttonData = new byte[pointCount * buttonSizeInBytes];

                // Create a bit reader to unpack the bits from the ISF stream into
                //    loosely packed byte buffer (e.g. button data aligned on full byte
                //    boundaries only)
                BitStreamReader bitReader =
                    new BitStreamReader(inputBuffer, (uint)buttonCount * pointCount);

                // unpack the button data into each packet
                int byteCounter = 0;
                while (!bitReader.EndOfStream)
                {
                    // unpack the fully bytes first
                    for (int fullBytes = 0; fullBytes < fullBytesForButtonsPerPacket; fullBytes++)
                    {
                        buttonData[byteCounter++] = bitReader.ReadByte(Native.BitsPerByte);
                    }
                    // then unpack a single partial byte if necessary
                    if (partialBitsForButtonsPerPacket > 0)
                    {
                        buttonData[byteCounter++] = bitReader.ReadByte((int)partialBitsForButtonsPerPacket);
                    }
                }

                // if the number of bytes allocated != necessary byte amount then an error occurred
                if (byteCounter != buttonData.Length)
                {
                    throw new ArgumentException(StrokeCollectionSerializer.ISFDebugMessage("Button data length not equal to expected length"));
                }

                //
                // set the point data in the raw array
                //
                FillButtonData( (int)pointCount,
                                buttonCount,
                                valueIntsPerPoint, //gives the first button index
                                rawPointData,
                                buttonData);
            }


            stylusPoints = new StylusPointCollection(stylusPointDescription, rawPointData, null, transform);

            // if we read too far into the stream (e.g. the packets were compressed)
            //      then move the stream pointer back to the end of the actual packet
            //      data before returning. This keeps the return value on the function
            //      (representing bytes read) honest and consistent with the stream
            //      position movement in this function.
            if (0 != locallyDecodedBytesRemaining)
            {
                inputStream.Seek(0 - (long)locallyDecodedBytesRemaining, SeekOrigin.Current);
            }

            return totalBytesInStrokeBlockOfIsfStream - locallyDecodedBytesRemaining;
        }
 /////////////////////////////////////////////////////////////////////
 /// <summary>
 ///		Returns a StylusPointCollection for processing the data from input.
 ///		This method creates a new StylusPointCollection and copies the data.
 /// </summary>
 public StylusPointCollection GetStylusPoints(IInputElement relativeTo, StylusPointDescription subsetToReformatTo)
 {
     return StylusDevice.GetStylusPoints(relativeTo, subsetToReformatTo);
 }
Exemple #36
0
 /// <summary>
 /// StylusPoint
 /// </summary>
 /// <param name="x">x</param>
 /// <param name="y">y</param>
 /// <param name="pressureFactor">pressureFactor</param>
 /// <param name="stylusPointDescription">stylusPointDescription</param>
 /// <param name="additionalValues">additionalValues</param>
 public StylusPoint(double x, double y, float pressureFactor, StylusPointDescription stylusPointDescription, int[] additionalValues)
     : this(x, y, pressureFactor, stylusPointDescription, additionalValues, true, true)
 {
 }
Exemple #37
0
 /// <summary>
 ///     Returns a StylusPointCollection object for processing the data in the packet.
 ///     This method creates a new StylusPointCollection and copies the data.
 /// </summary>
 internal abstract StylusPointCollection GetStylusPoints(IInputElement relativeTo, StylusPointDescription subsetToReformatTo);
Exemple #38
0
        /// <summary>
        /// internal ctor
        /// </summary>
        internal StylusPoint(
            double x,
            double y,
            float pressureFactor,
            StylusPointDescription stylusPointDescription,
            int[] additionalValues,
            bool validateAdditionalData,
            bool validatePressureFactor)
        {
            if (Double.IsNaN(x))
            {
                throw new ArgumentOutOfRangeException("x", SR.Get(SRID.InvalidStylusPointXYNaN));
            }
            if (Double.IsNaN(y))
            {
                throw new ArgumentOutOfRangeException("y", SR.Get(SRID.InvalidStylusPointXYNaN));
            }


            //we don't validate pressure when called by StylusPointDescription.Reformat
            if (validatePressureFactor &&
                (pressureFactor == Single.NaN || pressureFactor < 0.0f || pressureFactor > 1.0f))
            {
                throw new ArgumentOutOfRangeException("pressureFactor", SR.Get(SRID.InvalidPressureValue));
            }
            //
            // only accept values between MaxXY and MinXY
            // we don't throw when passed a value outside of that range, we just silently trunctate
            //
            _x = GetClampedXYValue(x);
            _y = GetClampedXYValue(y);
            _stylusPointDescription = stylusPointDescription;
            _additionalValues       = additionalValues;
            _pressureFactor         = pressureFactor;

            if (validateAdditionalData)
            {
                //
                // called from the public verbose ctor
                //
                if (null == stylusPointDescription)
                {
                    throw new ArgumentNullException("stylusPointDescription");
                }

                //
                // additionalValues can be null if PropertyCount == 3 (X, Y, P)
                //
                if (stylusPointDescription.PropertyCount > StylusPointDescription.RequiredCountOfProperties &&
                    null == additionalValues)
                {
                    throw new ArgumentNullException("additionalValues");
                }


                if (additionalValues != null)
                {
                    ReadOnlyCollection <StylusPointPropertyInfo> properties
                        = stylusPointDescription.GetStylusPointProperties();

                    int expectedAdditionalValues = properties.Count - StylusPointDescription.RequiredCountOfProperties; //for x, y, pressure
                    if (additionalValues.Length != expectedAdditionalValues)
                    {
                        throw new ArgumentException(SR.Get(SRID.InvalidAdditionalDataForStylusPoint), "additionalValues");
                    }

                    //
                    // any buttons passed in must each be in their own int.  We need to
                    // pack them all into one int here
                    //
                    int[] newAdditionalValues =
                        new int[stylusPointDescription.GetExpectedAdditionalDataCount()];

                    _additionalValues = newAdditionalValues;
                    for (int i = StylusPointDescription.RequiredCountOfProperties, j = 0; i < properties.Count; i++, j++)
                    {
                        //
                        // use SetPropertyValue, it validates buttons, but does not copy the
                        // int[] on writes (since we pass the bool flag)
                        //
                        SetPropertyValue(properties[i], additionalValues[j], false /*copy on write*/);
                    }
                }
            }
        }
        /////////////////////////////////////////////////////////////////////
        /// <summary>
        ///     Returns a StylusPointCollection object for processing the data in the packet.
        ///     This method creates a new StylusPointCollection and copies the data.
        /// </summary>
        public StylusPointCollection GetStylusPoints(IInputElement relativeTo, StylusPointDescription subsetToReformatTo)
        {
            if (null == subsetToReformatTo)
            {
                throw new ArgumentNullException("subsetToReformatTo");
            }
            // Fake up an empty one if we have to.
            if (_eventStylusPoints == null)
            {
                return new StylusPointCollection(subsetToReformatTo);
            }

            return _eventStylusPoints.Reformat(subsetToReformatTo, GetElementTransform(relativeTo));
        }
Exemple #40
0
        private void GetPacketData
        (
            Stroke stroke,
            out MS.Win32.Recognizer.PACKET_DESCRIPTION packetDescription, 
            out int countOfBytes, 
            out IntPtr packets, 
            out NativeMethods.XFORM xForm
        )
        {
            int i;
            countOfBytes = 0;
            packets = IntPtr.Zero;
            packetDescription = new MS.Win32.Recognizer.PACKET_DESCRIPTION();
            Matrix matrix = Matrix.Identity;
            xForm = new NativeMethods.XFORM((float)(matrix.M11), (float)(matrix.M12), (float)(matrix.M21),
                                            (float)(matrix.M22), (float)(matrix.OffsetX), (float)(matrix.OffsetY));

            StylusPointCollection stylusPoints = stroke.StylusPoints;
            if (stylusPoints.Count == 0)
            {
                return; //we'll fail when the calling routine sees that packets is IntPtr.Zer
            }

            if (stylusPoints.Description.PropertyCount > StylusPointDescription.RequiredCountOfProperties)
            {
                //
                // reformat to X, Y, P
                //
                StylusPointDescription reformatDescription
                    = new StylusPointDescription(
                            new StylusPointPropertyInfo[]{
                                new StylusPointPropertyInfo(StylusPointProperties.X),
                                new StylusPointPropertyInfo(StylusPointProperties.Y),
                                stylusPoints.Description.GetPropertyInfo(StylusPointProperties.NormalPressure)});
                stylusPoints = stylusPoints.Reformat(reformatDescription);
            }

            //
            // now make sure we only take a finite amount of data for the stroke
            //
            if (stylusPoints.Count > MaxStylusPoints)
            {
                stylusPoints = stylusPoints.Clone(MaxStylusPoints);
            }

            Guid[] propertyGuids = new Guid[]{  StylusPointPropertyIds.X, //required index for SPD
                                                StylusPointPropertyIds.Y, //required index for SPD
                                                StylusPointPropertyIds.NormalPressure}; //required index for SPD

            Debug.Assert(stylusPoints != null);
            Debug.Assert(propertyGuids.Length == StylusPointDescription.RequiredCountOfProperties);

            // Get the packet description
            packetDescription.cbPacketSize = (uint)(propertyGuids.Length * Marshal.SizeOf(typeof(Int32)));
            packetDescription.cPacketProperties = (uint)propertyGuids.Length;

            //
            // use X, Y defaults for metrics, sometimes mouse metrics can be bogus
            // always use NormalPressure metrics, though.
            //
            StylusPointPropertyInfo[] infosToUse = new StylusPointPropertyInfo[StylusPointDescription.RequiredCountOfProperties];
            infosToUse[StylusPointDescription.RequiredXIndex] = StylusPointPropertyInfoDefaults.X;
            infosToUse[StylusPointDescription.RequiredYIndex] = StylusPointPropertyInfoDefaults.Y;
            infosToUse[StylusPointDescription.RequiredPressureIndex] =
                stylusPoints.Description.GetPropertyInfo(StylusPointProperties.NormalPressure);

            MS.Win32.Recognizer.PACKET_PROPERTY[] packetProperties = 
                new MS.Win32.Recognizer.PACKET_PROPERTY[packetDescription.cPacketProperties];
            
            StylusPointPropertyInfo propertyInfo;
            for ( i = 0; i < packetDescription.cPacketProperties; i++ )
            {
                packetProperties[i].guid = propertyGuids[i];
                propertyInfo = infosToUse[i];

                MS.Win32.Recognizer.PROPERTY_METRICS propertyMetrics = new MS.Win32.Recognizer.PROPERTY_METRICS( );
                propertyMetrics.nLogicalMin = propertyInfo.Minimum;
                propertyMetrics.nLogicalMax = propertyInfo.Maximum;
                propertyMetrics.Units = (int)(propertyInfo.Unit);
                propertyMetrics.fResolution = propertyInfo.Resolution;
                packetProperties[i].PropertyMetrics = propertyMetrics;
            }

            unsafe
            {
                int allocationSize = (int)(Marshal.SizeOf(typeof(MS.Win32.Recognizer.PACKET_PROPERTY)) * packetDescription.cPacketProperties);
                packetDescription.pPacketProperties = Marshal.AllocCoTaskMem(allocationSize);
                MS.Win32.Recognizer.PACKET_PROPERTY* pPacketProperty = 
                    (MS.Win32.Recognizer.PACKET_PROPERTY*)(packetDescription.pPacketProperties.ToPointer());
                MS.Win32.Recognizer.PACKET_PROPERTY* pElement = pPacketProperty;
                for ( i = 0 ; i < packetDescription.cPacketProperties ; i ++ )
                {
                    Marshal.StructureToPtr(packetProperties[i], new IntPtr(pElement), false);
                    pElement++;
                }
            }

            // Get packet data
            int[] rawPackets = stylusPoints.ToHiMetricArray();
            int packetCount = rawPackets.Length;
            if (packetCount != 0)
            {
                countOfBytes = packetCount * Marshal.SizeOf(typeof(Int32));
                packets = Marshal.AllocCoTaskMem(countOfBytes);
                Marshal.Copy(rawPackets, 0, packets, packetCount);
            }
        }
Exemple #41
0
        private void InitStylusPointDescription()
        {
            int cProps;
            int cButtons;
            int pressureIndex = -1;

            // Make sure we are never called on the application thread when we need to talk
            // to penimc or else we can cause reentrancy!
            Debug.Assert(!_contexts._inputSource.Value.CheckAccess());

            // We should always have a valid IPimcContext2 interface pointer.
            Debug.Assert(_pimcContext != null && _pimcContext.Value != null);

            _pimcContext.Value.GetPacketDescriptionInfo(out cProps, out cButtons); // Calls Unmanaged code - SecurityCritical with SUC.

            List <StylusPointPropertyInfo> propertyInfos = new List <StylusPointPropertyInfo>(cProps + cButtons + 3);

            for (int i = 0; i < cProps; i++)
            {
                Guid  guid;
                int   min, max;
                int   units;
                float res;
                _pimcContext.Value.GetPacketPropertyInfo(i, out guid, out min, out max, out units, out res); // Calls Unmanaged code - SecurityCritical with SUC.

                if (pressureIndex == -1 && guid == StylusPointPropertyIds.NormalPressure)
                {
                    pressureIndex = i;
                }

                if (_statusPropertyIndex == -1 && guid == StylusPointPropertyIds.PacketStatus)
                {
                    _statusPropertyIndex = i;
                }

                StylusPointPropertyInfo propertyInfo = new StylusPointPropertyInfo(new StylusPointProperty(guid, false), min, max, (StylusPointPropertyUnit)units, res);

                propertyInfos.Add(propertyInfo);
            }

            Debug.Assert(_statusPropertyIndex != -1);  // We should always see this.

            // Make sure we actually created propertyInfos OK
            if (propertyInfos != null)
            {
                for (int i = 0; i < cButtons; i++)
                {
                    Guid buttonGuid;
                    _pimcContext.Value.GetPacketButtonInfo(i, out buttonGuid); // Calls Unmanaged code - SecurityCritical with SUC.

                    StylusPointProperty     buttonProperty = new StylusPointProperty(buttonGuid, true);
                    StylusPointPropertyInfo buttonInfo     = new StylusPointPropertyInfo(buttonProperty);
                    propertyInfos.Add(buttonInfo);
                }

                //validate we can never get X, Y at index != 0, 1
                Debug.Assert(propertyInfos[StylusPointDescription.RequiredXIndex /*0*/].Id == StylusPointPropertyIds.X, "X isn't where we expect it! Fix PenImc to ask for X at index 0");
                Debug.Assert(propertyInfos[StylusPointDescription.RequiredYIndex /*0*/].Id == StylusPointPropertyIds.Y, "Y isn't where we expect it! Fix PenImc to ask for Y at index 1");
                Debug.Assert(pressureIndex == -1 || pressureIndex == StylusPointDescription.RequiredPressureIndex /*2*/,
                             "Fix PenImc to ask for NormalPressure at index 2!");
                if (pressureIndex == -1)
                {
                    //pressure wasn't found.  Add it
                    propertyInfos.Insert(StylusPointDescription.RequiredPressureIndex /*2*/, StylusPointPropertyInfoDefaults.NormalPressure);
                }
                _infoX = propertyInfos[0];
                _infoY = propertyInfos[1];

                _stylusPointDescription = new StylusPointDescription(propertyInfos, pressureIndex);
            }
        }
        /// <summary>
        /// Returns true if the two StylusPointDescriptions have the same StylusPointProperties.  Metrics are ignored.
        /// </summary>
        /// <param name="stylusPointDescription1">stylusPointDescription1</param>
        /// <param name="stylusPointDescription2">stylusPointDescription2</param>
        public static bool AreCompatible(StylusPointDescription stylusPointDescription1, StylusPointDescription stylusPointDescription2)
        {
            if (stylusPointDescription1 == null || stylusPointDescription2 == null)
            {
                throw new ArgumentNullException("stylusPointDescription");
            }

            #pragma warning disable 6506 // if a StylusPointDescription is not null, then _stylusPointPropertyInfos is not null.
            //
            // ignore X, Y, Pressure - they are guaranteed to be the first3 members
            //
            Debug.Assert(   stylusPointDescription1._stylusPointPropertyInfos.Length >= RequiredCountOfProperties &&
                            stylusPointDescription1._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                            stylusPointDescription1._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                            stylusPointDescription1._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);

            Debug.Assert(   stylusPointDescription2._stylusPointPropertyInfos.Length >= RequiredCountOfProperties &&
                            stylusPointDescription2._stylusPointPropertyInfos[0].Id == StylusPointPropertyIds.X &&
                            stylusPointDescription2._stylusPointPropertyInfos[1].Id == StylusPointPropertyIds.Y &&
                            stylusPointDescription2._stylusPointPropertyInfos[2].Id == StylusPointPropertyIds.NormalPressure);

            if (stylusPointDescription1._stylusPointPropertyInfos.Length != stylusPointDescription2._stylusPointPropertyInfos.Length)
            {
                return false;
            }
            for (int x = RequiredCountOfProperties; x < stylusPointDescription1._stylusPointPropertyInfos.Length; x++)
            {
                if (!StylusPointPropertyInfo.AreCompatible(stylusPointDescription1._stylusPointPropertyInfos[x], stylusPointDescription2._stylusPointPropertyInfos[x]))
                {
                    return false;
                }
            }
            #pragma warning restore 6506

            return true;
        }