Программирование на Visual Basic | Microsoft Access, Excel, Word

В этом разделе сайта находятся примеры из сборника программ "Архив файлов на Microsoft Access". В нем рассказывается о программировании форм, отчетов, таблиц и других объектов. Используйте этот архив для изучения работы с приложением Microsoft Office Access и программированием на Visual Basic for Application. Тем кто уже знаком с VBA, используйте поиск для нахождения кодов. Наберите, например, DAO, ADO, Recordset и найдете нужную ссылку для решения проблемы с программированием

Microsoft Access. Как изменить размеры листа отчета

16. Используя специальное свойства отчетов Access, где можно указать специальную структуру параметров для печати, Вы сможете из Access управлять размерами бумаги для печати.

Option Compare Database
Option Explicit

Private Type str_DEVMODE
    RGB As String * 94 'Промежуточная переменная для копирования
End Type

'Полное описание структуры дано в модуле: p001.mdb
Private Type type_DEVMODE
    strDeviceName As String * 16
    intSpecVersion As Integer
    intDriverVersion As Integer
    intSize As Integer
    intDriverExtra As Integer
    lngFields As Long
    intOrientation As Integer
    intPaperSize As Integer
    intPaperLength As Integer
    intPaperWidth As Integer
    intScale As Integer
    intCopies As Integer
    intDefaultSource As Integer
    intPrintQuality As Integer
    intColor As Integer
    intDuplex As Integer
    intResolution As Integer
    intTTOption As Integer
    intCollate As Integer
    strFormName As String * 16
    lngPad As Long
    lngBits As Long
    lngPW As Long
    lngPH As Long
    lngDFI As Long
    lngDFr As Long
End Type

'==============================================================
' Открытие отчета
Private Sub Form_Open(Cancel As Integer)
    funChangeReport False
End Sub

'==============================================================
' Открыть отчет
Private Sub butChange_Click()
    On Error GoTo 999
    DoCmd.OpenReport "Пример 16", acViewPreview 'Открываем конструктор отчета
    Exit Sub
999:
    MsgBox Err.Description
    Err.Clear
End Sub

'==============================================================
' Изменяем размеры отчета
Private Sub myWidth_AfterUpdate()
    funChangeReport True
End Sub

'==============================================================
' Изменяем размеры отчета
Private Sub myLength_AfterUpdate()
    funChangeReport True
End Sub

'==============================================================
' Изменяем размеры отчета
'
Private Sub funChangeReport(boolChange As Boolean)
    Dim DevString As str_DEVMODE
    Dim DM As type_DEVMODE
    Dim strDevModeExtra As String
    Dim rpt As Report
    On Error GoTo 999
    DoCmd.OpenReport "Пример 16", acDesign 'Открываем конструктор отчета
    Set rpt = Reports("Пример 16") 'Определяем адрес отчета
    If Not IsNull(rpt.PrtDevMode) Then
        strDevModeExtra = rpt.PrtDevMode
        DevString.RGB = strDevModeExtra 'Структура отчета
        LSet DM = DevString 'Заполняем структуру
        If boolChange = True Then 'Изменение отчета
            On Error Resume Next
            rpt.Width = 32000
            Err.Clear
            DM.lngFields = DM.lngFields Or _
              DM.intPaperSize Or DM.intPaperLength Or DM.intPaperWidth
            DM.intPaperSize = 256 'Устанавливаем тип листа
            DM.intPaperWidth = Me.myWidth * 10 'Новая ширина
            DM.intPaperLength = Me.myLength * 10 'Новая длина
            LSet DevString = DM  'Обновляем свойство
            Mid(strDevModeExtra, 1, 94) = DevString.RGB
            rpt.PrtDevMode = strDevModeExtra
            DoCmd.Close acReport, "Пример 16", acSaveYes 'Закрываем отчет
        Else 'Отображение данных
            Me.myWidth = DM.intPaperWidth / 10 'Ширина
            Me.myLength = DM.intPaperLength / 10 'Ширина
            DoCmd.Close acReport, "Пример 16" 'Закрываем отчет
        End If
    End If
    Exit Sub
999:
    MsgBox Err.Description
End Sub

Microsoft Access. Вывод отчета в две колонки

