Code:
/ DotNET / DotNET / 8.0 / untmp / WIN_WINDOWS / lh_tools_devdiv_wpf / Windows / wcp / Print / Reach / Serialization / ImageSourceTypeConverter.cs / 3 / ImageSourceTypeConverter.cs
/*++ Copyright (C) 2004 - 2005 Microsoft Corporation All rights reserved. Module Name: ImageSourceTypeConverter.cs Abstract: This file implements the ImageSourceTypeConverter used by the Xps Serialization APIs for serializing images to a Xps package. Author: [....] ([....]) 1-December-2004 Revision History: --*/ using System; using System.Net; using System.Collections; using System.Collections.Specialized; using System.Collections.Generic; using System.ComponentModel; using System.IO; using System.IO.Packaging; using System.Windows.Media; using System.Windows.Media.Imaging; using System.Windows.Xps.Packaging; using System.Security; using System.Security.Permissions; using MS.Internal.ReachFramework; using System.Windows.Markup; using MS.Internal.IO.Packaging; namespace System.Windows.Xps.Serialization { ////// This class implements a type converter for converting /// images to Uris. It handles the writing of the image /// to a Xps package and returns a package URI to the /// caller. It also handles reading an image from a /// Xps package given a Uri. /// public class ImageSourceTypeConverter : ExpandableObjectConverter { #region Public overrides for ExpandableObjectConverted ////// Returns whether this converter can convert an object /// of the given type to the type of this converter. /// /// /// An ITypeDescriptorContext that provides a format context. /// /// /// A Type that represents the type you want to convert from. /// ////// true if this converter can perform the conversion; /// otherwise, false. /// public override bool CanConvertFrom( ITypeDescriptorContext context, Type sourceType ) { return IsSupportedType(sourceType); } ////// Returns whether this converter can convert the object /// to the specified type. /// /// /// An ITypeDescriptorContext that provides a format context. /// /// /// A Type that represents the type you want to convert to. /// ////// true if this converter can perform the conversion; /// otherwise, false. /// public override bool CanConvertTo( ITypeDescriptorContext context, Type destinationType ) { return IsSupportedType(destinationType); } ////// Converts the given value to the type of this converter. /// /// /// An ITypeDescriptorContext that provides a format context. /// /// /// The CultureInfo to use as the current culture. /// /// /// The Object to convert. /// ////// An Object that represents the converted value. /// public override object ConvertFrom( ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value ) { if( value == null ) { throw new ArgumentNullException("value"); } if (!IsSupportedType(value.GetType())) { throw new NotSupportedException(ReachSR.Get(ReachSRID.Converter_ConvertFromNotSupported)); } throw new NotImplementedException(); } ////// Converts the given value object to the specified type, /// using the arguments. /// /// /// An ITypeDescriptorContext that provides a format context. /// /// /// A CultureInfo object. If null is passed, the current /// culture is assumed. /// /// /// The Object to convert. /// /// /// The Type to convert the value parameter to. /// ////// The Type to convert the value parameter to. /// ////// Critical - 1) Calls GetImageMimeType which is security critical /// /// /// 2) Calls ReEncodeBitmap which is security critical /// /// TreatAsSafe: /// 1) MimeTypes demands Unrestriced registry access. Presumably /// to discover registered bitmaps. Registry information is not passed to caller. /// /// 2) Getting codecinfo data is OK (Direct quote from CodecInfo ) /// /// 3) Uses the information to detrmine Bitmap Source type so it can be serialzied into stream with the same type. /// [SecurityCritical, SecurityTreatAsSafe] public override object ConvertTo( ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value, Type destinationType ) { Toolbox.StartEvent(MS.Utility.EventTraceGuidId.DRXCONVERTIMAGEGUID); if( context == null ) { throw new ArgumentNullException("context"); } if (!IsSupportedType(destinationType)) { throw new NotSupportedException(ReachSR.Get(ReachSRID.Converter_ConvertToNotSupported)); } // // Check that we have a valid BitmapSource instance. // BitmapSource bitmapSource = (BitmapSource)value; if (bitmapSource == null) { throw new ArgumentException(ReachSR.Get(ReachSRID.MustBeOfType, "value", "BitmapSource")); } // // Get the current serialization manager. // PackageSerializationManager manager = (PackageSerializationManager)context.GetService(typeof(XpsSerializationManager)); //Get the image Uri if it has already been serialized Uri imageUri = GetBitmapSourceFromImageTable(manager, bitmapSource); // // Get the current page image cache // DictionarycurrentPageImageTable = manager.ResourcePolicy.CurrentPageImageTable; if (imageUri != null) { int uriHashCode = imageUri.GetHashCode(); if(!currentPageImageTable.ContainsKey(uriHashCode)) { // // Also, add a relationship for the current page to this image // resource. This is needed to conform with Xps specification. // manager.AddRelationshipToCurrentPage(imageUri, XpsS0Markup.ResourceRelationshipName); currentPageImageTable.Add(uriHashCode, imageUri); } } else { // // This image as never serialized before so we will do it now. // Retrieve the image serialization service from the resource policy // IServiceProvider resourceServiceProvider = manager.ResourcePolicy; XpsImageSerializationService imageService = (XpsImageSerializationService)resourceServiceProvider.GetService(typeof(XpsImageSerializationService)); if (imageService == null) { throw new XpsSerializationException(ReachSR.Get(ReachSRID.ReachSerialization_NoImageService)); } // // Obtain a valid encoder for the image. // BitmapEncoder encoder = imageService.GetEncoder(bitmapSource); string imageMimeType = GetImageMimeType(encoder); bool isSupportedMimeType = imageService.IsSupportedMimeType(bitmapSource); // // Acquire a writable stream from the serialization manager and encode // and serialize the image into the stream. // XpsResourceStream resourceStream = manager.AcquireResourceStream(typeof(BitmapSource), imageMimeType); bool bCopiedStream = false; BitmapFrame bitmapFrame = bitmapSource as BitmapFrame; if (isSupportedMimeType && bitmapFrame != null && bitmapFrame.Decoder != null ) { BitmapDecoder decoder = bitmapFrame.Decoder; try { Uri sourceUri = new Uri(decoder.ToString()); Stream srcStream = MS.Internal.WpfWebRequestHelper.CreateRequestAndGetResponseStream(sourceUri); CopyImageStream(srcStream, resourceStream.Stream); srcStream.Close(); bCopiedStream = true; } catch (UriFormatException) { //the uri was not valid we will re-encode the image below } catch (WebException) { //Web Request failed we will re-encode the image below } } if (!bCopiedStream) { Stream stream = new MemoryStream(); ReEncodeImage(bitmapSource, encoder, stream); stream.Position = 0; CopyImageStream(stream, resourceStream.Stream); } // // Make sure to commit the resource stream by releasing it. // imageUri = resourceStream.Uri; manager.ReleaseResourceStream(typeof(BitmapSource)); AddBitmapSourceToImageTables(manager, imageUri); } Toolbox.EndEvent(MS.Utility.EventTraceGuidId.DRXCONVERTIMAGEGUID); return imageUri; } /// /// Gets a collection of properties for the type of object /// specified by the value parameter. /// /// /// An ITypeDescriptorContext that provides a format context. /// /// /// An Object that specifies the type of object to get the /// properties for. /// /// /// An array of type Attribute that will be used as a filter. /// ////// A PropertyDescriptorCollection with the properties that are /// exposed for the component, or null if there are no properties. /// public override PropertyDescriptorCollection GetProperties( ITypeDescriptorContext context, object value, Attribute[] attributes ) { throw new NotImplementedException(); } #endregion Public overrides for ExpandableObjectConverted #region Private static helper methods ////// Looks up the type in a table to determine /// whether this type is supported by this /// class. /// /// /// Type to lookup in table. /// ////// True is supported; otherwise false. /// private static bool IsSupportedType( Type type ) { bool isSupported = false; foreach (Type t in SupportedTargetTypes) { if (t.Equals(type)) { isSupported = true; break; } } return isSupported; } private static void CopyImageStream( Stream sourceStream, Stream destinationStream ) { byte[] buffer= new byte[_readBlockSize]; int bytesRead = PackagingUtilities.ReliableRead( sourceStream, buffer, 0, _readBlockSize); while( bytesRead > 0 ) { destinationStream.Write(buffer, 0, bytesRead); bytesRead = PackagingUtilities.ReliableRead( sourceStream, buffer, 0, _readBlockSize); } } ////// Critical - 1) Asserts mediaAccessPermission for non site of origin data /// [SecurityCritical] private static void ReEncodeImage(BitmapSource bitmapSource, BitmapEncoder encoder, Stream stream ) { BitmapFrame bitmapFrame = null; // // The uri the BitmapFrame.Create will use is null since it is accessing metadata at // construction and its uri is still null // CodeAccessPermission mediaAccessPermission = SecurityHelper.CreateMediaAccessPermission(null); if (mediaAccessPermission != null) { mediaAccessPermission.Assert(); //BlessedAssert } try { bitmapFrame = BitmapFrame.Create(bitmapSource); } finally { if (mediaAccessPermission != null) { CodeAccessPermission.RevertAssert(); } } encoder.Frames.Add(bitmapFrame); if (mediaAccessPermission != null) { mediaAccessPermission.Assert(); //BlessedAssert } try { encoder.Save(stream); } finally { if (mediaAccessPermission != null) { CodeAccessPermission.RevertAssert(); } } } ////// Calculates a Crc32 value for a given BitmapSource. /// /// /// BitmapSource containing image data to calculate /// the Crc32 value for. /// ////// A 32-bit unsigned integer Crc32 value. /// ////// Critical: This code calls an inernal PresentationCore function CriticalCopyPixels /// TreatAsSafe: We just calcualte 32-bit CRC, image itself is not exposed /// [SecurityCritical, SecurityTreatAsSafe] private static UInt32 CalculateImageCrc32( BitmapSource bitmapSource ) { Crc32 crc32 = new Crc32(); int width = bitmapSource.PixelWidth; int height = bitmapSource.PixelHeight; int stride = (width * bitmapSource.Format.BitsPerPixel + 7) / 8; Int32Rect rect = new Int32Rect(0, 0, width, 1); byte[] pixels = new byte[stride]; for (int i = 0; i < height; i += 1) { bitmapSource.CriticalCopyPixels(rect, pixels, stride, 0); rect.Y++; crc32.AddData(pixels); } return crc32.Crc32Value; } ////// Critical - 1) Asserts to access the registry. May return path information which /// could disclose windows directory (ie. c:\windows\media\sound.wav) /// /// 2) Access unmanaged code, codecs /// /// [SecurityCritical] private static string GetImageMimeType( BitmapEncoder encoder ) { string mimetypes; string imageMimeType = "image/unknown"; // // To determine the mime-type of the image we just grab // the first one supported by this encoder and use that. // PermissionSet permissions = new PermissionSet(null); permissions.AddPermission(new SecurityPermission(SecurityPermissionFlag.UnmanagedCode)); permissions.AddPermission(new RegistryPermission(PermissionState.Unrestricted)); permissions.Assert(); try { mimetypes = encoder.CodecInfo.MimeTypes; } finally { CodeAccessPermission.RevertAssert(); } int comma = mimetypes.IndexOf(','); if (comma != -1) { imageMimeType = mimetypes.Substring(0, comma); } else { imageMimeType = mimetypes; } return imageMimeType; } private Uri GetBitmapSourceFromImageTable(PackageSerializationManager manager, BitmapSource bitmapSource) { Uri imageUri = null; //Initialize cache values _uriHashValue = 0; _crc32HashValue = 0; BitmapFrame bitmapFrame = bitmapSource as BitmapFrame; //Use the Uri hash table if we have a bitmap with a Uri if (bitmapFrame != null && bitmapFrame.Decoder != null) { String sourceUri = bitmapFrame.Decoder.ToString(); if (sourceUri != null) { _uriHashValue = sourceUri.GetHashCode(); DictionaryimageUriHashTable = manager.ResourcePolicy.ImageUriHashTable; if (imageUriHashTable.ContainsKey(_uriHashValue)) { imageUri = imageUriHashTable[_uriHashValue]; } } } //Checking the UriHash for zero tells us if the uri of the bitmap was checked and if it returned a valid Uri if (_uriHashValue == 0) { // // Calculate the image Crc32 value. This is used as a key // into the image cache. // _crc32HashValue = CalculateImageCrc32(bitmapSource); // // Get the current image cache // Dictionary imageCrcTable = manager.ResourcePolicy.ImageCrcTable; // // The image has already been cached (and therefore serialized). // No need to serialize it again so we just return the Uri in the // package where the original was serialized. For that Uri returned // a relationship is only created if this has not been included on // the current page before. // if (imageCrcTable.ContainsKey(_crc32HashValue)) { imageUri = imageCrcTable[_crc32HashValue]; } } return imageUri; } private void AddBitmapSourceToImageTables(PackageSerializationManager manager, Uri imageUri) { if (_uriHashValue != 0) { manager.ResourcePolicy.ImageUriHashTable.Add(_uriHashValue,imageUri); _uriHashValue = 0; } else { manager.ResourcePolicy.ImageCrcTable.Add(_crc32HashValue, imageUri); _crc32HashValue = 0; } manager.ResourcePolicy.CurrentPageImageTable.Add(imageUri.GetHashCode(), imageUri); } #endregion Private static helper methods #region Private static data /// /// A table of supported types for this type converter /// private static Type[] SupportedTargetTypes = { typeof(Uri) }; private static readonly int _readBlockSize = 1048576; //1MB ////// Cached hash values for image tables /// private int _uriHashValue; private UInt32 _crc32HashValue; #endregion Private static data } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu
This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- SystemTcpStatistics.cs
- ObjectRef.cs
- SRef.cs
- SelectedDatesCollection.cs
- UserControlCodeDomTreeGenerator.cs
- BaseConfigurationRecord.cs
- unitconverter.cs
- DataViewListener.cs
- Int32AnimationBase.cs
- Sorting.cs
- PathSegmentCollection.cs
- BindingContext.cs
- GcSettings.cs
- ConsumerConnectionPointCollection.cs
- MetabaseReader.cs
- HttpFileCollectionBase.cs
- XmlSchemaRedefine.cs
- FamilyTypefaceCollection.cs
- XPathMultyIterator.cs
- Route.cs
- ExpandCollapsePattern.cs
- XmlCDATASection.cs
- DataMisalignedException.cs
- ItemContainerGenerator.cs
- RuntimeDelegateArgument.cs
- NetStream.cs
- FontClient.cs
- Converter.cs
- Rfc4050KeyFormatter.cs
- WebServiceData.cs
- TextCollapsingProperties.cs
- DataSourceDescriptorCollection.cs
- EffectiveValueEntry.cs
- ProvidersHelper.cs
- SimpleBitVector32.cs
- LocatorGroup.cs
- UmAlQuraCalendar.cs
- XMLDiffLoader.cs
- NetTcpSection.cs
- CompilerParameters.cs
- SecurityContext.cs
- dsa.cs
- RelatedPropertyManager.cs
- PipeException.cs
- _Win32.cs
- DoubleAnimationUsingKeyFrames.cs
- Padding.cs
- Table.cs
- IssuedTokenParametersEndpointAddressElement.cs
- EmbeddedObject.cs
- DiagnosticsConfiguration.cs
- Evidence.cs
- StylusCollection.cs
- ImageConverter.cs
- ClientSession.cs
- WebControl.cs
- XPathException.cs
- HandlerBase.cs
- QilVisitor.cs
- CompensationToken.cs
- FileNotFoundException.cs
- XmlSchemaDocumentation.cs
- GridViewRow.cs
- COM2ComponentEditor.cs
- QuaternionAnimationBase.cs
- BitmapScalingModeValidation.cs
- Binding.cs
- UIElement.cs
- MsmqInputChannelListener.cs
- WebPartHeaderCloseVerb.cs
- MulticastDelegate.cs
- TextRangeSerialization.cs
- TypeTypeConverter.cs
- Popup.cs
- OleDbEnumerator.cs
- SiteMap.cs
- AttributeCollection.cs
- GridViewColumnCollection.cs
- Trace.cs
- XmlSchemaAnnotated.cs
- XamlParser.cs
- TextElementEnumerator.cs
- FloaterBaseParaClient.cs
- ColorDialog.cs
- CacheOutputQuery.cs
- COM2ComponentEditor.cs
- ListDictionaryInternal.cs
- ScopeElementCollection.cs
- BitStream.cs
- LassoSelectionBehavior.cs
- SymbolType.cs
- XmlException.cs
- ResXDataNode.cs
- OwnerDrawPropertyBag.cs
- PointAnimationUsingPath.cs
- WebPartManagerInternals.cs
- DeclarativeCatalogPart.cs
- DeleteCardRequest.cs
- ImageDrawing.cs
- ButtonBaseAdapter.cs