My Visual Basic.NET Standard Programming Notes

( These notes pertain to using this IDE on Microsoft Windows XP Home edition.)

Hi!


Connecting To A Database
Display a Web page from a Windows Application
Creating DLLs
Getting The Form To Update
Creating Setup Projects
To Pass Form1 To Other Classes
To Initiate NetMeeting
Using Click With Double-Click Events
Using The Enum Function
Using The Timer
To Create A Simple Clock
Some New Logical Functions
Save Settings To The Registry
Delete A File
Working With Bitmaps
Adding Event Handlers Dynamically
Event Handlers Notes
Properties
Shared
Scrollbars
Enabling Tabstops on Radio Buttons
Calling Methods Using Strings
System.Type
Unexplainable Error Messages
Security Permissions
Accessing Your Base Form
Bound Event Handling Compared To Non-Bound Event Handling
Notes On Streams
Notes On File Reading
String Concatenation
Conversion And Comparison Operations
Coding and The Break Command
Using Inputbox
Starting Other Applications
Bytes! I need bytes!
Passing And Reading Objects

		
		
		
		
		
		
		
Database Connections

Use the Microsoft Jet Provider and oledbconnection type.


Back To Top
		
		
Display a Web Page from a Windows Application

Use system.diagnostics.process.start("..\WebPageName.htm") on the event.

Back To Top
		
		
Creating DLLs

The template for dll projects, called Code Libraries, is not available
in the standard edition. However, if you discover what you need to code,
it may build.

Back To Top
		
		
Getting The Form To Update

There seems to be at least four ways to get the Windows form
or control to update:


There are differences, so check them out.

Back To Top
		
		
Creating Setup Projects

Creating Setup Projects is easy. But there are a couple of things
to watch out for:

Those settings a done in the AssemblyInfo.vb file.
Hopefully, that will avoid any uninstall problems.

