ActiveXHost.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ Dotnetfx_Win7_3.5.1 / Dotnetfx_Win7_3.5.1 / 3.5.1 / DEVDIV / depot / DevDiv / releases / Orcas / NetFXw7 / wpf / src / Framework / System / Windows / Interop / ActiveXHost.cs / 1 / ActiveXHost.cs

                            //------------------------------------------------------------------------------ 
// 
//      Copyright (c) Microsoft Corporation.  All rights reserved.
// 
// 
//
// Description: 
//      An ActiveXHost is a System.Windows.FrameworkElement which can 
//      host a windowed ActiveX control.  This class provides a technology
//      bridge between ActiveX controls and Avalon by wrapping ActiveX controls 
//      and exposing them as fully featured avalon elements. It implements both the
//      container interfaces (via aggregation) required to host the ActiveXControl
//      and also derives from HwndHost to support hosting an HWND in the avalon tree.
// 
//      Currently the activex hosting support is limited to windowed controls.
// 
//      Inheritors of this class simply need to concentrate on defining and implementing the 
//      properties/methods/events of the specific ActiveX control they are wrapping, the
//      default properties etc and the code to implement the activation etc. are 
//      encapsulated in the class below.
//
//      The classid of the ActiveX control is specified in the constructor.
// 
//
// History 
//  04/17/05    KusumaV      Created 
//
//----------------------------------------------------------------------------- 

using System;
using System.Collections;
using System.Collections.Specialized; 
using System.ComponentModel;
using System.Diagnostics; 
using System.Reflection; 
using System.Runtime.InteropServices;
using System.Security.Permissions; 
using System.Threading;

using System.Windows;
using System.Windows.Interop; 
using System.Windows.Controls;
using System.Windows.Input; 
using System.Windows.Markup; 
using MS.Internal;
using MS.Internal.Controls; 
using MS.Internal.Utility;
using MS.Win32;
using System.Security;
 
// Since we disable PreSharp warnings in this file, PreSharp warning is unknown to C# compiler.
// We first need to disable warnings about unknown message numbers and unknown pragmas. 
#pragma warning disable 1634, 1691 

namespace System.Windows.Interop 
{
    #region ActiveXHost

    ///  
    ///     An ActiveXHost is a Systew.Windows.FrameworkElement which can
    ///     host an ActiveX control. Currently the support is limited to 
    ///     windowed controls. This class provides a technology bridge 
    ///     between unmanaged ActiveXControls and Avalon framework.
    /// 
    ///     The only reason we expose this class public in ArrowHead without public OM
    ///     is for the WebBrowser control. The WebBrowser class derives from ActiveXHost, and
    ///     we are exposing the WebBrowser class in ArrowHead. This class does not have public
    ///     constructor and OM. It may be enabled in future releases. 
    /// 
    public class ActiveXHost : HwndHost 
    { 
        //-----------------------------------------------------
        // 
        //  Constructors and Finalizers
        //
        //-----------------------------------------------------
 
        #region Constructors and Finalizers
 
        static ActiveXHost() 
        {
            // We use this map to lookup which invalidator method to call 
            // when the Avalon parent's properties change.
            invalidatorMap[UIElement.VisibilityProperty] = new PropertyInvalidator(OnVisibilityInvalidated);
            invalidatorMap[FrameworkElement.IsEnabledProperty] = new PropertyInvalidator(OnIsEnabledInvalidated);
 
            // register for access keys
            EventManager.RegisterClassHandler(typeof(ActiveXHost), AccessKeyManager.AccessKeyPressedEvent, new AccessKeyPressedEventHandler(OnAccessKeyPressed)); 
 
            Control.IsTabStopProperty.OverrideMetadata(typeof(ActiveXHost), new FrameworkPropertyMetadata(true));
 
            FocusableProperty.OverrideMetadata(typeof(ActiveXHost), new FrameworkPropertyMetadata(true));

            EventManager.RegisterClassHandler(typeof(ActiveXHost), Keyboard.GotKeyboardFocusEvent, new KeyboardFocusChangedEventHandler(OnGotFocus));
            EventManager.RegisterClassHandler(typeof(ActiveXHost), Keyboard.LostKeyboardFocusEvent, new KeyboardFocusChangedEventHandler(OnLostFocus)); 
            KeyboardNavigation.TabNavigationProperty.OverrideMetadata(typeof(ActiveXHost), new FrameworkPropertyMetadata(KeyboardNavigationMode.Once));
        } 
 

        /// constructor for ActiveXHost 
        ///
        ///     Critical - calls trusted HwndHost ctor.
        ///                Takes the clsid to instantiate as input.
        ///     NOT TAS. Individual controls ( like WebOC) can become TAS if they justify why. 
        ///
        [SecurityCritical] 
        internal ActiveXHost(Guid clsid, bool fTrusted ) : base( fTrusted ) 
        {
            // Thread.ApartmentState is [Obsolete] 
            #pragma warning disable 0618
            //
            if (Thread.CurrentThread.ApartmentState != ApartmentState.STA)
            { 
                throw new ThreadStateException(SR.Get(SRID.AxRequiresApartmentThread, clsid.ToString()));
            } 
            #pragma warning restore 0618 

            _clsid.Value = clsid; 

            // hookup so we are notified when loading is finished.
            Initialized += new EventHandler(OnInitialized);
        } 

 
        #endregion Constructors and Finalizers 

        //------------------------------------------------------ 
        //
        //  Protected Methods
        //
        //----------------------------------------------------- 

        #region Protected Methods 
 
        #region Framework Related
 
        /// 
        ///     Overriden to push the values of invalidated properties down to our
        ///     ActiveX control.
        ///  
        protected override void OnPropertyChanged(DependencyPropertyChangedEventArgs e)
        { 
            base.OnPropertyChanged(e); 

            if (e.IsAValueChange || e.IsASubPropertyChange) 
            {
                DependencyProperty dp = e.Property;

                // We lookup the property in our invalidatorMap 
                // and call the appropriate method to push
                // down the changed value to the hosted ActiveX control. 
                if (dp != null && invalidatorMap.ContainsKey(dp)) 
                {
                    PropertyInvalidator invalidator = (PropertyInvalidator)invalidatorMap[dp]; 
                    invalidator(this);
                }
            }
        } 

        ///  
        ///     Overriden to create our window and parent it. 
        /// 
        /// 
        ///     Critical - calls methods on critical interface members
        ///
        [SecurityCritical ]
        protected override HandleRef BuildWindowCore(HandleRef hwndParent) 
        {
            this.ParentHandle = hwndParent; 
 
            //BuildWindowCore should only be called if visible. Bug 1236445 tracks this.
            TransitionUpTo(ActiveXHelper.ActiveXState.InPlaceActive); 

            //The above call should have set this interface
            Invariant.Assert(_axOleInPlaceActiveObject != null, "InPlace activation of ActiveX control failed");
 
            if (ControlHandle.Handle == IntPtr.Zero)
            { 
                IntPtr inplaceWindow = IntPtr.Zero; 
                _axOleInPlaceActiveObject.GetWindow(out inplaceWindow);
                AttachWindow(inplaceWindow); 
            }

            return _axWindow;
        } 

        ///  
        ///     Overridden to plug the ActiveX control into Avalon's layout manager. 
        /// 
        ///  
        ///     Critical - accesses ActiveXSite critical property
        ///     Not making TAS - you may be able to spoof content of web-pages if you could position any arbitrary
        ///                      control over a WebOC.
        ///  
        [ SecurityCritical ]
        protected override void OnWindowPositionChanged(Rect bounds) 
        { 
            //Its okay to process this if we the control is not yet created
 
            _boundRect = bounds;

            //These are already transformed to client co-ordinate/device units for high dpi also
            _bounds.left    = (int) bounds.X; 
            _bounds.top     = (int) bounds.Y;
            _bounds.right   = (int) (bounds.Width + bounds.X); 
            _bounds.bottom  = (int) (bounds.Height + bounds.Y); 

            //SetExtent only sets height and width, can call it for perf if X, Y haven't changed 
            //We need to call SetObjectRects instead, which updates X, Y, width and height
            //OnActiveXRectChange calls SetObjectRects
            this.ActiveXSite.OnActiveXRectChange(_bounds);
        } 

        ///  
        ///     Derived classes override this method to actually build the 
        ///     window being hosted.
        ///  
        protected override void DestroyWindowCore(HandleRef hwnd)
        {
        }
 
        /// 
        ///     Overridden to plug the ActiveX control into Avalon's layout manager. 
        ///  
        protected override Size MeasureOverride(Size swConstraint)
        { 
            base.MeasureOverride(swConstraint);

            double newWidth, newHeight;
 
            if (Double.IsPositiveInfinity(swConstraint.Width))
                newWidth = 150; 
            else 
                newWidth = swConstraint.Width;
 
            if (Double.IsPositiveInfinity(swConstraint.Height))
                newHeight = 150;
            else
                newHeight = swConstraint.Height; 

            return new Size(newWidth, newHeight); 
        } 

 
        /// 
        ///     Forward the access key to our hosted ActiveX control
        ///
        protected override void OnAccessKey(AccessKeyEventArgs args) 
        {
            Debug.Assert(args.Key.Length > 0, "got an empty access key"); 
            // 

        } 

