How to iterate through open forms in a VSTO add-in? - vsto

I have a VSTO add-in for MS Project that opens forms where the data is related to the specific project file that was active when the form was open. It is possible to open one form related to one project file, while having another different form open that is related to a second open project file.
When I close a project file I would like to check each open form, and close it if the forms base project ID equals the project ID of the project file that is closing. How do I access the open forms collection of the vsto application (or do something equivalent)? The Application.OpenForms object doesn't appear to exist in the vsto world.

Use a Dictionary object to store an instance of the form along with the name of the file. Every time a form is created, add it to the dictionary and when the project is closed, search the dictionary to close the appropriate copy.
Friend ProjectForms As New Dictionary(Of String, MyForm)
Friend Sub ShowForm()
Dim f As New MyForm
Try
ProjectForms.Add(ProjApp.ActiveProject.Name, f)
Catch AlreadyInTheDictionary As Exception
' do nothing, it's already in the dictionary
End Try
f.Show()
End Sub
Put this in the module with the application events (typically ThisAddIn).
Private Sub Application_ProjectBeforeClose(pj As MSProject.Project, ByRef Cancel As Boolean) Handles Application.ProjectBeforeClose
ProjectForms(pj.Name).Close()
End Sub

Related

How to automatically show VSTO Excel Workbook document level Action Pane when opening the Excel Workbook which project was built on

I created my Document-Level project in Visual Studio by selecting one of my existing excel workbooks in project startup wizard and then I designed my action pane and wrote a code as shown below. My action pane shows automatically when I debug/Start it from Visual Studio but when I try to open that specific document which I created my project on, it won't show.
This is my code in ThisWorkbook.vb so far:
Public Class ThisWorkbook
Dim apSavingActionPane As New ActionsPaneControl1
Private Sub ThisWorkbook_Startup() Handles Me.Startup
Me.ActionsPane.Controls.Add(apSavingActionPane)
Me.Application.CommandBars("Task Pane").Visible = True
End Sub
Private Sub ThisWorkbook_Shutdown() Handles Me.Shutdown
End Sub
End Class
First of all I should have Published my project
I tried that before but there was an error in publishing process because my solution was on my cloud storage folder on my computer and therefore my project couldn't built because of some creation time difference. I moved my solution on my local disk parts which won't sync after every change and my problem solved.

How to close windows opened by webview2 in VB.Net

I have a WinForms application which uses webview2 to embed an Edge browser window in my application. It works great, but when the user clicks a link within it, it opens an extra "child" window. That's fine too, but if that child window is left open, it causes the web application to timeout, so I'd like to close them automatically after a time.
I tried the common solutions to close open forms, but they only get the top level forms, and never these child ones.
I've tried this code to close them all, but the dynamically opened forms are not closed:
Public Sub CloseAllForms()
Dim FormList As ArrayList = New ArrayList()
'Add all opened forms into a Collection.
For Each Frm As Form In Application.OpenForms
FormList.Add(Frm.Name)
Next
'Now Close the forms
For Each FormName As String In FormList
If FormName <> "frmMain" Then Application.OpenForms(FormName).Close()
Next
End Sub
How can I reference these windows so that I can close them on a schedule?

Visual basic. Change default startup form in code, depending on value of variable

