I don't know where I got it. I will copy it here (hope it's OK to post so much text):
Option Explicit
' Read INI functions
Private Declare Function GetPrivateProfileInt Lib "kernel32" Alias "GetPrivateProfileIntA" (ByVal lpApplicationName As String, ByVal lpKeyName As String, ByVal nDefault As Long, ByVal lpFileName As String) As Long
Private Declare Function GetPrivateProfileString Lib "kernel32" Alias "GetPrivateProfileStringA" (ByVal lpApplicationName As String, ByVal lpKeyName As Any, ByVal lpDefault As String, ByVal lpReturnedString As String, ByVal nSize As Long, ByVal lpFileName As String) As Long
' Write INI function
Private Declare Function WritePrivateProfileString Lib "kernel32" Alias "WritePrivateProfileStringA" (ByVal lpApplicationName As String, ByVal lpKeyName As Any, ByVal lpString As Any, ByVal lpFileName As String) As Long
'
Public Sub INI_LoadControlPos(ByVal frm As Form, ByVal INIFile As String)
Dim i As Long
Dim j As Long
Dim buff As String
Dim ControlX As Control
Dim cIndex As Integer
' Loop through all the controls
For i = 0 To frm.Controls.Count - 1
' Get the current control
Set ControlX = frm.Controls(i)
Select Case TypeName(ControlX)
Case "ListView"
For j = 1 To ControlX.ColumnHeaders.Count
' Save the width of each columnheader
' But first check if the control is part of an array
On Error Resume Next
If (Not ControlX.Index <> ""

Then
ControlX.ColumnHeaders.Item(j).Width = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".ColumnHeader.Item(" & j & "

.Width", INIFile))
Else
ControlX.ColumnHeaders.Item(j).Width = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".ColumnHeader.Item(" & j & "

.Width", INIFile))
End If
Next j
Case "CoolBar"
For j = 1 To ControlX.Bands.Count
' Save the info for each band
' But first check if the control is part of an array
On Error Resume Next
If (Not ControlX.Index <> ""

Then
ControlX.Bands.Item(j).NewRow = CBool(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.NewRow", INIFile))
ControlX.Bands.Item(j).Position = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.Position", INIFile))
ControlX.Bands.Item(j).Height = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.Height", INIFile))
ControlX.Bands.Item(j).Width = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.Width", INIFile))
Else
ControlX.Bands.Item(j).NewRow = CBool(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.NewRow", INIFile))
ControlX.Bands.Item(j).Position = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.Position", INIFile))
ControlX.Bands.Item(j).Height = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.Height", INIFile))
ControlX.Bands.Item(j).Width = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.Width", INIFile))
End If
Next j
Case "SlidingDivider"
On Error Resume Next
If Not ControlX.Index <> "" Then
ControlX.Left = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Left", INIFile))
ControlX.Top = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Top", INIFile))
ControlX.Height = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Height", INIFile))
ControlX.Width = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Width", INIFile))
Else
cIndex = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Index", INIFile))
ControlX(cIndex).Left = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Left", INIFile))
ControlX(cIndex).Top = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Top", INIFile))
ControlX(cIndex).Height = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Height", INIFile))
ControlX(cIndex).Width = CInt(INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Width", INIFile))
End If
End Select
Next i
End Sub
Public Sub INI_LoadControlValues(ByVal frm As Form, ByVal INIFile As String)
' Function: INI_LoadControlValues
'
' Place in Form_Load to load the values for
' the controls you pass in the array. This
' function is mainly used for saving user-
' defined options/settings such as check-
' boxes and radio buttons. Currently only
' supports controls with the Value property
'
' Ex: INI_LoadControlValues Me, "c:\windows\myini.ini"
Dim i As Long ' Control counter
Dim j As Long ' ListView columnheader counter
Dim ControlX As Control
Dim ControlX_Type As String
Dim ControlX_Val As String
' Loop through all the controls
For i = 0 To frm.Controls.Count - 1
' Get the current control
Set ControlX = frm.Controls(i)
' Save the values for each control if there is one associated with it
' But first check if the control is part of an array
On Error Resume Next
If (Not ControlX.Index <> ""

Then
ControlX_Val = INI_Read("Control Data", frm.Name & "." & ControlX.Name & ".Value", INIFile)
Else
ControlX_Val = INI_Read("Control Data", frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Value", INIFile)
End If
' Determine what kind of control this is
' and get the data accordingly.
ControlX_Type = TypeName(ControlX)
Select Case ControlX_Type
Case "CheckBox"
If ControlX_Val <> "" Then ControlX.Value = CInt(ControlX_Val)
Case "OptionButton"
If ControlX_Val <> "" Then ControlX.Value = CInt(ControlX_Val)
Case "HScrollBar"
If ControlX_Val <> "" Then ControlX.Value = CInt(ControlX_Val)
Case "VScrollBar"
If ControlX_Val <> "" Then ControlX.Value = CInt(ControlX_Val)
Case "Slider"
If ControlX_Val <> "" Then ControlX.Value = CInt(ControlX_Val)
Case "FolderTreeview"
If ControlX_Val <> "" Then ControlX.SelectedFolder = ControlX_Val
Case "DriveListBox"
If ControlX_Val <> "" Then ControlX.Drive = ControlX_Val
Case "DirListBox"
If ControlX_Val <> "" Then ControlX.path = ControlX_Val
Case "FileListBox"
If ControlX_Val <> "" Then ControlX.path = ControlX_Val
Case "CcXploreTreeView"
ControlX.CurrentFolder = INI_Read("Control Data", CStr(frm.Name & "." & ControlX.Name & ".CurrentFolder"

, INIFile)
Case "CcXploreListView"
ControlX.CurrentFolder = CStr(INI_Read("Control Data", CStr(frm.Name & "." & ControlX.Name & ".CurrentFolder"

, INIFile))
ControlX.Pattern = CStr(INI_Read("Control Data", CStr(frm.Name & "." & ControlX.Name & ".Pattern"

, INIFile))
If ControlX.Pattern = "" Then ControlX.Pattern = "*.*"
Case "TextBox"
If ControlX_Val <> "" Then ControlX.Text = ControlX_Val
Case "ComboBox"
If ControlX_Val <> "" Then ControlX.Text = ControlX_Val
End Select
Next i
End Sub
Public Sub INI_LoadForm(ByVal frm As Form, Optional ByVal INIFile As String, Optional ResetFile As Boolean = False)
' This is for incase the file was already deleted
On Error Resume Next
' Create a generic INI name from the App title
If INIFile = "" Then INIFile = App.path & "\" & App.Title & ".ini"
If ResetFile = True Then Kill INIFile: Exit Sub
INI_LoadFormPos frm, INIFile
INI_LoadControlPos frm, INIFile
INI_LoadControlValues frm, INIFile
End Sub
Public Sub INI_LoadFormPos(ByVal frm As Form, ByVal INIFile As String)
' Function: INI_LoadFormPosition
'
' Place in Form_Load to place a form at its last position
' and size as long as you had INI_SaveFormPosition in that
' form's Form_Unload event.
' Don't position or resize the form if there
' are no values to read back form the ini.
Dim X As Integer
Dim buff As String
' Form.Left
buff = INI_Read("Form Data", CStr(frm.Name) & ".Left", INIFile)
If buff <> "" Then frm.Left = CInt(buff)
' Form.Top
buff = INI_Read("Form Data", CStr(frm.Name) & ".Top", INIFile)
If buff <> "" Then frm.Top = CInt(buff)
' Form.Height
buff = INI_Read("Form Data", CStr(frm.Name) & ".Height", INIFile)
If buff <> "" Then frm.Height = CInt(buff)
' Form.Width
buff = INI_Read("Form Data", CStr(frm.Name) & ".Width", INIFile)
If buff <> "" Then frm.Width = CInt(buff)
' Form.Tag
buff = INI_Read("Form Data", CStr(frm.Name) & ".Tag", INIFile)
If buff <> "" Then frm.Tag = CStr(buff)
' Form.WindowState
buff = INI_Read("Form Data", CStr(frm.Name) & ".WindowState", INIFile)
If buff <> "" Then frm.WindowState = vbMaximized
End Sub
Public Function INI_Read(ByVal Section As String, ByVal KeyName As String, Optional ByVal INIFile As String) As Variant
' Function: INI_Read
'
' Reads back a value from an INI
'
' [Section]
' KeyName = Value
' Create a generic INI name from the App title
If INIFile = "" Then INIFile = App.path & "\" & App.Title & ".ini"
Dim X As Integer
Dim buff As String
buff = Space(255)
X = GetPrivateProfileString(Section, CStr(KeyName), vbNullString, buff, 255, INIFile)
INI_Read = Left(buff, X)
End Function
Public Function INI_ReadBool(ByVal Section As String, ByVal KeyName As String, ByVal INIFile As String) As Boolean
' Function: INI_ReadValue
'
' Reads back a value from an INI
Dim X As Integer
Dim buff As String
buff = Space(255)
X = GetPrivateProfileString(Section, CStr(KeyName), vbNullString, buff, 255, INIFile)
If LCase(Left(buff, X)) = "true" Or LCase(Left(buff, X)) = "1" Then INI_ReadBool = True Else INI_ReadBool = False
End Function
Public Sub INI_SaveControlPos(ByVal frm As Form, ByVal INIFile As String)
Dim i As Long
Dim j As Long
Dim ControlX As Control
' Loop through all the controls
For i = 0 To frm.Controls.Count - 1
' Get the current control
Set ControlX = frm.Controls(i)
' Save some specials values for ListView's and CoolBar's
Select Case TypeName(ControlX)
Case "ListView"
For j = 1 To ControlX.ColumnHeaders.Count
' Save the width of each columnheader
' But first check if the control is part of an array
On Error Resume Next
If (Not ControlX.Index <> ""

Then
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".ColumnHeader.Item(" & j & "

.Width"

, CStr(ControlX.ColumnHeaders.Item(j).Width), INIFile
Else
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".ColumnHeader.Item(" & j & "

.Width"

, CStr(ControlX.ColumnHeaders.Item(j).Width), INIFile
End If
Next j
Case "CoolBar"
For j = 1 To ControlX.Bands.Count
' Save the info for each band
' But first check if the control is part of an array
On Error Resume Next
If (Not ControlX.Index <> ""

Then
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.NewRow"

, CStr(ControlX.Bands.Item(j).NewRow), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.Position"

, CStr(ControlX.Bands.Item(j).Position), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.Height"

, CStr(ControlX.Bands.Item(j).Height), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".Bands.Item(" & j & "

.Width"

, CStr(ControlX.Bands.Item(j).Width), INIFile
Else
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.NewRow"

, CStr(ControlX.Bands.Item(j).NewRow), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.Position"

, CStr(ControlX.Bands.Item(j).Position), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.Height"

, CStr(ControlX.Bands.Item(j).Height), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Bands.Item(" & j & "

.Width"

, CStr(ControlX.Bands.Item(j).Width), INIFile
End If
Next j
Case "SlidingDivider"
On Error Resume Next
If Not ControlX.Index <> "" Then
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name) & ".Left", CStr(ControlX.Left), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name) & ".Top", CStr(ControlX.Top), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name) & ".Height", CStr(ControlX.Height), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name) & ".Width", CStr(ControlX.Width), INIFile
Else
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

"

& ".Index", CStr(ControlX.Index), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

"

& ".Left", CStr(ControlX.Left), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

"

& ".Top", CStr(ControlX.Top), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

"

& ".Height", CStr(ControlX.Height), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

"

& ".Width", CStr(ControlX.Width), INIFile
End If
End Select ' Case TypeName(ControlX)
Next i
End Sub
Public Sub INI_SaveControlValues(ByVal frm As Form, ByVal INIFile As String, Optional ByVal SaveOthers As Boolean = False)
' Function: INI_SaveControlValues
'
' Place in Form_UnLoad to save the values for
' the controls you pass in the array. This
' function is mainly used for saving user-
' defined options/settings such as check-
' boxes and radio buttons. Currently only
' supports controls with the Value property
'
' Ex: INI_SaveControlValues Me, "c:\windows\myini.ini"
Dim i As Long ' Control counter
Dim j As Long ' ListView columnheader counter
Dim ControlX As Control
Dim ControlX_Type As String
Dim ControlX_Val As Variant
' Loop through all the controls
For i = 0 To frm.Controls.Count - 1
' Get the current control
Set ControlX = frm.Controls(i)
ControlX_Val = ""
' Determine what kind of control this is
' and get the data accordingly.
ControlX_Type = TypeName(ControlX)
Select Case ControlX_Type
' Controls having to do with setting options
Case "CheckBox"
ControlX_Val = ControlX.Value
Case "OptionButton"
ControlX_Val = ControlX.Value
Case "Slider"
ControlX_Val = ControlX.Value
Case "HScrollBar"
ControlX_Val = ControlX.Value
Case "VScrollBar"
ControlX_Val = ControlX.Value
' Controls having to do with file access
Case "FolderTreeview"
ControlX_Val = ControlX.SelectedFolder
Case "DriveListBox"
ControlX_Val = ControlX.Drive
Case "DirListBox"
ControlX_Val = ControlX.path
Case "FileListBox"
ControlX_Val = ControlX.path
Case "CcXploreListView"
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".CurrentFolder"

, CStr(ControlX.CurrentFolder), INIFile
If ControlX.Pattern = "" Then ControlX.Pattern = "*.*": WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".Pattern"

, CStr(ControlX.Pattern), INIFile
Case "CcXploreTreeView"
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".CurrentFolder"

, CStr(ControlX.CurrentFolder), INIFile
WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".RootFolder"

, CStr(ControlX.RootFolder), INIFile
' Usually will not be saved
Case "TextBox"
If SaveOthers = True And ControlX.PasswordChar = "" Then ControlX_Val = ControlX.Text
Case "ComboBox"
ControlX_Val = ControlX.Text
End Select
' Save the values for each control if there is one associated with it
' But first check if the control is part of an array
On Error Resume Next
If (Not ControlX.Index <> ""

Then
If ControlX_Val <> "" Or ControlX_Type = "TextBox" Or ControlX_Type = "ComboBox" Then WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & ".Value"

, CStr(ControlX_Val), INIFile
Else
If ControlX_Val <> "" Or ControlX_Type = "TextBox" Or ControlX_Type = "ComboBox" Then WritePrivateProfileString "Control Data", CStr(frm.Name & "." & ControlX.Name & "(" & ControlX.Index & "

" & ".Value"

, CStr(ControlX_Val), INIFile
End If
Next i
End Sub
Public Sub INI_SaveForm(ByVal frm As Form, Optional ByVal INIFile As String, Optional ByVal SaveOthers As Boolean)
' This function calls it's 3 child functions
' Create a generic INI name from the App title
If INIFile = "" Then INIFile = App.path & "\" & App.Title & ".ini"
Call INI_SaveFormPos(frm, INIFile)
Call INI_SaveControlPos(frm, INIFile)
Call INI_SaveControlValues(frm, INIFile, SaveOthers)
End Sub
Public Sub INI_SaveFormPos(ByVal frm As Form, ByVal INIFile As String)
' Function: INI_SaveFormPosition
'
' Place in Form_Unload to save the form's position and size
' so you can retrieve them in Form_Load with INI_LoadFormPosition
' We don't want to save data when the form is minimized or
' maximized because we get strange numbers.
If frm.WindowState = 1 Then Exit Sub
If frm.WindowState = 0 Then
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".Left", CStr(frm.Left), INIFile) ' Form.Left
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".Top", CStr(frm.Top), INIFile) ' Form.Top
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".Height", CStr(frm.Height), INIFile) ' Form.Height
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".Width", CStr(frm.Width), INIFile) ' Form.Width
End If
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".Tag", CStr(frm.Tag), INIFile) ' Form.Tag
If frm.WindowState = vbMaximized Then ' Form.WindowState
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".WindowState", CStr(frm.WindowState), INIFile)
Else
Call WritePrivateProfileString("Form Data", CStr(frm.Name) & ".WindowState", "", INIFile)
End If
End Sub
Public Sub INI_Write(ByVal Section As String, ByVal KeyName As String, ByVal vValue As Variant, Optional ByVal INIFile As String)
' Function: INI_Write
'
' Writes a value to an INI
'
' [Section]
' KeyName = Value
' Create a generic INI name from the App title
If INIFile = "" Then INIFile = App.path & "\" & App.Title & ".ini"
Call WritePrivateProfileString(Section, CStr(KeyName), CStr(vValue), INIFile)
End Sub