17. Это свойство вывода на печать поможет напечатать отчет в несколько колонок (как на газетном листе). Настраивается через конструктор.

Option Compare Database
Option Explicit

Private Type str_DEVMODE
    RGB As String * 94 'Промежуточная переменная для копирования
End Type

'Полное описание структуры дано в модуле: p001.mdb
Private Type type_DEVMODE
    strDeviceName As String * 16
    intSpecVersion As Integer
    intDriverVersion As Integer
    intSize As Integer
    intDriverExtra As Integer
    lngFields As Long
    intOrientation As Integer
    intPaperSize As Integer
    intPaperLength As Integer
    intPaperWidth As Integer
    intScale As Integer
    intCopies As Integer
    intDefaultSource As Integer
    intPrintQuality As Integer
    intColor As Integer
    intDuplex As Integer
    intResolution As Integer
    intTTOption As Integer
    intCollate As Integer
    strFormName As String * 16
    lngPad As Long
    lngBits As Long
    lngPW As Long
    lngPH As Long
    lngDFI As Long
    lngDFr As Long
End Type

'==============================================================
' Открытие отчета
Private Sub Form_Open(Cancel As Integer)
    funChangeReport False
End Sub

'==============================================================
' Открыть отчет
Private Sub butChange_Click()
    On Error GoTo 999
    DoCmd.OpenReport "Пример 16", acViewPreview 'Открываем конструктор отчета
    Exit Sub
999:
    MsgBox Err.Description
    Err.Clear
End Sub

'==============================================================
' Изменяем размеры отчета
Private Sub myWidth_AfterUpdate()
    funChangeReport True
End Sub

'==============================================================
' Изменяем размеры отчета
Private Sub myLength_AfterUpdate()
    funChangeReport True
End Sub

'==============================================================
' Изменяем размеры отчета
'
Private Sub funChangeReport(boolChange As Boolean)
    Dim DevString As str_DEVMODE
    Dim DM As type_DEVMODE
    Dim strDevModeExtra As String
    Dim rpt As Report
    On Error GoTo 999
    DoCmd.OpenReport "Пример 16", acDesign 'Открываем конструктор отчета
    Set rpt = Reports("Пример 16") 'Определяем адрес отчета
    If Not IsNull(rpt.PrtDevMode) Then
        strDevModeExtra = rpt.PrtDevMode
        DevString.RGB = strDevModeExtra 'Структура отчета
        LSet DM = DevString 'Заполняем структуру
        If boolChange = True Then 'Изменение отчета
            On Error Resume Next
            rpt.Width = 32000
            Err.Clear
            DM.lngFields = DM.lngFields Or _
              DM.intPaperSize Or DM.intPaperLength Or DM.intPaperWidth
            DM.intPaperSize = 256 'Устанавливаем тип листа
            DM.intPaperWidth = Me.myWidth * 10 'Новая ширина
            DM.intPaperLength = Me.myLength * 10 'Новая длина
            LSet DevString = DM  'Обновляем свойство
            Mid(strDevModeExtra, 1, 94) = DevString.RGB
            rpt.PrtDevMode = strDevModeExtra
            DoCmd.Close acReport, "Пример 16", acSaveYes 'Закрываем отчет
        Else 'Отображение данных
            Me.myWidth = DM.intPaperWidth / 10 'Ширина
            Me.myLength = DM.intPaperLength / 10 'Ширина
            DoCmd.Close acReport, "Пример 16" 'Закрываем отчет
        End If
    End If
    Exit Sub
999:
    MsgBox Err.Description
End Sub

Microsoft Access. Добавление текстовых меток в отчет

10. Этот пример показывает, как можно добавить в отчет текст, например, комментарий расположенный не в таблице, а некотором месте.

Private Sub ОбластьДанных_Print(Cancel As Integer, PrintCount As Integer)
    funDrawText Me, 2700, "Наименование", "Распродажа" 'Добавляем в ячейку текст
    funDrawText Me, 50, "Цена", "Новая" 'Добавляем в ячейку текст
End Sub