The easiest way to create the project is to add a Setup Project
to the solution you want to package. Next select the folder
that the application is to be installed to (Application Folder
is default and likely what you want), if necessary. Then, (here's the trick...)
select the Setup Project in the Solution Explorer and right-click it.
Select Add >. Then choose the Project Output of the project to package,
and anything else that you want to go with it.

Note: Apparently it does not automatically package the .NET Framwork
redistributable with the program. It will be in the project window however.
To include it, change the exclude property of it to false.
Otherwise, the output window will tell you what its name is and that
it is on the component update disk.

Then all you have to do is build the Setup Project. It will create
the files in the Setup Projects' folder. Go to the release folder
(hopefully!) and find the Setup file. That's the one that will install
the program.

Back To Top

		
		
To Pass Form1 To Other Classes

To pass Form1 to other classes, set it up like this:

		In the class put:
		
		Class MyClass
		  Public Sub Whatever(ByVal f1 As Form1)
		    ' work with Form1 by using f1.controlname    
		  End Sub
		End Class
		
		

Then call the sub like this:

		
		Class Form1
		  Dim mc as MyClass
		  mc.Whatever(Me)
		End Class
		
		

Back To Top


		
		
To Initiate NetMeeting

To initiate NetMeeting, create a reference to the NetMeetingLib COM object.
Then use:

	
        Dim nm As New NetMeetingLib.NetMeeting()
        nm.CallTo("phonenumber")
	
		
		
Back To Top
		
		
Using Click With Double-Click

The click event prevents all calls to the double-click event.


Back To Top
		
		
Using The Enum Function

Here is a simple example of using the enum function.


	Enum These
		one = 1
		two
		three
	End Enum
		
	Class MyClass		
	  Dim i As Int32
          i = Val(These.two)
          Select Case i
            Case 1
                MsgBox(These.one.ToString)
                MsgBox(Val(These.one))
            Case 2
                MsgBox(These.two.ToString)
                MsgBox(Val(These.two))
            Case 3
                MsgBox(These.three.ToString)
                MsgBox(Val(These.three))
          End Select
   End MyClass
		

The above will produce msgbox results of "two" and 2.


Back To Top
		
		
Using The Timer

To use the timer, it needs to be declared at the class level and
with withevents to take action when the interval is up (called
a tick event). Be aware that one second = 1000 milliseconds,
which is what the timer will count in.


Back To Top
		
		
		
		
To Create A Simple Clock

Set a timer for 1000 milliseconds. Create the event handler. Then in the
Tick event, put lblTimeView.Text = TimeOfDay.
If you want the date with it, exchange "TimeOfDay" for "Now". That's it.


Back To Top
		
		
		
		
Some New Logical Functions

	The Choose function:

	strHobby = Choose(intDeterminingNum, "Cycling", "Hiking", "Running")
	
	The IIF function:

	strStatus = IIf(dteArrival  <  #9:00 AM#, "Early", "Late")
	
	The Partition function:

	Partition(intDeterminingNum, startNum, stopNum, intervalNum)
Returns something like: "25:49" The Switch function: strHelper = Switch(strColor = "Cyan", "Cathy", _ strSize = "Small", "Stan" _ strToss = "Tails", "Talia" _ strGain = "Great", "Gary") To use the switch function, pass it all four of the left side variables, ie, strColor, strSize, etc. The first value that matches the corresponding right- side parameter will determine the value that will be assigned. So if strSize is the first one to match (have a value of "Small"), then "Stan" will be returned.

Back To Top
		
	
Save Settings To The Registry

Saving user settings to the Registry is easy. Use the types of
commands below.

		
		SaveSetting("KeyPointWorkFlowChartingProgram", "Charts", "Centering", True)
		GetSetting("KeyPointWorkFlowChartingProgram", "Charts", "Centering", "False")
		DeleteSetting("KeyPointWorkFlowChartingProgram")
		
		

Back To Top
		
		
Delete A File

		
	Class MyClass
		    
		' ( Optional ) Should be declared at class-level
		Private WithEvents fsw As New FileSystemWatcher()

		Sub DeleteMyFile		
		    ' Delete the old password file and raise notification event.	
			fsw.Path = Application.StartupPath
			fsw.EnableRaisingEvents = True

	        	Dim fsea As New FileSystemEventArgs(WatcherChangeTypes.Deleted, _
                                    Application.StartupPath, "unwanted.txt")

		    	Dim junkfile As File
		    
			' Try to delete the unwanted file.
			Try
				junkfile.Delete(".\unwanted.txt")
			Catch ex As Exception
				MsgBox(ex.Message)
			End Try
		 	
			' (Optional) Catch the filesystemwatcher deleted event in an event handler somewhere.
		End Sub
 	End Class
		
		

Back To Top
		
		
Working With Bitmaps

NOTE: These processes only work with ready-made,
ie., properly formatted, bitmap files. To read a
bitmap from file, see the section in SaveToClip below.

		
	Public Sub SaveToClip(ByVal p As PictureBox, ByVal g As Graphics)
	    
        '////////////////////////////////////////////////////////
        ' This works with a ready-made bitmap. 4/22/03
	
        ( Optional -- get bitmap from a file )
           Dim bmp As New Bitmap("E:\Pictures\myPic.bmp")
           g.DrawImage(bmp, New Point(0, 0))
           p.Image = bmp
        ( End Optional )
        
        Clipboard.SetDataObject(p.Image, True)
	    
        '////////////////////////////////////////////////////////
	
    End Sub


    Public Sub GetFromClip(ByVal p As PictureBox)
	    
        '/////////////////////////////////////////////////////////
        ' This works with a ready-made bitmap. 4/22/03
        ' Create a new instance of the DataObject interface.
	
        Dim data As IDataObject = Clipboard.GetDataObject()
        If (data.GetDataPresent(DataFormats.Bitmap)) Then
            p.Image = data.GetData(DataFormats.Bitmap)
        End If
	    
        '/////////////////////////////////////////////////////////
	
    End Sub
	
	

Back To Top
		
		
Adding Event Handlers Dynamically

To add an event handler dynamically:
		
		Class MyClass
		
		  Dim WithEvents SomeObj as CSomeClass
		  Dim AnothObj as CAnotherClass
		   
		  Private Sub MySub()
		    ' To add a handler, the delegate sub must be public.	
		    AddHandler SomeObj.SomeEvent, AddressOf AnothObj.SomePublicSub
		  End Sub
		  
		End Class
		
		

Back To Top
		
		
Event Handlers Notes

Only the Objects' creator can hear the events by default.
The object must be declared using "WithEvents" in order to hear events.
This can only be done at the class level. Example:
		
		Class MyClass
		
		  Dim WithEvents SomeObj as CSomeClass
		  
		  Private Sub MySub()handles SomeObj.SomeEvent
		    ' whatever
		  End Sub
		  
		End Class
		
		

Back To Top
		
		
Properties

Remember, properties can only be accessed by the creator of
the instance of the class, unless they are shared.

Back To Top
		
		
Shared

The "Shared" modifier can be used quite a bit, but generally,
it is best limited to simple value-types, since "Shared" items
strongly like to limit their communications to only communicating
with other "Shared" items.

Back To Top
		
		
Scrollbars

If a scrollbar is deleted, its "ValueChanged" event-handler WILL NOT
function, EVEN THOUGH IT IS THERE. To fix this, simply re-create that
event-handler and move the code for scrolling into the new event handler.

Back To Top
		
		
Enabling Tabstops on Radio Buttons

To fully enable radio buttons as tabstops, you must set each radio button
tabstop property to TRUE, and set the "checked" property of one radio button
of each group to TRUE. Otherwise that group of radio buttons will not actually
be included in the tab order at runtime.

Back To Top
		
		
Calling Methods Using Strings.

This example also sets or gets property values by using strings.
	
	Imports Microsoft.VisualBasic.CallType
	    ' Imports statements must be at the top of a module.	
	Sub TestCallByName1()
	    '  Set a property.
	  CallByName(TextBox1, "Text", CallType.Set, "New Text")
	    '  Retrieve the value of a property.	
	  MsgBox(CallByName(TextBox1, "Text", CallType.Get))
	    '  Call a method.
	  CallByName(TextBox1, "Hide", CallType.Method)
	End Sub
	
	
	
For more info, use the VB.NET help files on "CallByName."

Back To Top
		
		
System.Type

When a built-in method requests a System.Type, as far as I
have found out, it wants an object reference to a class (an instance),
and to know its type.

Example:
		
	Class MyClass
		Structure SMyStruct
			Dim x as int16
		End Structure
		Public myStructObj as New SMyStruct
	End Class
		
	Class ThisClass
		dim myClassObj as New MyClass
		
		Dim xmlSer as System.Xml.XmlSerialization.XmlSerializer(myClassObj.myStructObj.GetType)
		
		Private Sub Whatever()
		    ' Use xmlSer	
		End Sub
	
	End Class
	
		


Back To Top
		
Unexplainable Error Messages

The first thing to note is that the IntelliSense feature can (and does) list
attributes, methods, properties, etc. that do not exist. ( The IntelliSense feature
is the pop-up window that appears after you type an object name and a dot. )

This clearly indicates that it does not get its content from the Object Browser.
To resolve these issues, use only those attributes, methods, properties, etc. that
are listed in the Object Browser. Do note however, that even that functionality
is not guaranteed!



Back To Top
		
Security Permissions

For a permission to be granted to the entire assembly:
		
		imports System.Security.Permissions
		<Assembly: FileIOPermission(SecurityAction.RequestMinimum)>
		Class MyClass
			Private Sub WriteMyFile()
			    ' Perform file I/O
			End Sub
		End Class		
		
		
For a permission to be granted to a subroutine or class:
		
		imports System.Security.Permissions
		Class MyClass
		
		  <FileIOPermission(SecurityAction.Demand)> Public Sub MyXMLWriting()
		    ' Perform file I/O
		  End Sub
		
		End Class
		
		
For specific blocks of code:
		
	imports System.Security.Permissions
	Class MyClass
	  Sub MySub
		Dim MyPermission as New _
			Security.Permissions.FileIOPermission(PermissionState.Unrestricted)

		Try
			MyPermission.Demand()
		Catch e as Exception
			    ' Insert code to handle the exception.
		End Try
	  End Sub
	End Class
	
	
For a list of permissions that can be requested, try looking under
"code access permissions" in the VB.NET help files.

Back To Top
		
Accessing Your Base Form

Sometimes you need enough access to your GUI to warrant creating
a global variable. Also, this can truely help you both create
and use reusable code.
		
	Module GlobalsModule
		
	   Public BaseForm As Form1
		
	   Public Sub SetBaseName(ByVal f1 As Form1)
	     BaseForm = f1
	   End Sub
		  
	End Module 
	
	Class MyClass
	
	   Protected Overrides Sub OnLoad(ByVal e As System.EventArgs)
               Call SetBaseName(Me)
           End Sub
       
        End Class
		
		

Note that access to the BaseForm events will not be passed using this method.
Also, access to the base class is generally safe in regards to variables in that
variable access is the same as it is for any class, ie. no access to private variables
will be granted.

(Somewhat Related Event Topic: " Bound Event Handling Compared To Non-Bound Event Handling ")

Back To Top

		

Bound Event Handling Compared To Non-Bound Event Handling

NOTE: In this context, Bound and Non-Bound Events may be my own terms. They
are used to differentiate events that are triggered by a control ( Bound
Events ) from those that are raised in code ( Non-Bound Events ).

By default Bound Events will only be heard by the class they belong to
( in the Controls Collection ). Non-Bound Events, on the other hand, by
default cannot be heard by their own class ( the class they are declared
in by using " Event MyEvent() " ).

Use the " AddHandler " method to set up event handlers:
For a Class to handle its own events, use this format:


    Class MyClass
	   
       Event MyEvent()
	   
       Private Sub MySub()
          AddHandler Me.MyEvent, AddressOf Me.HandleMyEvent
          RaiseEvent MyEvent()
          RemoveHandler Me.MyEvent, AddressOf Me.HandleMyyEvent
       End Sub
    
    End Class

        

For a Class to handle another Class's Event, use this format:

	
    Class AClassThatRaisesAnEvent
       
       Event SomeEvent()
       
       Public Sub DoSomething()
          RaiseEvent SomeEvent()
       End Sub
    
    End Class
		
    Class MyClass
	   
    Private SomeObj as New AClassThatRaisesAnEvent()
	  
       Private Sub DoSomeWork()
	
	  
	  ' Maybe does part of the work here.

	  ' Needs to use another object which raises an event that we need
	  ' to write the reaction code for, so set up an event handler.
          AddHandler SomeObj.SomeEvent, AddressOf Me.HandleSomeObjctsEvent
          Call SomeObj.DoSomething()
	  
	  ' Maybe does some more work here.

       End Sub
	
       Private Sub HandleSomeObjctsEvent() handles SomeObj.SomeEvent
	  
           ' Respond to the event here.

	   ' Note that if another call is made to the "DoSomeWork()" method,
	   ' it would add an additional handler ( another instance of this handler ).
	   ' Thus, every time the event is raised, this handler would be called
	   ' twice. That would also be the case if a different sub 
	   ' had used the "AddHandler" method to add this sub as a handler.
	   RemoveHandler SomeObj.SomeEvent, AddressOf Me.HandleSomeObjctsEvent
       End Sub
	   
    End Class

    

Back To Top
	
Notes On Streams

When a built-in method requires a stream, such as "System.IO.Stream,"
it may accept a file stream, as in "System.IO.FileStream."


Back To Top
	
Notes On File Reading

When using FileGet to retreive a record from a random access
or binary file:

		
		

If there is no record loaded during the read,
the values in the structure will be "nothing" --
except for Date type values which will have a default
value of #12:00:00#.

A value of "nothing" can subsequently be used
in a comparison such as:

		
		' ( Even if PageNum = "nothing" this will evaluate without crashing. )
		If SMyStruct.PageNum = 2 Then 
			' do whatever
		End If 
		
		

Back To Top
	
String Concatenation

Notice that a non-empty string cannot be added to an empty
string, but an empty string can be added to a non-empty string. So...

		Example:
		
		Dim strSomething as String
		Dim strEmpty as String
		
		strSomething = "Book"
		strEmpty = ""
		
		' Now try concatenations
		strEmpty &= strSomething ' This will give ""
		strEmpty = strSomething & strEmpty ' This will give "Book"
		
		

Back To Top
	
Conversion And Comparison Operations

The CInt(myNum) type of built-in type-conversion functions
are great. Just note that if your program ever tries to convert
an empty string to a number, it will crash the program
unless you handle the exception it throws in a Try Block.

		
		So  CInt("")  will throw an exception.
		
		Also note that built-in functions such as  Join( strMyString , "," )
		tend to create strings like this    "12      ".
		
		So if you use that in a subsequent comparison, it will not equal 
		a string such as "12". 
		( You can use the Trim(myString) function to help with this though. )
		

Back To Top
	
Coding and The Break Command

The Stop command is the programmatic equivalent
of the Break command.

When developing code, it's nice, and necessary, to put some Try Blocks
in, (partly because they're much more bother to put in afterwards). But
when an exception is thrown that is caught by the Try Block, maybe all
all you get is a message, and the program ends without showing you
where the error took place. That's a real hinderance to debugging sometimes.
The fix for these woes is the Stop command. ( It actually works like
you clicked the "Break" button. )

		Example:
		
		Try
			FileGet(FileNum,".\MyFile.txt")
		Catch ex as System.Exception
			msgbox(ex.Message)
			Stop  ' this is like the "Break" button
		End Try
		
		

Back To Top
	
Using Inputbox

Whe using the built-in Inputbox, always get the return value as a string
because if the Cancel button is used, or the response is "", an exception
will be thrown if it tries to store the value in a numeric data type (because
the conversion to a numeric data type will be attempted before the value
can be stored -- this is an implicit conversion, in other words.)


Back To Top
	

		
Starting Other Applications

Here are three ways to start an application through VB.NET:


		System.Diagnostics.Process.Start("ProgramName.exe")
		'		OR 
		
		Dim ProcID as Integer 
		ProcID = Shell("cmd.exe", AppWinStyle.NormalFocus)
		'		OR 
			' This next one only works on some apps
			' (those that own their windows.)
		AppActivate(ProcID)
		

Back To Top
		
Bytes! I need bytes!

You need to have your data in an array of bytes sometimes,
for various tasks like network transmissions. Try something like
the following to load a buffer of bytes with your data.

		
        Dim Buffer(5000) As Byte
        Buffer = System.Text.Encoding.Default.GetBytes("This is my data.")
        
        ' OR
        
        Buffer = System.Text.Encoding.ASCII.GetBytes("This is my data.")
        
		

Back To Top
		
Passing And Reading Objects

Here is one way to pass a multi-part object and discover what
data types it contains, as well as their values:

	
	Public Class PassObject
		
	        Structure SMyObj
			Dim a as String
			Dim b as Boolean
		End Structure
		
		Public Sub PassTheObject()
		
			' Create our data object 
			
			Dim MyObj as New SMyObj()
			
			' Load our data values 
			
			MyObj.a = "Some text."
			MyObj.b = True
			
			' Create our reader object 
			
			Dim ReadObject as New MyReadObject()
			
			' Call our reader and pass the data object 
			
			ReadObject.ShowObjContents(MyObj)
		End Sub
	End Class
	
		
    Public Class MyReadObject
        Public Sub ShowObjContents(ByVal objContents As Object)
          Dim fi() As System.Reflection.FieldInfo = objContents.GetType.GetFields()
          Dim i As Int16
          For i = 0 To UBound(fi)
            Console.WriteLine(fi(i).FieldType().ToString)
            Console.WriteLine(fi(i).GetValue(objContents))
          Next
        End Sub
    End Class
    
    

Back To Top