        #endregion Framework Related

        #region ActiveX Related 

        protected override void Dispose(bool disposing) 
        { 
            try
            { 
                if ((disposing) && (!_isDisposed))
                {
                    TransitionDownTo(ActiveXHelper.ActiveXState.Passive);
                    _isDisposed = true; 
                }
            } 
            finally 
            {
                //This destroys the parent window, so call base after we have done our processing. 
                base.Dispose(disposing);
            }
        }
 
        // The native ActiveX control QI's for interfaces on it's site to see if
        // it needs to change it's behaviour. Since the AxSite class is generic, 
        // it only implements site interfaces that are generic to all sites. QI's 
        // for any more specific interfaces will fail. This is a problem if anyone
        // wants to support any other interfaces on the site. In order to overcome 
        // this, one needs to extend AxSite and implement any additional interfaces
        // needed.
        //
        // ActiveX wrapper controls that derive from this class should override the 
        // below method and return their own AxSite derived object.
        // 
        // This method is protected by an InheritanceDemand (from HwndSource) and 
        // a LinkDemand because extending a site is strictly an advanced feature for
        // which one needs UnmanagedCode permissions. 
        //

        /// Returns an object that will be set as the site for the native ActiveX control.
        /// Implementors of the site can derive from ActiveXSite class. 
        ///
        /// Critical - calls critical ctor. 
        /// 
        [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.UnmanagedCode)]
        [SecurityCritical] 
        internal virtual ActiveXSite CreateActiveXSite()
        {
            return new ActiveXSite(this);
        } 

        [SecurityCritical] 
        internal virtual object CreateActiveXObject(Guid clsid) 
        {
            return UnsafeNativeMethods.CoCreateInstance(ref clsid, null, NativeMethods.CLSCTX_INPROC_SERVER, ref NativeMethods.IID_IUnknown); 
        }

        /// This will be called when the native ActiveX control has just been created.
        /// Inheritors of this class can override this method to cast the nativeActiveXObject 
        /// parameter to the appropriate interface. They can then cache this interface
        /// value in a member variable. However, they must release this value when 
        /// DetachInterfaces is called (by setting the cached interface variable to null). 
        internal virtual void AttachInterfaces(object nativeActiveXObject)
        { 
        }

        /// See AttachInterfaces for a description of when to override DetachInterfaces.
        internal virtual void DetachInterfaces() 
        {
        } 
 
        /// This will be called when we are ready to start listening to events.
        /// Inheritors can override this method to hook their own connection points. 
        internal virtual void CreateSink()
        {
        }
 
        /// 
        /// This will be called when it is time to stop listening to events. 
        /// This is where inheritors have to disconnect their connection points. 
        /// 
        ///  
        /// Critical: Potentially unsafe. For example, disconnecting the event sink breaks the site-locking
        /// feature of the WebBrowser control.
        /// 
        [SecurityCritical] 
        internal virtual void DetachSink()
        { 
        } 

        ///  
        /// Called whenever the ActiveX state changes. Subclasses can do additional hookup/cleanup depending
        /// on the state transitions
        /// 
        ///  
        /// 
        internal virtual void OnActiveXStateChange(int oldState, int newState) 
        { 
        }
 
        #endregion ActiveX Related

        #endregion Protected Methods
 
        //------------------------------------------------------
        // 
        //  Protected Properties 
        //
        //------------------------------------------------------ 

        #region Protected Properties

        protected bool IsDisposed 
        {
            get { return _isDisposed; } 
        } 

        #endregion Protected Properties 

        //-----------------------------------------------------
        //
        //  Internal Methods 
        //
        //------------------------------------------------------ 
 
        #region Internal Methods
 
        #region ActiveX Related

        /// This method needs to be called by the user of ActiveXHost for each
        /// hosted ActiveX control that has a mnemonic bound to it 
        internal void RegisterAccessKey(char key)
        { 
            AccessKeyManager.Register(key.ToString(), this); 
        }
 
