Code:
/ DotNET / DotNET / 8.0 / untmp / WIN_WINDOWS / lh_tools_devdiv_wpf / Windows / wcp / TrustUi / MS / Internal / documents / Application / WriteableOnDemandStream.cs / 1 / WriteableOnDemandStream.cs
//------------------------------------------------------------------------------
//
// Copyright (C) Microsoft Corporation. All rights reserved.
//
//
// This class acts as a type of proxy; it is responsible for forwarding all
// stream requests to the active stream. Unlike a proxy it is also controls
// which stream is active. Initially the active stream is the stream provided
// at construction, at the time of the first write operation the active stream
// is replaced with one provided by a delegate.
//
// History:
// 07/04/2005: [....]: Initial implementation.
// 08/28/2005: [....]: Adjusted spacing and style to match team better
//-----------------------------------------------------------------------------
using System;
using System.IO;
using System.Windows.TrustUI;
namespace MS.Internal.Documents.Application
{
///
/// This class acts as a type of proxy; it is responsible for forwarding all
/// stream requests to the active stream. Unlike a proxy it is also
/// controls which stream is active. Initially the active stream is the
/// stream provided on construction, at the time of the first write
/// operation the active stream is replaced with one provided by a delegate.
///
///
/// As this class only proxies the abstract methods of Stream, if we are
/// proxing a stream that has overriden other virutal methods behavioral
/// inconsistencies may occur. This could be solved by forwarding all
/// calls. For internal use it is not currently needed.
///
internal sealed class WriteableOnDemandStream : Stream
{
#region Constructors
//-------------------------------------------------------------------------
// Constructors
//-------------------------------------------------------------------------
///
/// Constructs the class with readingStream as the active Stream.
///
///
/// The read only Stream.
/// FileMode that will be use to create write
/// stream.
/// FileAccess that will be use to create write
/// stream.
/// Delegate used to create a
/// write stream on first write operation.
internal WriteableOnDemandStream(
Stream readingStream,
FileMode mode,
FileAccess access,
GetWriteableInstance writeableStreamFactory)
{
if (readingStream == null)
{
throw new ArgumentNullException("readingStream");
}
if (writeableStreamFactory == null)
{
throw new ArgumentNullException("writeableStreamFactory");
}
_active = readingStream;
_mode = mode;
_access = access;
_writeableStreamFactory = writeableStreamFactory;
_wantedWrite = ((_access == FileAccess.ReadWrite)
|| (_access == FileAccess.Write));
}
#endregion Constructors
#region Stream Overrides
//--------------------------------------------------------------------------
// Stream Overrides
//-------------------------------------------------------------------------
// Due to sub-nesting of pure proxies vs. decorating ones code structure
// is simplier in this case by grouping Methods & Properies.
#region Pure Proxies for Stream
//--------------------------------------------------------------------------
// This region of code simply follows the proxy patern and only forwards
// the calls to the active stream.
//--------------------------------------------------------------------------
///
///
///
public override bool CanRead
{
get
{
return _active.CanRead;
}
}
///
///
///
public override bool CanSeek
{
get
{
return _active.CanSeek;
}
}
///
///
///
public override void Flush()
{
Trace.SafeWriteIf(
_isActiveWriteable,
Trace.Packaging,
"Flush is being called on read-only stream.");
if (_isActiveWriteable)
{
_active.Flush();
}
}
///
///
///
public override long Length
{
get
{
return _active.Length;
}
}
///
///
///
public override long Position
{
get
{
return _active.Position;
}
set
{
_active.Position = value;
}
}
///
///
///
public override int Read(byte[] buffer, int offset, int count)
{
return _active.Read(buffer, offset, count);
}
///
///
///
public override long Seek(long offset, SeekOrigin origin)
{
return _active.Seek(offset, origin);
}
#endregion Pure Proxies for Stream
#region Decorating Proxies for Stream
//-------------------------------------------------------------------------
// This region of code follows the decorator patern, the added behavior
// is the replacement of the active stream with one that is writeable
// on the first write operation.
//--------------------------------------------------------------------------
///
///
///
public override bool CanWrite
{
get
{
// asking if we can write is not a write operation,
// however, as the active type had to implement this
// abstract property thier implementation is the one
// we should prefer, when we are writable, until then
// it's more efficent to assume if the user asked for
// write it will be supported
if (_isActiveWriteable)
{
return _active.CanWrite;
}
else
{
return _wantedWrite;
}
}
}
///
///
///
public override void SetLength(long value)
{
EnsureWritable();
_active.SetLength(value);
}
///
///
///
public override void Write(byte[] buffer, int offset, int count)
{
EnsureWritable();
_active.Write(buffer, offset, count);
}
#endregion Decorating Proxies for Stream
#endregion Stream Overrides
#region Internal Delegates
//-------------------------------------------------------------------------
// Internal Delegates
//-------------------------------------------------------------------------
///
/// The delegate is use as a factory to return writable copy of the
/// stream we were originally given.
///
/// The FileMode desired.
/// The FileAccess desired.
/// A writeable Stream.
public delegate Stream GetWriteableInstance(
FileMode mode,
FileAccess access);
#endregion Internal Delegates
#region Protected Methods - Stream Overrides
//-------------------------------------------------------------------------
// Protected Methods - Stream Overrides
//--------------------------------------------------------------------------
///
/// Ensure we do not aquire new resources.
///
/// Indicates if we are disposing.
protected override void Dispose(bool disposing)
{
try
{
if (disposing)
{
if (_isActiveWriteable && _active.CanWrite)
{
_active.Flush();
// we do not want to dispose of _active
// first we are merely a proxy; and being done with
// us is not the same as being done with the PackagePart
// it supprots, the Package which created _active
// is calls dispose
}
_isActiveWriteable = true;
}
}
finally
{
base.Dispose(disposing);
}
}
#endregion Protected Methods - Stream Overrides
#region Private Methods
//-------------------------------------------------------------------------
// Private Methods
//--------------------------------------------------------------------------
///
/// Ensures either the active stream is our writeable stream or uses the
/// factory delegate to get one and assign it as the active stream.
///
///
///
private void EnsureWritable()
{
if (!_wantedWrite)
{
throw new NotSupportedException(
SR.Get(SRID.PackagingWriteNotSupported));
}
if (!_isActiveWriteable)
{
Stream writer = _writeableStreamFactory(_mode, _access);
if (writer == null)
{
throw new IOException(
SR.Get(SRID.PackagingWriteableDelegateGaveNullStream));
}
if (writer.Equals(this))
{
throw new IOException(
SR.Get(SRID.PackagingCircularReference));
}
writer.Position = _active.Position;
_active = writer;
_isActiveWriteable = true;
}
}
#endregion Private Methods
#region Private Fields
//--------------------------------------------------------------------------
// Private Fields
//-------------------------------------------------------------------------
///
/// The delegate we were given to have a writeable stream created.
///
private GetWriteableInstance _writeableStreamFactory;
///
/// The stream we should be currently using.
///
private Stream _active;
///
/// Whether the active stream is writeable.
///
private bool _isActiveWriteable;
///
/// The caller's desired FileMode provided on construction.
///
private FileMode _mode;
///
/// The caller's desired FileAccess provided on construction.
///
private FileAccess _access;
///
/// Calculated using FileAccess, it determines if writing was indicated.
///
private bool _wantedWrite;
#endregion Private Methods
}
}
// 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
- FilterableAttribute.cs
- UrlMapping.cs
- NavigationFailedEventArgs.cs
- InkCanvasFeedbackAdorner.cs
- ColorContext.cs
- WpfSharedBamlSchemaContext.cs
- IPPacketInformation.cs
- SessionSwitchEventArgs.cs
- CreatingCookieEventArgs.cs
- IconBitmapDecoder.cs
- WebServiceAttribute.cs
- mda.cs
- CodeTypeMember.cs
- SqlDataSource.cs
- PackageStore.cs
- LayoutEditorPart.cs
- ApplicationContext.cs
- LineSegment.cs
- BatchWriter.cs
- DesignerTransactionCloseEvent.cs
- Figure.cs
- CollectionAdapters.cs
- Vars.cs
- FlowLayoutSettings.cs
- SystemUnicastIPAddressInformation.cs
- BufferedStream.cs
- SafeBitVector32.cs
- BlurBitmapEffect.cs
- TemplateDefinition.cs
- Matrix3DConverter.cs
- ImageSource.cs
- RootBrowserWindowAutomationPeer.cs
- ObjectItemLoadingSessionData.cs
- XDeferredAxisSource.cs
- DataGridViewUtilities.cs
- QilNode.cs
- ConfigurationValidatorAttribute.cs
- MergeFailedEvent.cs
- Splitter.cs
- SQLRoleProvider.cs
- ControlBuilder.cs
- Container.cs
- AstNode.cs
- ProgressiveCrcCalculatingStream.cs
- MsmqPoisonMessageException.cs
- SerializerDescriptor.cs
- InstanceHandleReference.cs
- StylusPlugin.cs
- WebEventTraceProvider.cs
- AppDomain.cs
- ToolStripManager.cs
- iisPickupDirectory.cs
- CoreSwitches.cs
- Switch.cs
- WebException.cs
- XmlHierarchicalEnumerable.cs
- BuilderInfo.cs
- AsyncOperation.cs
- SqlTypeSystemProvider.cs
- _FtpDataStream.cs
- BrowserCapabilitiesFactoryBase.cs
- ToolStripDesigner.cs
- RTLAwareMessageBox.cs
- SchemaImporter.cs
- XmlNodeChangedEventManager.cs
- ExternalCalls.cs
- ValidationSummary.cs
- Viewport3DAutomationPeer.cs
- ClientRoleProvider.cs
- TextBoxAutomationPeer.cs
- DataChangedEventManager.cs
- CollectionBase.cs
- AssociatedControlConverter.cs
- XmlNodeReader.cs
- DataControlLinkButton.cs
- TextBoxRenderer.cs
- BindingMemberInfo.cs
- PaginationProgressEventArgs.cs
- DataServiceQueryProvider.cs
- DataSourceCacheDurationConverter.cs
- ExtensionElement.cs
- CodeMemberEvent.cs
- RunClient.cs
- ContentValidator.cs
- HighContrastHelper.cs
- DefaultDiscoveryServiceExtension.cs
- ButtonChrome.cs
- RegisteredArrayDeclaration.cs
- DataGridCellInfo.cs
- ItemList.cs
- WizardPanel.cs
- SamlDoNotCacheCondition.cs
- DataPagerFieldCollection.cs
- ComponentEditorForm.cs
- ServiceNotStartedException.cs
- AssemblyInfo.cs
- GeneralTransform3D.cs
- RayMeshGeometry3DHitTestResult.cs
- XmlSchemaSubstitutionGroup.cs
- RedirectionProxy.cs