'===============================================================
' Рисуем в поле текст strCaption в соответствии с условием
'
Private Function funDrawText(rpt As Report, pos As Single, strField As String, strCaption) As Long
Dim c As Control, h As Integer
        Set c = rpt.Section(acDetail).Controls(strField)
        h = rpt.FontSize 'Начальная высота шрифта
        If c  30 Then 'Условие для поля
            rpt.ScaleMode = 1 'Назначаем масштаб в твипах
            rpt.FontName = c.FontName  'Назначаем шрифт ячейки
            rpt.FontSize = 7  'Назначаем высоту текста
            rpt.ForeColor = RGB(255, 0, 0) 'Назначаем цвет
            rpt.CurrentX = pos + c.Left 'x координата текста в твипах
            rpt.CurrentY = 0 'y координата текста
            rpt.Print strCaption 'Печататем текст
        End If
        'Пример другого поля
        If strField = "Наименование" Then
            rpt.FontSize = 7  'Назначаем высоту текста
            rpt.ForeColor = RGB(0, 0, 255) 'Назначаем цвет
            rpt.CurrentX = pos + c.Left 'x координата текста в твипах
            rpt.Print strCaption 'Печататем текст
        End If
        
        rpt.FontSize = h 'Возвращаем размер шрифта для отчета
End Function

Microsoft Access. Добавление поля в отчет mde файла

11. Используя этот пример, Вы можете добавить поля даже в файлы, которые не изменяются в конструкторе.

Dim rstRpt As Recordset 'Запрос отчета
Dim x0 As Single 'Крайняя правая точка

'===============================================================
' Открываем запрос отчета и определяем параметры секции
Private Sub Report_Open(Cancel As Integer)
Dim dbs As Database, c As Control
    Set dbs = CurrentDb 'Выбираем базу данных
    Set rstRpt = dbs.OpenRecordset(Me.RecordSource) 'Открываем запрос
    'Находим последнее поле в отчете
    x0 = 0 'Инициализация
    For Each c In Me.Section(acDetail).Controls 'Просматриваем всю секцию
       If x0  c.Left + c.Width Then _
               x0 = c.Left + c.Width 'Крайняя правая точка в отчете
    Next c
End Sub

'===============================================================
' Находим запись отчета и печатаем текст
'
Private Sub ОбластьДанных_Print(Cancel As Integer, PrintCount As Integer)
Dim rpt As Report
    On Error GoTo 999
    'Находим в запросе нужную запись
    rstRpt.FindFirst "[Номенклатура]="  Me.Controls("Номенклатура")
    'Форматируем поле и добавляем в отчет после всех полей
    funDrawControl Me, 567 * 2, Format(rstRpt!Цена, "# ##0.00") 'Добавляем в ячейку текст
999:
    Err.Clear
End Sub

'===============================================================
' Рисуем элемент управления для отчета
'   myWidth - ширина поля
'   strDate - данные поля
'   Внимание! TextWidth может вернуть неправильный результат,
'             требуется пакет обновления SR-1
Private Function funDrawControl(rpt As Report, myWidth As Single, strDate) As Long
Dim c As Control
    
    'Пример текста в поле, который строится по образцу
    'Set c = Me.Section(acDetail).Controls("Номенклатура") 'Образец шрифта
    'Me.FontName = c.FontName  'Назначаем шрифт ячейки
    'Me.FontSize = c.FontSize  'Назначаем высоту текста
    'Me.ScaleMode = 1 'Назначаем масштаб в твипах
    
    'Расчитываем позицию текста и печаем его
    rpt.CurrentY = (rpt.Height - rpt.TextHeight("0")) / 2 'y-координата текста
    rpt.CurrentX = x0 + myWidth - rpt.TextWidth(strDate) 'x-координата текста
    rpt.ForeColor = RGB(255, 0, 0) 'Цвет текста
    rpt.Print strDate 'Печатаем текст
    
    'Рисуем прямоугольник вокруг поля
    rpt.ForeColor = RGB(255, 0, 0) 'Назначаем цвет
    rpt.Line (x0, 0)-(x0 + myWidth, rpt.Height), , B 'Прямоугольник
End Function

'===============================================================
' Закрываем запрос отчета
Private Sub Report_Close()
    rstRpt.Close
End Sub

Microsoft Access. Встроенные SELECT запросы