        ///
        /// Critical - exposes critical _axSite member.
        /// LinkDemand added, since without it, this property would make the LinkDemand on CreateActiveXSite meaningless.
        /// 
        internal ActiveXSite ActiveXSite
        { 
            [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.UnmanagedCode)] 
            [SecurityCritical]
            get 
            {
                if (_axSite == null)
                {
                    _axSite = CreateActiveXSite(); 
                }
                return _axSite; 
            } 
        }
 
        ///
        /// Critical - exposes critical _axContainer member.
        ///
        internal ActiveXContainer Container 
        {
            [SecurityCritical] 
            get 
            {
                if (_axContainer == null) 
                {
                    _axContainer = new ActiveXContainer(this);
                }
                return _axContainer; 
            }
        } 
 
        internal ActiveXHelper.ActiveXState ActiveXState
        { 
            get
            {
                return _axState;
            } 
            set
            { 
                _axState = value; 
            }
        } 

        internal bool GetAxHostState(int mask)
        {
            return _axHostState[mask]; 
        }
 
        internal void SetAxHostState(int mask, bool value) 
        {
            _axHostState[mask] = value; 
        }

        internal void TransitionUpTo(ActiveXHelper.ActiveXState state)
        { 
            if (!this.GetAxHostState(ActiveXHelper.inTransition))
            { 
                this.SetAxHostState(ActiveXHelper.inTransition, true); 

                try 
                {
                    ActiveXHelper.ActiveXState oldState;

                    while (state > this.ActiveXState) 
                    {
                        oldState = this.ActiveXState; 
 
                        switch (this.ActiveXState)
                        { 
                            case ActiveXHelper.ActiveXState.Passive:
                                TransitionFromPassiveToLoaded();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded; 
                                break;
                            case ActiveXHelper.ActiveXState.Loaded: 
                                TransitionFromLoadedToRunning(); 
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Running; 
                                break;
                            case ActiveXHelper.ActiveXState.Running:
                                TransitionFromRunningToInPlaceActive();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Failed transition"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive;
                                break; 
                            case ActiveXHelper.ActiveXState.InPlaceActive: 
                                TransitionFromInPlaceActiveToUIActive();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.UIActive, "Failed transition"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.UIActive;
                                break;
                            default:
                                Debug.Fail("bad state"); 
                                this.ActiveXState = this.ActiveXState + 1;  // To exit the loop
                                break; 
                        } 

                        OnActiveXStateChange((int)oldState, (int)this.ActiveXState); 
                    }
                }
                finally
                { 
                    this.SetAxHostState(ActiveXHelper.inTransition, false);
                } 
            } 
        }
 
        internal void TransitionDownTo(ActiveXHelper.ActiveXState state)
        {
            if (!this.GetAxHostState(ActiveXHelper.inTransition))
            { 
                this.SetAxHostState(ActiveXHelper.inTransition, true);
 
                try 
                {
                    ActiveXHelper.ActiveXState oldState; 

                    while (state < this.ActiveXState)
                    {
                        oldState = this.ActiveXState; 

                        switch (this.ActiveXState) 
                        { 
                            case ActiveXHelper.ActiveXState.Open:
                                Debug.Fail("how did we ever get into the open state?"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.UIActive;
                                break;
                            case ActiveXHelper.ActiveXState.UIActive:
                                TransitionFromUIActiveToInPlaceActive(); 
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive; 
                                break; 
                            case ActiveXHelper.ActiveXState.InPlaceActive:
                                TransitionFromInPlaceActiveToRunning(); 
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Running;
                                break;
                            case ActiveXHelper.ActiveXState.Running: 
                                TransitionFromRunningToLoaded();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Failed transition"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded; 
                                break;
                            case ActiveXHelper.ActiveXState.Loaded: 
                                TransitionFromLoadedToPassive();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Passive, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Passive;
                                break; 
                            default:
                                Debug.Fail("bad state"); 
                                this.ActiveXState = this.ActiveXState - 1;  // To exit the loop 
                                break;
                        } 

                        OnActiveXStateChange((int)oldState, (int)this.ActiveXState);
                    }
                } 
                finally
                { 
                    this.SetAxHostState(ActiveXHelper.inTransition, false); 
                }
            } 
        }

        ///
        ///     Critical - runs arbitrary code on critical _axOleObject member. 
        ///
        [SecurityCritical] 
        internal bool DoVerb(int verb) 
        {
            int hr = _axOleObject.DoVerb(verb, 
                                         IntPtr.Zero,
                                         this.ActiveXSite,
                                         0,
                                         this.ParentHandle.Handle, 
                                         _bounds);
 
            Debug.Assert(hr == NativeMethods.S_OK, String.Format("DoVerb call failed for verb 0x{0:X}", verb)); 
            return hr == NativeMethods.S_OK;
        } 

        ///
        ///     Critical - Calls setParent, accesses _axWindow.
        /// 
        [SecurityCritical]
        internal void AttachWindow(IntPtr hwnd) 
        { 
            if (_axWindow.Handle == hwnd)
                return; 

            //

 

            _axWindow = new HandleRef(this, hwnd); 
 
            if (this.ParentHandle.Handle != IntPtr.Zero)
            { 
                UnsafeNativeMethods.SetParent(_axWindow, this.ParentHandle);
            }
        }
 
        ///
        ///     Critical - calls ActiveXSite.StartEvents - critical code. 
        /// 
        [ SecurityCritical ]
        private void StartEvents() 
        {
            if (!this.GetAxHostState(ActiveXHelper.sinkAttached))
            {
                this.SetAxHostState(ActiveXHelper.sinkAttached, true); 
                CreateSink();
            } 
            this.ActiveXSite.StartEvents(); 
        }
 
        ///
        ///     Critical - calls ActiveXSite.StopEvents - critical code.
        ///     NOT TAS: if you can stop listening to events - you could
        ///              potentially turn off a mitigation. On the WebOC this could 
        ///              stop site-locking mitigation.
        /// 
        [ SecurityCritical ] 
        private void StopEvents()
        { 
            if (this.GetAxHostState(ActiveXHelper.sinkAttached))
            {
                this.SetAxHostState(ActiveXHelper.sinkAttached, false);
                DetachSink(); 
            }
            this.ActiveXSite.StopEvents(); 
        } 

        /// 
        /// Critical - Calls critical code ( CoCreateInstance) calls critical interface members, _axInstance
        /// TreatAsSafe - although this method instantiates the control.
        ///               considered safe as the parameter that controls what to instantiate is critical for set.
        ///               and set only via the critical CTOR. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromPassiveToLoaded() 
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Passive, "Wrong start state to transition from"); 
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Passive)
            {
                //
                // First, create the ActiveX control 
                Debug.Assert(_axInstance == null, "_axInstance must be null");
 
                _axInstance = CreateActiveXObject(_clsid.Value); 
                Debug.Assert(_axInstance != null, "w/o an exception being thrown we must have an object...");
 
                //
                // We are now Loaded!
                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded;
 
                //
                // Lets give them a chance to cast the ActiveX object 
                // to the appropriate interfaces. 
                this.AttachInterfacesInternal();
            } 
        }

        ///
        /// Critical - accesses critical interface members, _axInstance 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromLoadedToPassive()
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Loaded) 
            {
                // 
                // Need to make sure that we don't handle any PropertyChanged 
                // notifications at this point.
                //this.NoComponentChangeEvents++; 
                try
                {
                    //
                    // Release the _axInstance 
                    if (_axInstance != null)
                    { 
                        // 
                        // Lets first get the cached interface pointers of _axInstance released.
                        this.DetachInterfacesInternal(); 

                        Marshal.FinalReleaseComObject(_axInstance);
                        _axInstance = null;
                    } 
                }
                finally 
                { 
                    //
                } 

                //
                // We are now Passive!
                this.ActiveXState = ActiveXHelper.ActiveXState.Passive; 
            }
        } 
 
        ///
        /// Critical - calls critical code - SetClientSite. 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical.
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromLoadedToRunning() 
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Loaded) 
            {
                //
                // See if the ActiveX control returns OLEMISC_SETCLIENTSITEFIRST
                int bits = 0; 
                int hr = _axOleObject.GetMiscStatus(NativeMethods.DVASPECT_CONTENT, out bits);
                if (NativeMethods.Succeeded(hr) && ((bits & NativeMethods.OLEMISC_SETCLIENTSITEFIRST) != 0)) 
                { 
                    //
                    // Simply setting the site to the ActiveX control should activate it. 
                    // And this will take us to the Running state.
                    _axOleObject.SetClientSite(this.ActiveXSite);
                }
 
                StartEvents();
 
                // 
                // We are now Running!
                this.ActiveXState = ActiveXHelper.ActiveXState.Running; 
            }
        }

        /// 
        /// Critical - accesses critical code, _axOleOlebject, StopEvents
        /// TreatAsSafe - state transitions considered safe. 
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromRunningToLoaded()
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Wrong start state to transition from"); 
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Running)
            { 
                StopEvents(); 

                // 
                // Inform the ActiveX control that it's been un-sited.
                _axOleObject.SetClientSite(null);

                // 
                // We are now Loaded!
                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded; 
            } 
        }
 
        ///
        /// Critical - calls critical code - DoVerb.
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromRunningToInPlaceActive()
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Running)
            {
                try 
                {
                    DoVerb(NativeMethods.OLEIVERB_INPLACEACTIVATE); 
                } 
                catch (Exception e)
                { 
                    if(CriticalExceptions.IsCriticalException(e))
                    {
                        throw;
                    } 
                    else
                    { 
                        throw new TargetInvocationException(SR.Get(SRID.AXNohWnd, GetType().Name), e); 
                    }
                } 

                //
                // We are now InPlaceActive!
                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive; 
            }
        } 
 
        ///
        /// Critical - calls critical code - InPlaceDeactivate. 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical.
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromInPlaceActiveToRunning() 
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive) 
            {
                //
                // InPlaceDeactivate.
                _axOleInPlaceObject.InPlaceDeactivate(); 

                // 
                // We are now Running! 
                this.ActiveXState = ActiveXHelper.ActiveXState.Running;
            } 
        }

        ///
        /// Critical - calls critical code - DoVerb. 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromInPlaceActiveToUIActive()
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive) 
            {
                DoVerb(NativeMethods.OLEIVERB_UIACTIVATE); 
 
                //
                // We are now UIActive! 
                this.ActiveXState = ActiveXHelper.ActiveXState.UIActive;
            }
        }
 
        ///
        /// Critical - accesses critical interface members, _axOleInPlaceObject 
        /// TreatAsSafe - state transitions considered safe. 
        ///                     Instantiating a control is considered critical.
        ///                     However once instantiated, state transitions considered ok. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromUIActiveToInPlaceActive()
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.UIActive, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.UIActive) 
            { 
                int hr = _axOleInPlaceObject.UIDeactivate();
                Debug.Assert(NativeMethods.Succeeded(hr), "Failed in IOleInPlaceObject.UiDeactivate"); 

                //
                // We are now InPlaceActive!
                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive; 
            }
        } 
 
        #endregion ActiveX Related
 
        #endregion Internal Methods

        //-----------------------------------------------------
        // 
        //  Internal Properties
        // 
        //----------------------------------------------------- 

        #region Internal Properties 

        #region Framework Related

        ///  
        ///     The DependencyProperty for the TabIndex property.
        ///     Flags:              Can be used in style rules 
        ///     Default Value:      1 
        /// 
        internal static readonly DependencyProperty TabIndexProperty 
            = Control.TabIndexProperty.AddOwner(typeof(ActiveXHost));

        /// 
        ///     TabIndex property change the order of Tab navigation between Controls. 
        ///     Control with lower TabIndex will get focus before the Control with higher index
        ///  
        internal int TabIndex 
        {
            get { return (int) GetValue(TabIndexProperty); } 
            set { SetValue(TabIndexProperty, value); }
        }

        /// 
        ///     Critical - accesses _hwndParent critical member.
        /// 
        internal HandleRef ParentHandle 
        {
            [ SecurityCritical ] 
            get { return _hwndParent; }

            [ SecurityCritical ]
            set { _hwndParent = value; } 
        }
 
        // This returns a COMRECT. 
        internal NativeMethods.COMRECT Bounds
        { 
            get { return _bounds; }
            //How do we notify Avalon tree/layout that the control needs a new size?
            set { _bounds = value; }
        } 

        // This returns a Rect. 
        internal Rect BoundRect 
        {
            get { return _boundRect; } 
        }

        #endregion Framework Related
 
        #region ActiveX Related
 
        ///  
        /// Returns the hosted ActiveX control's handle
        ///  
        ///
        ///     Critical - returns critical _axWindow member
        ///
        internal HandleRef ControlHandle 
        {
            [ SecurityCritical ] 
            get { return _axWindow; } 
        }
 
        ///
        ///Returns the native webbrowser object that this control wraps. Needs FullTrust to access.
        /// Internally we will access the private field directly for perf reasons, no security checks
        /// 
        ///
        ///     Critical - returns critical Instance member. 
        /// 
        internal object ActiveXInstance
        { 
            [ SecurityCritical ]
            get
            {
                return _axInstance; 
            }
        } 
 

        /// 
        ///     Critical - returns critical Instance member.
        ///
        internal UnsafeNativeMethods.IOleInPlaceObject ActiveXInPlaceObject
        { 
            [ SecurityCritical ]
            get 
            { 
                return _axOleInPlaceObject;
            } 
        }

        ///
        ///     Critical - returns critical Instance member. 
        ///
        internal UnsafeNativeMethods.IOleInPlaceActiveObject ActiveXInPlaceActiveObject 
        { 
            [SecurityCritical]
            get 
            {
                return _axOleInPlaceActiveObject;
            }
        } 

        #endregion ActiveXRelated 
 
        #endregion Internal Properties
 
        //-----------------------------------------------------
        //
        //  Private Methods
        // 
        //------------------------------------------------------
 
        #region Private Methods 

        #region Framework Methods 

        private void OnInitialized(object sender, EventArgs e)
        {
            // 

 
 

 


            this.Initialized -= new EventHandler(this.OnInitialized);
 
            //Cannot inplace activate yet, since BuildWindowCore is not called yet
            //and we need that for getting the parent handle to pass on to the control. 
        } 

        private static void OnIsEnabledInvalidated(ActiveXHost axHost) 
        {
            //

 

 
        } 

        private static void OnVisibilityInvalidated(ActiveXHost axHost) 
        {
            if (axHost != null)
            {
                switch (axHost.Visibility) 
                {
                    case Visibility.Visible: 
                        // 
                        break;
                    case Visibility.Collapsed: 
                        //
                        break;
                    case Visibility.Hidden:
                        // 

 
 
                        break;
                } 
            }
        }

        ///     This event handler forwards focus events to the hosted ActiveX control 
        private static void OnGotFocus(object sender, KeyboardFocusChangedEventArgs e)
        { 
            ActiveXHost axhost = sender as ActiveXHost; 

            if (axhost != null) 
            {
                Invariant.Assert(axhost.ActiveXState >= ActiveXHelper.ActiveXState.InPlaceActive, "Should at least be InPlaceActive when getting focus");

                if (axhost.ActiveXState < ActiveXHelper.ActiveXState.UIActive) 
                {
                    axhost.TransitionUpTo(ActiveXHelper.ActiveXState.UIActive); 
                } 
            }
        } 

        ///     This event handler forwards focus events to the hosted WF controls
        private static void OnLostFocus(object sender, KeyboardFocusChangedEventArgs e)
        { 
            ActiveXHost axhost = sender as ActiveXHost;
 
            if (axhost != null) 
            {
                // If the focus goes from our control window to one of the child windows, 
                // we should not deactivate.
                //

                Invariant.Assert(axhost.ActiveXState >= ActiveXHelper.ActiveXState.UIActive, "Should at least be UIActive when losing focus"); 

                bool uiDeactivate = !axhost.IsKeyboardFocusWithin; 
 
                if (uiDeactivate)
                { 
                    axhost.TransitionDownTo(ActiveXHelper.ActiveXState.InPlaceActive);
                }
            }
        } 

        private static void OnAccessKeyPressed(object sender, AccessKeyPressedEventArgs args) 
        { 
            if (!args.Handled && args.Scope == null && args.Target == null)
            { 
                args.Target = (UIElement)sender;
            }
        }
 
        /*
                private void GetMnemonicList(SWF.Control control, ArrayList mnemonicList) { 
 
                    // Get the mnemonic for our control
                    // 
                    char mnemonic = HostUtils.GetMnemonic(control.Text, true);
                    if (mnemonic != 0)
                    {
                        mnemonicList.Add(mnemonic); 
                    }
 
                    // And recurse for our children, currently we only support one activex control 
                    //
                    if (HostedControl != null) GetMnemonicList(HostedControl, mnemonicList); 
                }
        */

        #endregion Framework Methods 

        #region ActiveX Related 
 
        ///
        ///     Critical -  accesses critical interface pointers. 
        ///
        [ SecurityCritical ]
        private void AttachInterfacesInternal()
        { 
            Debug.Assert(_axInstance != null, "The native control is null");
            _axOleObject = (UnsafeNativeMethods.IOleObject)_axInstance; 
            _axOleInPlaceObject = (UnsafeNativeMethods.IOleInPlaceObject)_axInstance; 
            _axOleInPlaceActiveObject = (UnsafeNativeMethods.IOleInPlaceActiveObject)_axInstance;
            // 
            // Lets give the inheriting classes a chance to cast
            // the ActiveX object to the appropriate interfaces.
            AttachInterfaces(_axInstance);
        } 

        /// 
        ///     Critical - accesses critical interface members. 
        ///     TreatAsSafe - clearing the interfaces is ok.
        /// 
        [ SecurityCritical, SecurityTreatAsSafe ]
        private void DetachInterfacesInternal()
        {
            _axOleObject = null; 
            _axOleInPlaceObject = null;
            _axOleInPlaceActiveObject = null; 
            // 
            // Lets give the inheriting classes a chance to release
            // their cached interfaces of the ActiveX object. 
            DetachInterfaces();
        }

        /// 
        ///     Critical - calls calls critical interface members.
        /// 
        [ SecurityCritical ] 
        private NativeMethods.SIZE SetExtent(int width, int height)
        { 
            NativeMethods.SIZE sz = new NativeMethods.SIZE();
            sz.cx = width;
            sz.cy = height;
 
            bool resetExtents = false;
            try 
            { 
                _axOleObject.SetExtent(NativeMethods.DVASPECT_CONTENT, sz);
            } 
            catch (COMException)
            {
                resetExtents = true;
            } 
            if (resetExtents)
            { 
                _axOleObject.GetExtent(NativeMethods.DVASPECT_CONTENT, sz); 
                try
                { 
                    _axOleObject.SetExtent(NativeMethods.DVASPECT_CONTENT, sz);
                }
                catch (COMException e)
                { 
                    Debug.Fail(e.ToString());
                } 
            } 
            return GetExtent();
        } 

        ///
        ///     Critical - accesses critical interface member _axOleObject
        ///     TreatAsSafe - getting the size of the control is considered ok. 
        ///
        [ SecurityCritical, SecurityTreatAsSafe ] 
        private NativeMethods.SIZE GetExtent() 
        {
            NativeMethods.SIZE sz = new NativeMethods.SIZE(); 
            _axOleObject.GetExtent(NativeMethods.DVASPECT_CONTENT, sz);
            return sz;
        }
 
        #endregion ActiveX Related
 
        #endregion Private Methods 

 
        //-----------------------------------------------------
        //
        //  Private Properties
        // 
        //------------------------------------------------------
 
        #region Private Properties 

        #endregion Private Properties 

        //------------------------------------------------------
        //
        //  Private Fields 
        //
        //----------------------------------------------------- 
 
        #region Private Fields
 
        #region Framework Related

        private static Hashtable invalidatorMap = new Hashtable();
 
        private delegate void PropertyInvalidator(ActiveXHost axhost);
 
        private NativeMethods.COMRECT _bounds    = new NativeMethods.COMRECT(0, 0, 0, 0); 
        private Rect             _boundRect      = new Rect(0, 0, 0, 0);
 
        private Size             _cachedSize     = Size.Empty;
        ///
        ///     Critical - _hwndParent considered critical.
        /// 
        [SecurityCritical ]
        private HandleRef        _hwndParent; 
        private bool             _isDisposed; 

        #endregion Framework Related 

        #region ActiveX Related

        /// 
        ///     Critical - _clsId controls what code to run and instantiate.
        /// 
        private SecurityCriticalDataForSet    _clsid; 

        /// 
        ///     Critical - hwnd of control
        ///
        [ SecurityCritical ]
        private HandleRef                   _axWindow; 
        private BitVector32                 _axHostState    = new BitVector32();
        private ActiveXHelper.ActiveXState  _axState        = ActiveXHelper.ActiveXState.Passive; 
 
        ///
        ///     Critical - ActiveXSite interfaces of control 
        ///
        [ SecurityCritical ]
        private ActiveXSite                 _axSite;
 
        ///
        ///     Critical - ActiveXContainer of control 
        /// 
        [ SecurityCritical ]
        private ActiveXContainer            _axContainer; 

        ///
        ///     Critical - all methods on this Interface are critical
        /// 
        [SecurityCritical]
        private object                      _axInstance; 
 
        // Pointers to the ActiveX object: Interface pointers are cached for perf.
        /// 
        ///     Critical - all methods on this Interface are critical
        ///
        [SecurityCritical]
        private UnsafeNativeMethods.IOleObject              _axOleObject; 

        /// 
        ///     Critical - all methods on this Interface are critical 
        ///
        [SecurityCritical] 
        private UnsafeNativeMethods.IOleInPlaceObject       _axOleInPlaceObject;

        ///
        ///     Critical - all methods on this Interface are critical 
        ///
        [SecurityCritical] 
        private UnsafeNativeMethods.IOleInPlaceActiveObject _axOleInPlaceActiveObject; 

        #endregion ActiveX Related 


        #endregion Private Fields
    } 
    #endregion ActiveXHost
} 

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
//------------------------------------------------------------------------------ 
// 
//      Copyright (c) Microsoft Corporation.  All rights reserved.
// 
// 
//
// Description: 
//      An ActiveXHost is a System.Windows.FrameworkElement which can 
//      host a windowed ActiveX control.  This class provides a technology
//      bridge between ActiveX controls and Avalon by wrapping ActiveX controls 
//      and exposing them as fully featured avalon elements. It implements both the
//      container interfaces (via aggregation) required to host the ActiveXControl
//      and also derives from HwndHost to support hosting an HWND in the avalon tree.
// 
//      Currently the activex hosting support is limited to windowed controls.
// 
//      Inheritors of this class simply need to concentrate on defining and implementing the 
//      properties/methods/events of the specific ActiveX control they are wrapping, the
//      default properties etc and the code to implement the activation etc. are 
//      encapsulated in the class below.
//
//      The classid of the ActiveX control is specified in the constructor.
// 
//
// History 
//  04/17/05    KusumaV      Created 
//
//----------------------------------------------------------------------------- 

