File: IntelliSense\Session.cs
Web Access
Project: src\src\EditorFeatures\Core\Microsoft.CodeAnalysis.EditorFeatures.csproj (Microsoft.CodeAnalysis.EditorFeatures)
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.
 
#nullable disable
 
using System;
using Microsoft.CodeAnalysis.Editor.Shared.Extensions;
using Roslyn.Utilities;
 
namespace Microsoft.CodeAnalysis.Editor.Implementation.IntelliSense;
 
internal class Session<TController, TModel, TPresenterSession> : ISession<TModel>
    where TPresenterSession : IIntelliSensePresenterSession
    where TController : IController<TModel>
    where TModel : class
{
    public TController Controller { get; }
    public ModelComputation<TModel> Computation { get; }
 
    // The presenter session for the computation we've got going.  It's lifetime is tied 1:1 with
    // the computation.  When the computation starts we make a presenter (note: this does not
    // mean that the user will ever see any UI), and when the computation is stopped, we will
    // end the presentation session.
    public TPresenterSession PresenterSession { get; }
 
    public Session(TController controller, ModelComputation<TModel> computation, TPresenterSession presenterSession)
    {
        this.Controller = controller;
        this.Computation = computation;
        this.PresenterSession = presenterSession;
 
        // If the UI layer dismisses the presenter, then we want to know about it so we can stop
        // doing whatever it is we're doing.
        this.PresenterSession.Dismissed += OnPresenterSessionDismissed;
    }
 
    public TModel InitialUnfilteredModel { get { return this.Computation.InitialUnfilteredModel; } }
 
    private void OnPresenterSessionDismissed(object sender, EventArgs e)
    {
        Computation.ThreadingContext.ThrowIfNotOnUIThread();
        Contract.ThrowIfFalse(ReferenceEquals(this.PresenterSession, sender));
        Controller.StopModelComputation();
    }
 
    public virtual void Stop()
    {
        Computation.ThreadingContext.ThrowIfNotOnUIThread();
        this.Computation.Stop();
        this.PresenterSession.Dismissed -= OnPresenterSessionDismissed;
        this.PresenterSession.Dismiss();
    }
 
    public TModel WaitForController()
    {
        Computation.ThreadingContext.ThrowIfNotOnUIThread();
        return Computation.WaitForController();
    }
}