Code:
/ DotNET / DotNET / 8.0 / untmp / WIN_WINDOWS / lh_tools_devdiv_wpf / Windows / wcp / TrustUi / MS / Internal / documents / Application / DocumentManager.cs / 1 / DocumentManager.cs
//------------------------------------------------------------------------------
//
// Copyright (C) Microsoft Corporation. All rights reserved.
//
//
/// Exposes the basic operations that can be performed on documents. (Open,
/// EnableEdit, Save)
//
//
// History:
// 08/28/2005: [....]: Initial implementation.
//-----------------------------------------------------------------------------
using System;
using System.Collections.Generic;
using System.IO;
using System.Security;
using MS.Internal.PresentationUI;
namespace MS.Internal.Documents.Application
{
///
/// Exposes the basic operations that can be performed on documents. (Open,
/// EnableEdit, Save)
///
///
/// Responsibility:
/// The class is responsible for delegating the work to the appropriate
/// controller(s) in the order needed based on document dependencies.
///
/// Design Comments:
/// Packages are dependent on EncryptedPackages who are dependent on FileStreams
/// however all these classes are very different in function.
///
/// By design once a controller has reported handling a document it will not be
/// given to other controllers. A controller should not see documents they are
/// not in the dependency chain for.
///
/// Example: FileController should never see RightsDocument.
///
[FriendAccessAllowed]
internal sealed class DocumentManager
: ChainOfResponsiblity
{
#region Constructors
//-------------------------------------------------------------------------
// Constructors
//-------------------------------------------------------------------------
///
/// Will construct a DocumentManager using the provided controllers.
///
/// Controllers in order of responsiblity from
/// top to bottom.
internal DocumentManager(params IDocumentController[] controllers)
: base(controllers) { }
#endregion Constructors
#region Internal Methods
//--------------------------------------------------------------------------
// Internal Methods
//-------------------------------------------------------------------------
///
/// Creates the default chain of controllers. (PackageController,
/// RightsController and FileController)
///
/// A DocumentManager.
///
/// This exists because of a a design compromise; see SaveAs below.
///
/// This compromise breaks encapsulation, because we have an understanding of
/// begin used within a navigation application.
///
internal static DocumentManager CreateDefault()
{
if (_singleton == null)
{
_controllers.Add(new HostedController());
_controllers.Add(new PackageController());
_controllers.Add(new RightsController());
_controllers.Add(new FileController());
_singleton = new DocumentManager(
_controllers.ToArray());
Trace.SafeWrite(Trace.File, "DocumentManager singleton created.");
}
return _singleton;
}
///
/// Creates the default chain of documents. (PackageDocument,
/// RightsDocument and FileDocument)
///
/// A Document.
///
/// Critical:
/// - sets Document.Uri which is critical
/// NotSafe:
/// - only the caller can assert that this is the source of the request
///
[SecurityCritical]
internal static PackageDocument CreateDefaultDocument(
Uri source, CriticalFileToken fileToken)
{
// because we have a fileToken we might be able to save
_canSave = true;
PackageDocument doc = new PackageDocument(
new RightsDocument(
new FileDocument(fileToken)));
doc.Uri = source;
return doc;
}
///
/// Creates the default chain of documents. (PackageDocument,
/// RightsDocument and FileDocument)
///
/// A Document.
///
/// Critical:
/// - call FileDocument ctor which uses stream as source
/// - sets Document.Uri which is critical
/// NotSafe:
/// - origin of stream is known only to caller
/// - only the caller can assert that this is the source of the request
///
[SecurityCritical]
internal static PackageDocument CreateDefaultDocument(
Uri source, Stream stream)
{
PackageDocument doc = new PackageDocument(
new RightsDocument(
new FileDocument(stream)));
doc.Uri = source;
return doc;
}
///
/// Allows IDocumentControllers to be properly cleaned up when created
/// by the factory method of this class.
///
internal static void CleanUp()
{
foreach (IDocumentController controller in _controllers)
{
IDisposable disposable = controller as IDisposable;
if (disposable != null)
{
disposable.Dispose();
}
}
}
///
/// Will enable editing for the document.
///
/// A document.
internal void EnableEdit(Document document)
{
if (document == null)
{
document = _current;
}
if (!_isEditEnabled)
{
_isEditEnabled = OrderByLeastDependent(DispatchEnableEdit, document);
}
}
///
/// Will open the specified document.
///
/// A document.
/// True if the operation succeeded
internal bool Open(Document document)
{
ThrowIfNull(document);
_current = document;
// since we just loaded the document, it is now unmodified from the saved version
_isModified = false;
return OrderByLeastDependent(DispatchOpen, document);
}
///
/// Will save the current document to a user-specified location.
///
/// True if the operation succeeded
internal bool SaveAs(Document document)
{
if (document == null)
{
document = _current;
}
bool result = OrderByLeastDependent(DispatchSaveAsPreperation, document);
if (result)
{
result = OrderByMostDependent(DispatchSaveCommit, document);
}
if (result)
{
// since we just saved the document, it is now unmodified from the saved version
_isModified = false;
result = OrderByLeastDependent(DispatchRebind, document);
}
return result;
}
///
/// Will save the specified document.
///
/// A document.
/// True if the operation succeeded
internal bool Save(Document document)
{
if (document == null)
{
document = _current;
}
bool result = OrderByLeastDependent(DispatchSavePreperation, document);
if (result)
{
result = OrderByMostDependent(DispatchSaveCommit, document);
}
// We always Rebind even if the Commit failed -- if we fail we still
// need to Rebind the original document.
OrderByLeastDependent(DispatchRebind, document);
// since we just saved the document, it is now unmodified from the saved version
_isModified = false;
return result;
}
///
/// This event handler is called to notify us that the document was modified.
///
/// sender of the event (not used)
/// arguments of the event (not used)
internal static void OnModify(Object sender, EventArgs args)
{
_isModified = true;
}
///
/// Forces the given document to reload.
///
/// The document
/// True if the operation succeeded
internal bool Reload(Document document)
{
if (document == null)
{
document = _current;
}
// Set IsReloadNeeded to force reloading the document
document.IsReloadNeeded = true;
// Dispatch a rebind operation, which will cause a reload
return OrderByLeastDependent(DispatchRebind, document);
}
#endregion Internal Methods
#region Internal Properties
//--------------------------------------------------------------------------
// Internal Properties
//--------------------------------------------------------------------------
///
/// Gets or sets whether saving to the source of the document may be possible.
///
///
/// Currently we only support saving when opened by a file Uri.
///
internal bool CanSave
{
get
{
return _canSave;
}
set
{
_canSave = value;
}
}
///
/// This property returns true if the document has been modified from the
/// version on disk (and therefore it makes sense for the user to save it).
/// This property combines modification information from multiple sources.
///
///
/// Some changes are reflected in Package.IsDirty -- all other changes
/// will notify us by writing to this property. The document is considered
/// modified if it is modified either according to the PackageDocument or
/// our internal flag.
///
internal bool IsModified
{
get
{
PackageDocument doc = _current as PackageDocument;
// If we don't have a PackageDocument (for example, if we are viewing
// a read-only file), then only our internal flag is used.
if (doc == null || doc.Package == null)
{
return _isModified;
}
else
{
return doc.Package.IsDirty || _isModified;
}
}
}
#endregion Internal Properties
#region Private Methods
//-------------------------------------------------------------------------
// Private Methods
//--------------------------------------------------------------------------
///
/// Invokes EnableEdit on the controller provided using the document given.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private static bool DispatchEnableEdit
(IDocumentController controller, Document document)
{
if ((document.Dependency != null) && (document.Dependency.Workspace == null))
{
Trace.SafeWrite(
Trace.File,
"Skipping EnableEdit for {0} because dependent Stream is null.",
controller);
return true;
}
return controller.EnableEdit(document);
}
///
/// Invokes Open on the controller provided using the document given.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private static bool DispatchOpen
(IDocumentController controller, Document document)
{
if ((document.Dependency != null) && (document.Dependency.Source == null))
{
Trace.SafeWrite(
Trace.File,
"Skipping Open for {0} because dependent Stream is null.",
controller);
return true;
}
return controller.Open(document);
}
///
/// Invokes Rebind on the controller provided using the document given.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private static bool DispatchRebind
(IDocumentController controller, Document document)
{
if ((document.Dependency != null) && (document.Dependency.Source == null))
{
Trace.SafeWrite(
Trace.File,
"Skipping Rebind for {0} because dependent Stream is null.",
controller);
return true;
}
return controller.Rebind(document);
}
///
/// Invokes SaveAsPreperation on the controller provided using the document
/// given.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private static bool DispatchSaveAsPreperation
(IDocumentController controller, Document document)
{
if ((document.Dependency != null) && (document.Dependency.Destination == null))
{
Trace.SafeWrite(
Trace.File,
"Skipping SaveAsPreperation for {0} because dependent Stream is null.",
controller);
return true;
}
return controller.SaveAsPreperation(document);
}
///
/// Invokes SaveCommit on the controller provided using the document given.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private static bool DispatchSaveCommit
(IDocumentController controller, Document document)
{
if ((document.Dependency != null) && (document.Dependency.Destination == null))
{
Trace.SafeWrite(
Trace.File,
"Skipping SaveCommit for {0} because dependent Stream is null.",
controller);
return true;
}
return controller.SaveCommit(document);
}
///
/// Invokes SavePreperation on the controller provided using the document
/// given.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private static bool DispatchSavePreperation
(IDocumentController controller, Document document)
{
if ((document.Dependency != null) && (document.Dependency.Destination == null))
{
Trace.SafeWrite(
Trace.File,
"Skipping SavePreperation for {0} because dependent Stream is null.",
controller);
return true;
}
return controller.SavePreperation(document);
}
///
/// Invokes the action from the top of the document dependency chain to the
/// bottom, for each provider under it in the chain.
///
///
/// OrderByMostDependent is implement in the ChainOfDependency
/// (not a GoF pattern), it walks the tree of dependencies in this case the
/// most dependent would be first. The Chain of Responsiblity pattern is
/// invoke by the inherited member 'Dispatch' which is called for each
/// dependency.
///
/// The action to perform.
/// The document to perform it on.
private bool OrderByMostDependent(DispatchDelegate action, Document document)
{
return ChainOfDependencies.OrderByMostDependent(
document,
delegate(Document member)
{
return this.Dispatch(delegate(
IDocumentController controller,
Document subject)
{
return action(controller, subject);
},
member);
});
}
///
/// Invokes the action from the bottom of the document dependency chain up
/// to the top, for each provider under it in the chain.
///
///
/// OrderByLeastDependent is implement in the ChainOfDependency
/// (not a GoF pattern), it walks the tree of dependencies in this case the
/// least dependent would be first. The Chain of Responsiblity pattern is
/// invoke by the inherited member 'Dispatch' which is called for each
/// dependency.
///
/// The action to perform.
/// The document to perform it on.
private bool OrderByLeastDependent(DispatchDelegate action, Document document)
{
return ChainOfDependencies.OrderByLeastDependent(
document,
delegate(Document member)
{
return this.Dispatch(delegate(
IDocumentController controller,
Document subject)
{
return action(controller, subject);
},
member);
});
}
///
/// Will throw if the document is null.
///
///
/// The document to validate.
private static void ThrowIfNull(Document document)
{
if (document == null)
{
throw new ArgumentNullException("document");
}
}
#endregion Private Methods
#region Private Delegates
//-------------------------------------------------------------------------
// Private Delegates
//-------------------------------------------------------------------------
///
/// Defines the delegate for actions invoked by DocumentManager.
///
/// The controller to perform the action.
/// The document to perform it on.
/// True if handled by controller.
private delegate bool DispatchDelegate(
IDocumentController controller, Document document);
#endregion Private Delegates
#region Private Fields
//-------------------------------------------------------------------------
// Private Fields
//--------------------------------------------------------------------------
// Fields below simply prevents undesired user experience, they do not
// impact security constraints nor are they used as protection
private static Document _current;
private static DocumentManager _singleton;
private static bool _canSave;
private static bool _isEditEnabled;
private static bool _isModified;
private static List _controllers =
new List();
#endregion Private Fields
}
}
// 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
- RC2CryptoServiceProvider.cs
- LocationSectionRecord.cs
- WebServiceErrorEvent.cs
- WebPartZoneBase.cs
- UInt32Converter.cs
- LightweightCodeGenerator.cs
- WsdlExporter.cs
- EntityTypeEmitter.cs
- Task.cs
- IndentedWriter.cs
- BitmapData.cs
- OleDbPropertySetGuid.cs
- GridViewRowCollection.cs
- SqlFileStream.cs
- ToolStripContainer.cs
- BufferedGraphicsContext.cs
- EmulateRecognizeCompletedEventArgs.cs
- ConfigurationConverterBase.cs
- SamlSerializer.cs
- Rectangle.cs
- AuthenticationException.cs
- FieldNameLookup.cs
- AuthenticationService.cs
- FixedSOMTextRun.cs
- XPathDocumentIterator.cs
- RoutingService.cs
- StreamWriter.cs
- ExpressionEditorAttribute.cs
- SessionParameter.cs
- QueryFunctions.cs
- UnitySerializationHolder.cs
- SqlNode.cs
- SiteMap.cs
- ShaperBuffers.cs
- CompositeFontInfo.cs
- ScriptControl.cs
- JpegBitmapDecoder.cs
- MarkupObject.cs
- NodeCounter.cs
- Debug.cs
- XmlDataSourceView.cs
- XmlDigitalSignatureProcessor.cs
- XmlDictionaryWriter.cs
- XmlDigitalSignatureProcessor.cs
- XmlCountingReader.cs
- PropertyBuilder.cs
- PlainXmlSerializer.cs
- TypeToken.cs
- GeneratedView.cs
- OdbcStatementHandle.cs
- VerificationAttribute.cs
- TaskForm.cs
- ProjectedSlot.cs
- AccessViolationException.cs
- Scripts.cs
- BinaryMethodMessage.cs
- Label.cs
- Attributes.cs
- UnrecognizedPolicyAssertionElement.cs
- OleCmdHelper.cs
- InstanceHandleReference.cs
- ResourceDescriptionAttribute.cs
- Utils.cs
- UntrustedRecipientException.cs
- EntityDataSourceContextDisposingEventArgs.cs
- FrameworkElementFactoryMarkupObject.cs
- XmlILModule.cs
- XmlUtilWriter.cs
- cryptoapiTransform.cs
- NetworkAddressChange.cs
- DbgUtil.cs
- Size.cs
- ItemsChangedEventArgs.cs
- FontNameConverter.cs
- HashCodeCombiner.cs
- NavigationHelper.cs
- OleDbRowUpdatedEvent.cs
- Separator.cs
- ResourceManager.cs
- SystemResources.cs
- SecurityPolicySection.cs
- Vector3D.cs
- TargetControlTypeCache.cs
- UpdateEventArgs.cs
- CustomAttribute.cs
- ISessionStateStore.cs
- TypeInfo.cs
- XmlSecureResolver.cs
- Helper.cs
- SqlEnums.cs
- FacetDescription.cs
- StateChangeEvent.cs
- CompilationSection.cs
- xmlfixedPageInfo.cs
- DeviceContext.cs
- Polygon.cs
- BufferedGraphicsManager.cs
- Pool.cs
- WebPartConnectionsConfigureVerb.cs
- DataTableMapping.cs