using System;
using System.Collections;
using System.Collections.Specialized; 
using System.ComponentModel;
using System.Diagnostics; 
using System.Reflection; 
using System.Runtime.InteropServices;
using System.Security.Permissions; 
using System.Threading;

using System.Windows;
using System.Windows.Interop; 
using System.Windows.Controls;
using System.Windows.Input; 
using System.Windows.Markup; 
using MS.Internal;
using MS.Internal.Controls; 
using MS.Internal.Utility;
using MS.Win32;
using System.Security;
 
// Since we disable PreSharp warnings in this file, PreSharp warning is unknown to C# compiler.
// We first need to disable warnings about unknown message numbers and unknown pragmas. 
#pragma warning disable 1634, 1691 

namespace System.Windows.Interop 
{
    #region ActiveXHost

    ///  
    ///     An ActiveXHost is a Systew.Windows.FrameworkElement which can
    ///     host an ActiveX control. Currently the support is limited to 
    ///     windowed controls. This class provides a technology bridge 
    ///     between unmanaged ActiveXControls and Avalon framework.
    /// 
    ///     The only reason we expose this class public in ArrowHead without public OM
    ///     is for the WebBrowser control. The WebBrowser class derives from ActiveXHost, and
    ///     we are exposing the WebBrowser class in ArrowHead. This class does not have public
    ///     constructor and OM. It may be enabled in future releases. 
    /// 
    public class ActiveXHost : HwndHost 
    { 
        //-----------------------------------------------------
        // 
        //  Constructors and Finalizers
        //
        //-----------------------------------------------------
 