Использование встроенных запросов итогда бывает оправданным, если у Вас нет временных таюлиц. Хотя для больших и перегруженных информацией баз данных использование их не рекомендуется. В общем применяйте такие запросы без сортировки, тогда скорость их выполнения будет высокой.

SELECT Данные.Дата, Данные.КурсUSD, 
  (select count(*) from [Данные]) AS ЧислоКниг FROM 
            Данные, Данные AS Данные_1, [Пример 01];

Microsoft Access. Группировка записей в запросах

Когда Вам надо сгруппировать записи в запросах, например, найти сумму в колонке таблицы, то используйте вместе SELECT ключевое слово GROUP BY

-- Использование группировки
SELECT First(Книга) as Книги, avg(СуммаРуб) as [Средняя Цена] FROM [Данные] GROUP BY Книга

-- Выборка после группировки
SELECT First(Книга) as Книги, Avg(СуммаРуб) as [Средняя Цена] FROM [Данные] GROUP BY Книга 
HAVING Avg(СуммаРуб)350

Microsoft Access. Переменная высота строк в отчете

09. Программа построения табличных отчетов от Microsoft составлена так, что при изменении данных (1 строка, 2 строки) они могут не отображаться, т.к. в конструкторе эта высота уазывается жестко. Этот метод позволяет Вам обойти недостаток модуля отчетов от Microsoft и строить таблицы разной высоты.

Private Sub ОбластьДанных_Print(Cancel As Integer, PrintCount As Integer)
Dim h As Single
    h = funGetHeight(Me.Section(acDetail)) 'Опредеяем высоту строки
    funDrawBox Me, h, 1 'Оформляем секцию с толщиной линий = 1
End Sub

'===============================================================
' Расчет высоты строки в секции в зависимости от форматирования
' поля отчета, например, TextBox
'
Private Function funGetHeight(sec As Section) As Single
Dim c As Control
     funGetHeight = 0 'назначаем высоту ячейки
     For Each c In sec.Controls 'Просматриваем все поля отчета
         If funGetHeight  c.Height Then _
            funGetHeight = c.Height 'Возвращаем максимальную высоту
     Next c 'Следующее поле
End Function

'===============================================================
' Перед началом печати рисуем для каждого поля прямоугольник
'
Private Sub funDrawBox(rpt As Report, h As Single, w As Integer)
Dim c As Control
     rpt.DrawWidth = w 'Толщина линии
     'Красный цвет прямоугольника
     rpt.ForeColor = RGB(255, 0, 0) 'RED, GREEN, BLUE
     'Просматриваем все поля отчета
     For Each c In rpt.Section(acDetail).Controls
         rpt.Line (c.Left, c.Top)-(c.Left + c.width, h), , B 'Прямоугольник
     Next c
End Sub

Microsoft Access. Сортировка записей DESC, ASC

DESC - сортирует записи по убыванию, а ASC по возрастанию. Как будут сортироваться записи зависит и от настроек самой базы.

-- Сортировка по возрастанию и убыванию
SELECT * FROM [Данные] ORDER BY [СуммаРуб] ASC, [КурсUSD] DESC;

Microsoft Access. Использование FORMAT

Format встроенная функция в VBA, имеет много возможностей для форматирования различных данных типа дата, число и т.п. Применяется она только в mdb файлах. Для adp проектов ее использовать нельзя.

-- Форматирование даты
SELECT Продукт, Цена, Format(Now(),'YYYY-MM-DD') as ДатаЗаказа FROM Продукты;

-- Форматирование цен
SELECT *, "USD="  Format([СуммаРуб]/[КурсUSD],"0.00") as [СуммаUSD] FROM [Данные];

Microsoft Access. Использование условий WHERE

Применяя в запросах WHERE (ГДЕ) Вы сможете отобрать нужные записи. Обратите внимание на то, как отбираются данные по дате и используется ключевое слово LIKE

-- Условие выборки по дате, книге и цене
SELECT * FROM  [Данные] WHERE [Дата]=#11/15/2000# and ([Книга]='Война и Мир')
 and ([СуммаРуб]=500);

-- Возврат книг по названию, где есть буква В
SELECT * FROM [Данные] WHERE [Книга] LIKE 'В*'