public async Task <bool> StartDebug(EditorViewModel editor, ProjectViewModel currentProject, LoggerResult logger)
        {
            if (currentProject == null)
            {
                await editor.Session.Dialogs.MessageBox(Tr._p("Message", "An executable project must be set as current project in the session explorer in order to process build."),
                                                        MessageBoxButton.OK, MessageBoxImage.Information);

                return(false);
            }

            try
            {
                var projectWatcher = new ProjectWatcher(currentProject.Session, false);
                await projectWatcher.Initialize();

                var executableOutputPath = Path.GetDirectoryName(projectWatcher.CurrentGameExecutable.OutputFilePath);

                var debuggerProcess = await GetDebuggerProcess(editor);

                var projectCouldFirstCompile = new TaskCompletionSource <bool>();
                Task.Run(() => StartDebugHost(executableOutputPath, projectWatcher, projectCouldFirstCompile, RecompilationDelay, debuggerProcess, logger)).Forget();

                return(await projectCouldFirstCompile.Task);
            }
            catch
            {
                return(false);
            }
        }
Exemple #2
0
        public CodeViewModel(StrideAssetsViewModel strideAssetsViewModel) : base(strideAssetsViewModel.SafeArgument(nameof(strideAssetsViewModel)).ServiceProvider)
        {
            projectWatcherTask = Task.Run(async() =>
            {
                var result = new ProjectWatcher(strideAssetsViewModel.Session);
                await result.Initialize();
                return(result);
            });

            workspaceTask = projectWatcherTask.Result.RoslynHost.ContinueWith(roslynHost => roslynHost.Result.Workspace);

            workspaceTask = workspaceTask.ContinueWith(workspaceTask =>
            {
                var projectWatcher = projectWatcherTask.Result;
                var workspace      = workspaceTask.Result;

                // Load and update roslyn workspace with latest compiled version
                foreach (var trackedAssembly in projectWatcher.TrackedAssemblies)
                {
                    var project = trackedAssembly.Project;
                    if (project != null)
                    {
                        workspace.AddOrUpdateProject(project);
                    }
                }

                void TrackedAssemblies_CollectionChanged(object sender, Core.Collections.TrackingCollectionChangedEventArgs e)
                {
                    var project = ((ProjectWatcher.TrackedAssembly)e.Item).Project;
                    if (project != null)
                    {
                        switch (e.Action)
                        {
                        case NotifyCollectionChangedAction.Add:
                            {
                                workspace.AddOrUpdateProject(project);
                                break;
                            }

                        case NotifyCollectionChangedAction.Remove:
                            {
                                workspace.RemoveProject(project.Id);
                                break;
                            }
                        }
                    }
                }
                projectWatcher.TrackedAssemblies.CollectionChanged += TrackedAssemblies_CollectionChanged;

                // TODO: Right now, we simply replace the solution with newly loaded one
                // Ideally, we should keep our existing solution and update it to follow external changes after initial loading (similar to VisualStudioWorkspace)
                // This should provide better integration with background changes and local changes
                projectWatcher.AssembliesChangedBroadcast.LinkTo(new ActionBlock <List <AssemblyChangedEvent> >(events =>
                {
                    if (events.Count == 0)
                    {
                        return;
                    }

                    Dispatcher.InvokeAsync(async() =>
                    {
                        // Update projects
                        foreach (var e in events.Where(x => x.ChangeType == AssemblyChangeType.Project))
                        {
                            var project = e.Project;
                            if (project != null)
                            {
                                await ReloadProject(strideAssetsViewModel.Session, project);
                            }
                        }

                        // Update files
                        foreach (var e in events.Where(x => x.ChangeType == AssemblyChangeType.Source))
                        {
                            var documentId = workspace.CurrentSolution.GetDocumentIdsWithFilePath(e.ChangedFile).FirstOrDefault();
                            if (documentId != null)
                            {
                                workspace.HostDocumentTextLoaderChanged(documentId, new FileTextLoader(e.ChangedFile, null));
                            }
                        }
                    }).Wait();
                }), new DataflowLinkOptions());

                return(workspace);
            });

            // Apply syntax highlighting for tooltips
            keywordBrush = new SolidColorBrush(ClassificationHighlightColorsDark.KeywordColor);
            typeBrush    = new SolidColorBrush(ClassificationHighlightColorsDark.TypeColor);
            keywordBrush.Freeze();
            typeBrush.Freeze();

            // TODO: Update with latest RoslynPad
            //SymbolDisplayPartExtensions.StyleRunFromSymbolDisplayPartKind = StyleRunFromSymbolDisplayPartKind;
            //SymbolDisplayPartExtensions.StyleRunFromTextTag = StyleRunFromTextTag;
        }