        #region Constructors and Finalizers
 
        static ActiveXHost() 
        {
            // We use this map to lookup which invalidator method to call 
            // when the Avalon parent's properties change.
            invalidatorMap[UIElement.VisibilityProperty] = new PropertyInvalidator(OnVisibilityInvalidated);
            invalidatorMap[FrameworkElement.IsEnabledProperty] = new PropertyInvalidator(OnIsEnabledInvalidated);
 
            // register for access keys
            EventManager.RegisterClassHandler(typeof(ActiveXHost), AccessKeyManager.AccessKeyPressedEvent, new AccessKeyPressedEventHandler(OnAccessKeyPressed)); 
 
            Control.IsTabStopProperty.OverrideMetadata(typeof(ActiveXHost), new FrameworkPropertyMetadata(true));
 
            FocusableProperty.OverrideMetadata(typeof(ActiveXHost), new FrameworkPropertyMetadata(true));

            EventManager.RegisterClassHandler(typeof(ActiveXHost), Keyboard.GotKeyboardFocusEvent, new KeyboardFocusChangedEventHandler(OnGotFocus));
            EventManager.RegisterClassHandler(typeof(ActiveXHost), Keyboard.LostKeyboardFocusEvent, new KeyboardFocusChangedEventHandler(OnLostFocus)); 
            KeyboardNavigation.TabNavigationProperty.OverrideMetadata(typeof(ActiveXHost), new FrameworkPropertyMetadata(KeyboardNavigationMode.Once));
        } 
 

        /// constructor for ActiveXHost 
        ///
        ///     Critical - calls trusted HwndHost ctor.
        ///                Takes the clsid to instantiate as input.
        ///     NOT TAS. Individual controls ( like WebOC) can become TAS if they justify why. 
        ///
        [SecurityCritical] 
        internal ActiveXHost(Guid clsid, bool fTrusted ) : base( fTrusted ) 
        {
            // Thread.ApartmentState is [Obsolete] 
            #pragma warning disable 0618
            //
            if (Thread.CurrentThread.ApartmentState != ApartmentState.STA)
            { 
                throw new ThreadStateException(SR.Get(SRID.AxRequiresApartmentThread, clsid.ToString()));
            } 
            #pragma warning restore 0618 

            _clsid.Value = clsid; 

            // hookup so we are notified when loading is finished.
            Initialized += new EventHandler(OnInitialized);
        } 

 
        #endregion Constructors and Finalizers 

        //------------------------------------------------------ 
        //
        //  Protected Methods
        //
        //----------------------------------------------------- 

        #region Protected Methods 
 
        #region Framework Related
 
        /// 
        ///     Overriden to push the values of invalidated properties down to our
        ///     ActiveX control.
        ///  
        protected override void OnPropertyChanged(DependencyPropertyChangedEventArgs e)
        { 
            base.OnPropertyChanged(e); 

            if (e.IsAValueChange || e.IsASubPropertyChange) 
            {
                DependencyProperty dp = e.Property;

                // We lookup the property in our invalidatorMap 
                // and call the appropriate method to push
                // down the changed value to the hosted ActiveX control. 
                if (dp != null && invalidatorMap.ContainsKey(dp)) 
                {
                    PropertyInvalidator invalidator = (PropertyInvalidator)invalidatorMap[dp]; 
                    invalidator(this);
                }
            }
        } 

        ///  
        ///     Overriden to create our window and parent it. 
        /// 
        /// 
        ///     Critical - calls methods on critical interface members
        ///
        [SecurityCritical ]
        protected override HandleRef BuildWindowCore(HandleRef hwndParent) 
        {
            this.ParentHandle = hwndParent; 
 
            //BuildWindowCore should only be called if visible. Bug 1236445 tracks this.
            TransitionUpTo(ActiveXHelper.ActiveXState.InPlaceActive); 

            //The above call should have set this interface
            Invariant.Assert(_axOleInPlaceActiveObject != null, "InPlace activation of ActiveX control failed");
 
            if (ControlHandle.Handle == IntPtr.Zero)
            { 
                IntPtr inplaceWindow = IntPtr.Zero; 
                _axOleInPlaceActiveObject.GetWindow(out inplaceWindow);
                AttachWindow(inplaceWindow); 
            }

            return _axWindow;
        } 

        ///  
        ///     Overridden to plug the ActiveX control into Avalon's layout manager. 
        /// 
        ///  
        ///     Critical - accesses ActiveXSite critical property
        ///     Not making TAS - you may be able to spoof content of web-pages if you could position any arbitrary
        ///                      control over a WebOC.
        ///  
        [ SecurityCritical ]
        protected override void OnWindowPositionChanged(Rect bounds) 
        { 
            //Its okay to process this if we the control is not yet created
 
            _boundRect = bounds;

            //These are already transformed to client co-ordinate/device units for high dpi also
            _bounds.left    = (int) bounds.X; 
            _bounds.top     = (int) bounds.Y;
            _bounds.right   = (int) (bounds.Width + bounds.X); 
            _bounds.bottom  = (int) (bounds.Height + bounds.Y); 

            //SetExtent only sets height and width, can call it for perf if X, Y haven't changed 
            //We need to call SetObjectRects instead, which updates X, Y, width and height
            //OnActiveXRectChange calls SetObjectRects
            this.ActiveXSite.OnActiveXRectChange(_bounds);
        } 

        ///  
        ///     Derived classes override this method to actually build the 
        ///     window being hosted.
        ///  
        protected override void DestroyWindowCore(HandleRef hwnd)
        {
        }
 
        /// 
        ///     Overridden to plug the ActiveX control into Avalon's layout manager. 
        ///  
        protected override Size MeasureOverride(Size swConstraint)
        { 
            base.MeasureOverride(swConstraint);

            double newWidth, newHeight;
 
            if (Double.IsPositiveInfinity(swConstraint.Width))
                newWidth = 150; 
            else 
                newWidth = swConstraint.Width;
 
            if (Double.IsPositiveInfinity(swConstraint.Height))
                newHeight = 150;
            else
                newHeight = swConstraint.Height; 

            return new Size(newWidth, newHeight); 
        } 

 
        /// 
        ///     Forward the access key to our hosted ActiveX control
        ///
        protected override void OnAccessKey(AccessKeyEventArgs args) 
        {
            Debug.Assert(args.Key.Length > 0, "got an empty access key"); 
            // 

        } 

        #endregion Framework Related

        #region ActiveX Related 

        protected override void Dispose(bool disposing) 
        { 
            try
            { 
                if ((disposing) && (!_isDisposed))
                {
                    TransitionDownTo(ActiveXHelper.ActiveXState.Passive);
                    _isDisposed = true; 
                }
            } 
            finally 
            {
                //This destroys the parent window, so call base after we have done our processing. 
                base.Dispose(disposing);
            }
        }
 