I have been working on a Visual Basic project in Visual Studio and have encountered a problem.
I understand that the Startup form property in the Application page of the Project Designer can be changed to a default form, however what I require is a way to do this through code in ApplicationEvents.vb depending on the value of a variable within application settings.
The goal is that if a user completes a form then a value is assigned to a variable, e.g. variable username = "xxx". If this value is true, then the default startup is a login form (as the user has already registered), and if it is false then the user is taken to a register form.
I appreciate that I could use another form to determine this, however this seems like I would be squandering the capabilities of ApplicationEvents and not using it correctly (I also want to avoid the inevitable flicker of a blank form as it decides).
I know that the default form is stored in Application.myapp, however with the final publication of the .exe this file will (presumably) not be exported with it, so I want to avoid writing directly to it. I have also read into the windowsformsapplicationbase.mainform property, however cannot figure out how to use it?
Here is a example piece of code from ApplicationEvents.vb to demonstrate my question.
If String.IsNullOrEmpty(My.Settings.username) Then
MsgBox("You have not registered")
'set register as default form
Else
MsgBox("You have registered")
'set login as default form
End If
Usually, if you need that much control over what happens at start-up, you just want to disable the a application framework. To do so, just un-check the Enable application framework check-box in the Application tab of the My Project settings designer window. Once you un-check that, you will be able to change the Startup object to Sub Main. Then you can add a new module with a Main method, like this:
Module Module1
Public Sub Main()
Application.EnableVisualStyles()
If String.IsNullOrEmpty(My.Settings.username) Then
Application.Run(New RegisterForm())
Else
Application.Run(New LoginForm())
End If
End Sub
End Module
Be aware, however--by disabling the application framework, you will loose the other automatic functionality that it provides, such as ApplicationEvents. If you want to use the application framework, you can accomplish the same thing by simply setting the MyApplication.MainForm property in the MyApplication.Startup event:
Partial Friend Class MyApplication
Private Sub MyApplication_Startup(sender As Object, e As ApplicationServices.StartupEventArgs) Handles Me.Startup
If String.IsNullOrEmpty(My.Settings.username) Then
Me.MainForm = New RegisterForm()
Else
Me.MainForm = New LoginForm()
End If
End Sub
End Class
Alternatively, you could always show the same form, but then have the form contain nothing but a single UserControl. Then you can simply switch which UserControl is displayed depending upon the settings. The user-controls would need to include all of the controls that would have otherwise been placed on the two different forms.

Auto displaying form on opening a template file, dotm from explorer

I have written a form based document generation macro (in VBA) for distribution to a sales team.
For their ease of use, I want to provide a self-contained file which will display the form as soon as the document is opened.
Using AutoOpen I can get the form to display as intended if word is already open and the dotm file is opened within. However, if I double click the file from within explorer, nothing happens and I have to launch the macro manually. I thought AutoExec might allow this but no luck there. I've spent considerable time trying to get this to work through googling etc. but I'm not getting anywhere.
How can I make the form display even when the file is opened with a double click? Is it possible to do this without having to change normal.dotm for each user?
For further background, I am using Word 2013 with macros fully enabled during testing. The dotm file is stored in a trusted location.
I am using a macro to launch the form like this...
Public Sub AutoOpen()
StartPage.Show
End Sub
I have tried using AutoExec as well to no avail.
In the "generator.dotm" file got to Visual Basic and go in to the "ThisDocument" Microsoft Word Object.
At the top of the Visual Basic Editor select "Document" in the left hand side and then click on "New" on the right hand side. Private Sub Document_New() method will appear for you to be able to edit. Then you can call your userform in there. Similar to:
Private Sub Document_New()
Dim myForm As UserForm1
Set myForm = New UserForm1
myForm.Show
End Sub
Save your Generator.dotm and double click it through Windows explorer and you should get the results that you would like.

How to properly close form1 after showing form2

I have a script editor that I'm using to code through the object model of software my company uses. It has a login form to make sure that you are able to access the system and a main form to pull the script from the object and edit using ScintillaNET.
The issue that I am having is when I pass the object to the main form and leave the login form open it runs smoothly but I want to close the login form after the main form is open. When I do this it stops immediately after opening the main form.
Here is a sample of my code. You can see for now that I have commented out the line Me.Close() as that seems to the issue.
' Close this form, show the main form and pass the M3 object to it
Dim f As FormMain = New FormMain
' Pass the M3 object to next form
f.M3System = M3System
f.Show()
'Me.Close()
any help would be awesome!!!
This is a built-in feature for VB.NET. Use Project + Properties, Application tab.
Change the Shutdown mode setting to "When last form closes".