        // The native ActiveX control QI's for interfaces on it's site to see if
        // it needs to change it's behaviour. Since the AxSite class is generic, 
        // it only implements site interfaces that are generic to all sites. QI's 
        // for any more specific interfaces will fail. This is a problem if anyone
        // wants to support any other interfaces on the site. In order to overcome 
        // this, one needs to extend AxSite and implement any additional interfaces
        // needed.
        //
        // ActiveX wrapper controls that derive from this class should override the 
        // below method and return their own AxSite derived object.
        // 
        // This method is protected by an InheritanceDemand (from HwndSource) and 
        // a LinkDemand because extending a site is strictly an advanced feature for
        // which one needs UnmanagedCode permissions. 
        //

        /// Returns an object that will be set as the site for the native ActiveX control.
        /// Implementors of the site can derive from ActiveXSite class. 
        ///
        /// Critical - calls critical ctor. 
        /// 
        [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.UnmanagedCode)]
        [SecurityCritical] 
        internal virtual ActiveXSite CreateActiveXSite()
        {
            return new ActiveXSite(this);
        } 

        [SecurityCritical] 
        internal virtual object CreateActiveXObject(Guid clsid) 
        {
            return UnsafeNativeMethods.CoCreateInstance(ref clsid, null, NativeMethods.CLSCTX_INPROC_SERVER, ref NativeMethods.IID_IUnknown); 
        }

        /// This will be called when the native ActiveX control has just been created.
        /// Inheritors of this class can override this method to cast the nativeActiveXObject 
        /// parameter to the appropriate interface. They can then cache this interface
        /// value in a member variable. However, they must release this value when 
        /// DetachInterfaces is called (by setting the cached interface variable to null). 
        internal virtual void AttachInterfaces(object nativeActiveXObject)
        { 
        }

        /// See AttachInterfaces for a description of when to override DetachInterfaces.
        internal virtual void DetachInterfaces() 
        {
        } 
 
        /// This will be called when we are ready to start listening to events.
        /// Inheritors can override this method to hook their own connection points. 
        internal virtual void CreateSink()
        {
        }
 
        /// 
        /// This will be called when it is time to stop listening to events. 
        /// This is where inheritors have to disconnect their connection points. 
        /// 
        ///  
        /// Critical: Potentially unsafe. For example, disconnecting the event sink breaks the site-locking
        /// feature of the WebBrowser control.
        /// 
        [SecurityCritical] 
        internal virtual void DetachSink()
        { 
        } 

        ///  
        /// Called whenever the ActiveX state changes. Subclasses can do additional hookup/cleanup depending
        /// on the state transitions
        /// 
        ///  
        /// 
        internal virtual void OnActiveXStateChange(int oldState, int newState) 
        { 
        }
 
        #endregion ActiveX Related

        #endregion Protected Methods
 
        //------------------------------------------------------
        // 
        //  Protected Properties 
        //
        //------------------------------------------------------ 

        #region Protected Properties

        protected bool IsDisposed 
        {
            get { return _isDisposed; } 
        } 

        #endregion Protected Properties 

        //-----------------------------------------------------
        //
        //  Internal Methods 
        //
        //------------------------------------------------------ 
 
        #region Internal Methods
 
        #region ActiveX Related

        /// This method needs to be called by the user of ActiveXHost for each
        /// hosted ActiveX control that has a mnemonic bound to it 
        internal void RegisterAccessKey(char key)
        { 
            AccessKeyManager.Register(key.ToString(), this); 
        }
 
        ///
        /// Critical - exposes critical _axSite member.
        /// LinkDemand added, since without it, this property would make the LinkDemand on CreateActiveXSite meaningless.
        /// 
        internal ActiveXSite ActiveXSite
        { 
            [SecurityPermission(SecurityAction.LinkDemand, Flags=SecurityPermissionFlag.UnmanagedCode)] 
            [SecurityCritical]
            get 
            {
                if (_axSite == null)
                {
                    _axSite = CreateActiveXSite(); 
                }
                return _axSite; 
            } 
        }
 
        ///
        /// Critical - exposes critical _axContainer member.
        ///
        internal ActiveXContainer Container 
        {
            [SecurityCritical] 
            get 
            {
                if (_axContainer == null) 
                {
                    _axContainer = new ActiveXContainer(this);
                }
                return _axContainer; 
            }
        } 
 
        internal ActiveXHelper.ActiveXState ActiveXState
        { 
            get
            {
                return _axState;
            } 
            set
            { 
                _axState = value; 
            }
        } 

        internal bool GetAxHostState(int mask)
        {
            return _axHostState[mask]; 
        }
 
        internal void SetAxHostState(int mask, bool value) 
        {
            _axHostState[mask] = value; 
        }

        internal void TransitionUpTo(ActiveXHelper.ActiveXState state)
        { 
            if (!this.GetAxHostState(ActiveXHelper.inTransition))
            { 
                this.SetAxHostState(ActiveXHelper.inTransition, true); 

                try 
                {
                    ActiveXHelper.ActiveXState oldState;

                    while (state > this.ActiveXState) 
                    {
                        oldState = this.ActiveXState; 
 
                        switch (this.ActiveXState)
                        { 
                            case ActiveXHelper.ActiveXState.Passive:
                                TransitionFromPassiveToLoaded();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded; 
                                break;
                            case ActiveXHelper.ActiveXState.Loaded: 
                                TransitionFromLoadedToRunning(); 
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Running; 
                                break;
                            case ActiveXHelper.ActiveXState.Running:
                                TransitionFromRunningToInPlaceActive();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Failed transition"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive;
                                break; 
                            case ActiveXHelper.ActiveXState.InPlaceActive: 
                                TransitionFromInPlaceActiveToUIActive();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.UIActive, "Failed transition"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.UIActive;
                                break;
                            default:
                                Debug.Fail("bad state"); 
                                this.ActiveXState = this.ActiveXState + 1;  // To exit the loop
                                break; 
                        } 

                        OnActiveXStateChange((int)oldState, (int)this.ActiveXState); 
                    }
                }
                finally
                { 
                    this.SetAxHostState(ActiveXHelper.inTransition, false);
                } 
            } 
        }
 
        internal void TransitionDownTo(ActiveXHelper.ActiveXState state)
        {
            if (!this.GetAxHostState(ActiveXHelper.inTransition))
            { 
                this.SetAxHostState(ActiveXHelper.inTransition, true);
 
                try 
                {
                    ActiveXHelper.ActiveXState oldState; 

                    while (state < this.ActiveXState)
                    {
                        oldState = this.ActiveXState; 

                        switch (this.ActiveXState) 
                        { 
                            case ActiveXHelper.ActiveXState.Open:
                                Debug.Fail("how did we ever get into the open state?"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.UIActive;
                                break;
                            case ActiveXHelper.ActiveXState.UIActive:
                                TransitionFromUIActiveToInPlaceActive(); 
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive; 
                                break; 
                            case ActiveXHelper.ActiveXState.InPlaceActive:
                                TransitionFromInPlaceActiveToRunning(); 
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Running;
                                break;
                            case ActiveXHelper.ActiveXState.Running: 
                                TransitionFromRunningToLoaded();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Failed transition"); 
                                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded; 
                                break;
                            case ActiveXHelper.ActiveXState.Loaded: 
                                TransitionFromLoadedToPassive();
                                Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Passive, "Failed transition");
                                this.ActiveXState = ActiveXHelper.ActiveXState.Passive;
                                break; 
                            default:
                                Debug.Fail("bad state"); 
                                this.ActiveXState = this.ActiveXState - 1;  // To exit the loop 
                                break;
                        } 

                        OnActiveXStateChange((int)oldState, (int)this.ActiveXState);
                    }
                } 
                finally
                { 
                    this.SetAxHostState(ActiveXHelper.inTransition, false); 
                }
            } 
        }

        ///
        ///     Critical - runs arbitrary code on critical _axOleObject member. 
        ///
        [SecurityCritical] 
        internal bool DoVerb(int verb) 
        {
            int hr = _axOleObject.DoVerb(verb, 
                                         IntPtr.Zero,
                                         this.ActiveXSite,
                                         0,
                                         this.ParentHandle.Handle, 
                                         _bounds);
 
            Debug.Assert(hr == NativeMethods.S_OK, String.Format("DoVerb call failed for verb 0x{0:X}", verb)); 
            return hr == NativeMethods.S_OK;
        } 

        ///
        ///     Critical - Calls setParent, accesses _axWindow.
        /// 
        [SecurityCritical]
        internal void AttachWindow(IntPtr hwnd) 
        { 
            if (_axWindow.Handle == hwnd)
                return; 

            //

 

            _axWindow = new HandleRef(this, hwnd); 
 
            if (this.ParentHandle.Handle != IntPtr.Zero)
            { 
                UnsafeNativeMethods.SetParent(_axWindow, this.ParentHandle);
            }
        }
 
        ///
        ///     Critical - calls ActiveXSite.StartEvents - critical code. 
        /// 
        [ SecurityCritical ]
        private void StartEvents() 
        {
            if (!this.GetAxHostState(ActiveXHelper.sinkAttached))
            {
                this.SetAxHostState(ActiveXHelper.sinkAttached, true); 
                CreateSink();
            } 
            this.ActiveXSite.StartEvents(); 
        }
 
        ///
        ///     Critical - calls ActiveXSite.StopEvents - critical code.
        ///     NOT TAS: if you can stop listening to events - you could
        ///              potentially turn off a mitigation. On the WebOC this could 
        ///              stop site-locking mitigation.
        /// 
        [ SecurityCritical ] 
        private void StopEvents()
        { 
            if (this.GetAxHostState(ActiveXHelper.sinkAttached))
            {
                this.SetAxHostState(ActiveXHelper.sinkAttached, false);
                DetachSink(); 
            }
            this.ActiveXSite.StopEvents(); 
        } 

        /// 
        /// Critical - Calls critical code ( CoCreateInstance) calls critical interface members, _axInstance
        /// TreatAsSafe - although this method instantiates the control.
        ///               considered safe as the parameter that controls what to instantiate is critical for set.
        ///               and set only via the critical CTOR. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromPassiveToLoaded() 
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Passive, "Wrong start state to transition from"); 
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Passive)
            {
                //
                // First, create the ActiveX control 
                Debug.Assert(_axInstance == null, "_axInstance must be null");
 
                _axInstance = CreateActiveXObject(_clsid.Value); 
                Debug.Assert(_axInstance != null, "w/o an exception being thrown we must have an object...");
 
                //
                // We are now Loaded!
                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded;
 
                //
                // Lets give them a chance to cast the ActiveX object 
                // to the appropriate interfaces. 
                this.AttachInterfacesInternal();
            } 
        }

        ///
        /// Critical - accesses critical interface members, _axInstance 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromLoadedToPassive()
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Loaded) 
            {
                // 
                // Need to make sure that we don't handle any PropertyChanged 
                // notifications at this point.
                //this.NoComponentChangeEvents++; 
                try
                {
                    //
                    // Release the _axInstance 
                    if (_axInstance != null)
                    { 
                        // 
                        // Lets first get the cached interface pointers of _axInstance released.
                        this.DetachInterfacesInternal(); 

                        Marshal.FinalReleaseComObject(_axInstance);
                        _axInstance = null;
                    } 
                }
                finally 
                { 
                    //
                } 

                //
                // We are now Passive!
                this.ActiveXState = ActiveXHelper.ActiveXState.Passive; 
            }
        } 
 
        ///
        /// Critical - calls critical code - SetClientSite. 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical.
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromLoadedToRunning() 
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Loaded, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Loaded) 
            {
                //
                // See if the ActiveX control returns OLEMISC_SETCLIENTSITEFIRST
                int bits = 0; 
                int hr = _axOleObject.GetMiscStatus(NativeMethods.DVASPECT_CONTENT, out bits);
                if (NativeMethods.Succeeded(hr) && ((bits & NativeMethods.OLEMISC_SETCLIENTSITEFIRST) != 0)) 
                { 
                    //
                    // Simply setting the site to the ActiveX control should activate it. 
                    // And this will take us to the Running state.
                    _axOleObject.SetClientSite(this.ActiveXSite);
                }
 
                StartEvents();
 
                // 
                // We are now Running!
                this.ActiveXState = ActiveXHelper.ActiveXState.Running; 
            }
        }

        /// 
        /// Critical - accesses critical code, _axOleOlebject, StopEvents
        /// TreatAsSafe - state transitions considered safe. 
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromRunningToLoaded()
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Wrong start state to transition from"); 
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Running)
            { 
                StopEvents(); 

                // 
                // Inform the ActiveX control that it's been un-sited.
                _axOleObject.SetClientSite(null);

                // 
                // We are now Loaded!
                this.ActiveXState = ActiveXHelper.ActiveXState.Loaded; 
            } 
        }
 
        ///
        /// Critical - calls critical code - DoVerb.
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromRunningToInPlaceActive()
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.Running, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.Running)
            {
                try 
                {
                    DoVerb(NativeMethods.OLEIVERB_INPLACEACTIVATE); 
                } 
                catch (Exception e)
                { 
                    if(CriticalExceptions.IsCriticalException(e))
                    {
                        throw;
                    } 
                    else
                    { 
                        throw new TargetInvocationException(SR.Get(SRID.AXNohWnd, GetType().Name), e); 
                    }
                } 

                //
                // We are now InPlaceActive!
                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive; 
            }
        } 
 
        ///
        /// Critical - calls critical code - InPlaceDeactivate. 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical.
        ///                     However once instantiated, state transitions considered ok.
        /// 
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromInPlaceActiveToRunning() 
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive) 
            {
                //
                // InPlaceDeactivate.
                _axOleInPlaceObject.InPlaceDeactivate(); 

                // 
                // We are now Running! 
                this.ActiveXState = ActiveXHelper.ActiveXState.Running;
            } 
        }

        ///
        /// Critical - calls critical code - DoVerb. 
        /// TreatAsSafe - state transitions considered safe.
        ///                     Instantiating a control is considered critical. 
        ///                     However once instantiated, state transitions considered ok. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ] 
        private void TransitionFromInPlaceActiveToUIActive()
        {
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.InPlaceActive) 
            {
                DoVerb(NativeMethods.OLEIVERB_UIACTIVATE); 
 
                //
                // We are now UIActive! 
                this.ActiveXState = ActiveXHelper.ActiveXState.UIActive;
            }
        }
 
        ///
        /// Critical - accesses critical interface members, _axOleInPlaceObject 
        /// TreatAsSafe - state transitions considered safe. 
        ///                     Instantiating a control is considered critical.
        ///                     However once instantiated, state transitions considered ok. 
        ///
        [SecurityCritical, SecurityTreatAsSafe ]
        private void TransitionFromUIActiveToInPlaceActive()
        { 
            Debug.Assert(this.ActiveXState == ActiveXHelper.ActiveXState.UIActive, "Wrong start state to transition from");
            if (this.ActiveXState == ActiveXHelper.ActiveXState.UIActive) 
            { 
                int hr = _axOleInPlaceObject.UIDeactivate();
                Debug.Assert(NativeMethods.Succeeded(hr), "Failed in IOleInPlaceObject.UiDeactivate"); 

                //
                // We are now InPlaceActive!
                this.ActiveXState = ActiveXHelper.ActiveXState.InPlaceActive; 
            }
        } 
 
        #endregion ActiveX Related
 
        #endregion Internal Methods

        //-----------------------------------------------------
        // 
        //  Internal Properties
        // 
        //----------------------------------------------------- 

        #region Internal Properties 

        #region Framework Related

        ///  
        ///     The DependencyProperty for the TabIndex property.
        ///     Flags:              Can be used in style rules 
        ///     Default Value:      1 
        /// 
        internal static readonly DependencyProperty TabIndexProperty 
            = Control.TabIndexProperty.AddOwner(typeof(ActiveXHost));

        /// 
        ///     TabIndex property change the order of Tab navigation between Controls. 
        ///     Control with lower TabIndex will get focus before the Control with higher index
        ///  
        internal int TabIndex 
        {
            get { return (int) GetValue(TabIndexProperty); } 
            set { SetValue(TabIndexProperty, value); }
        }

        /// 
        ///     Critical - accesses _hwndParent critical member.
        /// 
        internal HandleRef ParentHandle 
        {
            [ SecurityCritical ] 
            get { return _hwndParent; }

            [ SecurityCritical ]
            set { _hwndParent = value; } 
        }
 
        // This returns a COMRECT. 
        internal NativeMethods.COMRECT Bounds
        { 
            get { return _bounds; }
            //How do we notify Avalon tree/layout that the control needs a new size?
            set { _bounds = value; }
        } 

        // This returns a Rect. 
        internal Rect BoundRect 
        {
            get { return _boundRect; } 
        }

        #endregion Framework Related
 
        #region ActiveX Related
 
        ///  
        /// Returns the hosted ActiveX control's handle
        ///  
        ///
        ///     Critical - returns critical _axWindow member
        ///
        internal HandleRef ControlHandle 
        {
            [ SecurityCritical ] 
            get { return _axWindow; } 
        }
 
        ///
        ///Returns the native webbrowser object that this control wraps. Needs FullTrust to access.
        /// Internally we will access the private field directly for perf reasons, no security checks
        /// 
        ///
        ///     Critical - returns critical Instance member. 
        /// 
        internal object ActiveXInstance
        { 
            [ SecurityCritical ]
            get
            {
                return _axInstance; 
            }
        } 
 

        /// 
        ///     Critical - returns critical Instance member.
        ///
        internal UnsafeNativeMethods.IOleInPlaceObject ActiveXInPlaceObject
        { 
            [ SecurityCritical ]
            get 
            { 
                return _axOleInPlaceObject;
            } 
        }

        ///
        ///     Critical - returns critical Instance member. 
        ///
        internal UnsafeNativeMethods.IOleInPlaceActiveObject ActiveXInPlaceActiveObject 
        { 
            [SecurityCritical]
            get 
            {
                return _axOleInPlaceActiveObject;
            }
        } 

        #endregion ActiveXRelated 
 
        #endregion Internal Properties
 
        //-----------------------------------------------------
        //
        //  Private Methods
        // 
        //------------------------------------------------------
 
        #region Private Methods 

        #region Framework Methods 

        private void OnInitialized(object sender, EventArgs e)
        {
            // 

 
 

 


            this.Initialized -= new EventHandler(this.OnInitialized);
 
            //Cannot inplace activate yet, since BuildWindowCore is not called yet
            //and we need that for getting the parent handle to pass on to the control. 
        } 

        private static void OnIsEnabledInvalidated(ActiveXHost axHost) 
        {
            //

 

 
        } 

        private static void OnVisibilityInvalidated(ActiveXHost axHost) 
        {
            if (axHost != null)
            {
                switch (axHost.Visibility) 
                {
                    case Visibility.Visible: 
                        // 
                        break;
                    case Visibility.Collapsed: 
                        //
                        break;
                    case Visibility.Hidden:
                        // 

 
 
                        break;
                } 
            }
        }

        ///     This event handler forwards focus events to the hosted ActiveX control 
        private static void OnGotFocus(object sender, KeyboardFocusChangedEventArgs e)
        { 
            ActiveXHost axhost = sender as ActiveXHost; 

            if (axhost != null) 
            {
                Invariant.Assert(axhost.ActiveXState >= ActiveXHelper.ActiveXState.InPlaceActive, "Should at least be InPlaceActive when getting focus");

                if (axhost.ActiveXState < ActiveXHelper.ActiveXState.UIActive) 
                {
                    axhost.TransitionUpTo(ActiveXHelper.ActiveXState.UIActive); 
                } 
            }
        } 

        ///     This event handler forwards focus events to the hosted WF controls
        private static void OnLostFocus(object sender, KeyboardFocusChangedEventArgs e)
        { 
            ActiveXHost axhost = sender as ActiveXHost;
 
            if (axhost != null) 
            {
                // If the focus goes from our control window to one of the child windows, 
                // we should not deactivate.
                //

                Invariant.Assert(axhost.ActiveXState >= ActiveXHelper.ActiveXState.UIActive, "Should at least be UIActive when losing focus"); 

                bool uiDeactivate = !axhost.IsKeyboardFocusWithin; 
 
                if (uiDeactivate)
                { 
                    axhost.TransitionDownTo(ActiveXHelper.ActiveXState.InPlaceActive);
                }
            }
        } 

        private static void OnAccessKeyPressed(object sender, AccessKeyPressedEventArgs args) 
        { 
            if (!args.Handled && args.Scope == null && args.Target == null)
            { 
                args.Target = (UIElement)sender;
            }
        }
 
        /*
                private void GetMnemonicList(SWF.Control control, ArrayList mnemonicList) { 
 
                    // Get the mnemonic for our control
                    // 
                    char mnemonic = HostUtils.GetMnemonic(control.Text, true);
                    if (mnemonic != 0)
                    {
                        mnemonicList.Add(mnemonic); 
                    }
 
                    // And recurse for our children, currently we only support one activex control 
                    //
                    if (HostedControl != null) GetMnemonicList(HostedControl, mnemonicList); 
                }
        */

        #endregion Framework Methods 

        #region ActiveX Related 
 
        ///
        ///     Critical -  accesses critical interface pointers. 
        ///
        [ SecurityCritical ]
        private void AttachInterfacesInternal()
        { 
            Debug.Assert(_axInstance != null, "The native control is null");
            _axOleObject = (UnsafeNativeMethods.IOleObject)_axInstance; 
            _axOleInPlaceObject = (UnsafeNativeMethods.IOleInPlaceObject)_axInstance; 
            _axOleInPlaceActiveObject = (UnsafeNativeMethods.IOleInPlaceActiveObject)_axInstance;
            // 
            // Lets give the inheriting classes a chance to cast
            // the ActiveX object to the appropriate interfaces.
            AttachInterfaces(_axInstance);
        } 

        /// 
        ///     Critical - accesses critical interface members. 
        ///     TreatAsSafe - clearing the interfaces is ok.
        /// 
        [ SecurityCritical, SecurityTreatAsSafe ]
        private void DetachInterfacesInternal()
        {
            _axOleObject = null; 
            _axOleInPlaceObject = null;
            _axOleInPlaceActiveObject = null; 
            // 
            // Lets give the inheriting classes a chance to release
            // their cached interfaces of the ActiveX object. 
            DetachInterfaces();
        }

        /// 
        ///     Critical - calls calls critical interface members.
        /// 
        [ SecurityCritical ] 
        private NativeMethods.SIZE SetExtent(int width, int height)
        { 
            NativeMethods.SIZE sz = new NativeMethods.SIZE();
            sz.cx = width;
            sz.cy = height;
 
            bool resetExtents = false;
            try 
            { 
                _axOleObject.SetExtent(NativeMethods.DVASPECT_CONTENT, sz);
            } 
            catch (COMException)
            {
                resetExtents = true;
            } 
            if (resetExtents)
            { 
                _axOleObject.GetExtent(NativeMethods.DVASPECT_CONTENT, sz); 
                try
                { 
                    _axOleObject.SetExtent(NativeMethods.DVASPECT_CONTENT, sz);
                }
                catch (COMException e)
                { 
                    Debug.Fail(e.ToString());
                } 
            } 
            return GetExtent();
        } 

        ///
        ///     Critical - accesses critical interface member _axOleObject
        ///     TreatAsSafe - getting the size of the control is considered ok. 
        ///
        [ SecurityCritical, SecurityTreatAsSafe ] 
        private NativeMethods.SIZE GetExtent() 
        {
            NativeMethods.SIZE sz = new NativeMethods.SIZE(); 
            _axOleObject.GetExtent(NativeMethods.DVASPECT_CONTENT, sz);
            return sz;
        }
 
        #endregion ActiveX Related
 
        #endregion Private Methods 

 
        //-----------------------------------------------------
        //
        //  Private Properties
        // 
        //------------------------------------------------------
 
        #region Private Properties 

        #endregion Private Properties 

        //------------------------------------------------------
        //
        //  Private Fields 
        //
        //----------------------------------------------------- 
 
        #region Private Fields
 
        #region Framework Related

        private static Hashtable invalidatorMap = new Hashtable();
 
        private delegate void PropertyInvalidator(ActiveXHost axhost);
 
        private NativeMethods.COMRECT _bounds    = new NativeMethods.COMRECT(0, 0, 0, 0); 
        private Rect             _boundRect      = new Rect(0, 0, 0, 0);
 
        private Size             _cachedSize     = Size.Empty;
        ///
        ///     Critical - _hwndParent considered critical.
        /// 
        [SecurityCritical ]
        private HandleRef        _hwndParent; 
        private bool             _isDisposed; 

        #endregion Framework Related 

        #region ActiveX Related

        /// 
        ///     Critical - _clsId controls what code to run and instantiate.
        /// 
        private SecurityCriticalDataForSet    _clsid; 

        /// 
        ///     Critical - hwnd of control
        ///
        [ SecurityCritical ]
        private HandleRef                   _axWindow; 
        private BitVector32                 _axHostState    = new BitVector32();
        private ActiveXHelper.ActiveXState  _axState        = ActiveXHelper.ActiveXState.Passive; 
 
        ///
        ///     Critical - ActiveXSite interfaces of control 
        ///
        [ SecurityCritical ]
        private ActiveXSite                 _axSite;
 
        ///
        ///     Critical - ActiveXContainer of control 
        /// 
        [ SecurityCritical ]
        private ActiveXContainer            _axContainer; 

        ///
        ///     Critical - all methods on this Interface are critical
        /// 
        [SecurityCritical]
        private object                      _axInstance; 
 
        // Pointers to the ActiveX object: Interface pointers are cached for perf.
        /// 
        ///     Critical - all methods on this Interface are critical
        ///
        [SecurityCritical]
        private UnsafeNativeMethods.IOleObject              _axOleObject; 

        /// 
        ///     Critical - all methods on this Interface are critical 
        ///
        [SecurityCritical] 
        private UnsafeNativeMethods.IOleInPlaceObject       _axOleInPlaceObject;

        ///
        ///     Critical - all methods on this Interface are critical 
        ///
        [SecurityCritical] 
        private UnsafeNativeMethods.IOleInPlaceActiveObject _axOleInPlaceActiveObject; 

        #endregion ActiveX Related 


        #endregion Private Fields
    } 
    #endregion ActiveXHost
} 

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK