Lost your password?


Хитрости »
Основные понятия (27)
Сводные таблицы и анализ данных (10)
Графики и диаграммы (5)
Работа с VB проектом (12)
Power BI и Power Query (23)
Условное форматирование (5)
Списки и диапазоны (5)
Макросы(VBA процедуры) (68)
Разное (43)
Баги и глюки Excel (5)

Как из VBA выбрать и установить принтер для Excel

Основная задача кодов Visual Basic for Applications - автоматизация. И задачи зачастую бывают самые разные. Одна из таких задач - печать листов или ячеек по условию или в цикле. Сама по себе отправка на печать листа или диапазона не представляет сложностей, это легко можно записать макрорекордером и вставить в свой код. Выглядеть это будет примерно так:

Sub Макрос1()
    ActiveWindow.SelectedSheets.PrintOut Copies:=1, Collate:=True, IgnorePrintAreas:=False
End Sub

Но зачастую необходимо не просто отправить на печать, а еще и на определенный принтер. При этом не просто указать другой принтер, а дать возможность выбрать принтер пользователю, не задавая его жестко в коде. Ведь у разных пользователей могут быть разные принтеры подключены. Часто такое необходимо при печати этикеток или других специфических материалов(открытки, буклеты и т.п.) потому, что для них как правило используют не стандартный офисный черно-белый лазерный принтер, а некий более продвинутый с возможностью заправки специфических листов. Как видно из кода выше - там нет и малейшего намека на указание принтера. Хотя в принципе параметр такой есть - ActivePrinter.
На самом деле есть несколько вариантов выбора принтера, но я покажу самый надежный (как оказалось) и в тоже время самый простой - через стандартный диалог выбора принтеров:

Sub ShowPrinters()
    Application.Dialogs(xlDialogPrinterSetup).Show
End Sub

Этот диалог после вызова автоматически назначает выбранный в нем принтер принтером по умолчанию для печати. Т.е. теперь чтобы мы ни отправили на печать будет отправлено на этот принтер. Все бы хорошо, но тут появляется небольшая проблема: в этом случае у нас не только из кодов будет идти печать на этот принтер, но и при обычной печати. А это нам не надо, ведь тогда даже 100500 каких-то "левых" документов вместо печати на лазерном черно-белом будут распечатаны на офигительном цветном. За такое можно и премии лишиться :) Конечно, можно каждый раз перед ручной печатью выставлять нужный принтер. Но во-первых об этом можно просто забыть, а во-вторых - как только изменим один раз, нам придется перед печатью из кода опять менять принтер. Замкнутый круг и автоматизацией вообще не пахнет.
Поэтому лучше чуть-чуть все усложнить и при каждой печати из кода VBA назначать нужный принтер. Я заготовил универсальный код, который отправляет на печать либо активный лист, либо указанный диапазон ячеек именно на выбранный для печати из VBA принтер. При желании и умении код можно доработать для печати листов и диапазонов в цикле. Но основной упор сделан на выбор принтера для печати только из кода. Т.е. при первом запуске кода печати будет предложено выбрать принтер:
Окно выбора принтера
Если принтер будет выбран и нажата кнопка Ок, то принтер будет запомнен и сразу после этого сброшен и установлен заново тот принтер, который был изначально установлен для печати. Однако при печати из кода будет использован именно выбранный принтер, а не тот, который будет применяться при ручной печати.
Т.е. при ручной печати будет один принтер, а при печати из кода - другой.

Option Explicit
'глобальная переменная для хранения значения выбранного принтера при печати из VBA
Public sNowPrinter As String
'---------------------------------------------------------------------------------------
' Procedure : ChangePrinter
' Author    : The_Prist(Щербаков Дмитрий)
' Purpose   : Функция выбора принтера для печати из кода VBA
'---------------------------------------------------------------------------------------
Sub ChangePrinter()
    sNowPrinter = "Set"
    Dim v, s
    'запоминаем текущий принтер, чтобы можно было вернуть его после выбора
    s = Application.ActivePrinter
    'показываем окно выбора принтера
    v = Application.Dialogs(xlDialogPrinterSetup).Show
    'если принтер был выбран - запоминаем выбор
    If v = True Then
        sNowPrinter = Application.ActivePrinter
    End If
    'возвращаем принтер по умолчанию, чтобы стандартная печать шла на него
    Application.ActivePrinter = s
End Sub
'---------------------------------------------------------------------------------------
' Procedure : DoPrint
' Author    : The_Prist(Щербаков Дмитрий)
' Purpose   : Функция печати указанного кол-ва копий указанного диапазона ячеек
'             rr       - ссылка на диапазон ячеек - Range("A1:B10")
'                        если не указан - на печать выводится весь активный лист
'             lCopies  - целое число, указывающее сколько копий выводить на печать
'                        если не указан - на печать выводится одна копия
'---------------------------------------------------------------------------------------
Function DoPrint(Optional rr As Range = Nothing, Optional lCopies As Long = 1)
    Dim sActPrinter As String
    'проверяем, установлен ли ранее принтер для печати
    If sNowPrinter = "" Or sNowPrinter = "Set" Then
        'если нет - вызываем процедуру выбора принтера
        Call ChangePrinter
        'если выбранный принтер не был выбран(нажали Отмена), то используем текущий
        If sNowPrinter = "Set" Then
            If MsgBox("Не выбран принтер для печати. Использовать установленный в качестве активного?", vbCritical + vbYesNo, "www.excel-vba.ru") = vbNo Then
                Exit Function
            End If
            sActPrinter = Application.ActivePrinter
        Else
            sActPrinter = sNowPrinter 'получаем выбранный в окне принтер
        End If
    End If
 
    If rr Is Nothing Then
        'печатаем активный лист на выбранном принтере
        ActiveSheet.PrintOut Copies:=lCopies, ActivePrinter:=sActPrinter
    Else
        'печатаем указанный диапазон ячеек на выбранном принтере
        rr.PrintOut Copies:=lCopies, ActivePrinter:=sActPrinter
    End If
End Function

Функция ChangePrinter показывает диалог выбора принтера и назначает выбранный принтер принтером по умолчанию, запоминает выбор и отменяет его, возвращая принтер до вызова функции.
Функция DoPrint непосредственно отправляет на печать именно на выбранный принтер. Если принтер ранее не был выбран, то сначала будет вызвана функция ChangePrinter.
При этом функция DoPrint имеет два необязательных аргумента:

  • rr - ссылка на диапазон ячеек (например Selection для вывода на печать выделенного диапазона или Range("A1:B10") для вывода на печать конкретного диапазона, вне зависимости от того, какой выделен). Если этот аргумент не указан, то на печать выводится весь активный лист.
  • lCopies - целое число, указывающее сколько копий выводить на печать. Если аргумент не указан - на печать выводится одна копия.
  • В процедуре ниже на печать выводится выделенный диапазон с количеством печатных копий листов - 2.

    Sub TestPrint()
        DoPrint Selection, 2
    End Sub

    Так же в функции DoPrint можно заменить ActiveSheet на конкретный лист. Например: Workbooks("Книга2.xlsx").Sheets("Лист3"). Книга Книга2.xlsx должна быть открыта и должна содержать лист с именем Лист3.

    В приложенном к статье файле так же есть пример печати по очереди каждой из этикеток, расположенных в два ряда:
    Этикетки на листе
    Хотя практичнее автоматически заполнять только один шаблон этикетки в цикле разными данными и его отправлять на печать.

    Скачать пример:

      Выбор принтера (74,5 KiB, 1 661 скачиваний)


    Статья помогла? Поделись ссылкой с друзьями!
      Плейлист   Видеоуроки

    Поиск по меткам

    Access apple watch Multex Power Query и Power BI VBA управление кодами Бесплатные надстройки Дата и время Записки ИП Надстройки Печать Политика Конфиденциальности Почта Программы Работа с приложениями Разработка приложений Росстат Тренинги и вебинары Финансовые Форматирование Функции Excel акции MulTEx ссылки статистика
    Обсуждение: 4 комментария
    1. Антон:

      Здравствуйте! Столкнулся с проблемой, после установки любого принтера в системе пользователя один из файлов Excel при запуске начинает обращаться к подсистеме печати, и показывает окно выбора принтеров, точно такое же как у Вас в статье, далее все запускается в штатном режиме, но не надолго, при попытке выделить ячейки и скопировать их появляется сообщение о том, что печать невозможна так как буфер переполнен, при том что я не пытаюсь печатать, а всего лишь пытаюсь скопировать ячейки, это делает работу с файлом просто навсего невозможной. Запуск на другой машине привел к тому же самому, и на той и на другой установлен Office 2010, могу сделать вывод что дело в файле, но куда копать не знаю, он очень объемный и обладает кучей формул, но без макросов и как я понял без VBA скриптов. Просмотрел данный файл в редакторе VBA ничего не нашел, как избавиться от этой проблемы?

      • Антон, в данной ситуации могу посоветовать лишь одно: отключить принтер от ПК, сбросить полностью параметры печати в этой книге, а так же удалить все представления(Вид -Представления).
        Если книга в общем доступе - сначала снять общий доступ, удалив журнал и представления.

    2. Михаил:

      Доброго времени суток. Функция ChangePrinter работает отлично, спасибо Вам, Ваши статьи очень информативны. Однако у меня проблема вот в чем. Функция выбора принтера мне нужна не для выбора принтера по принципу хочу \не хочу, а по принципу, работает\не работает. Поэтому, Ваша форма позволяет мне выбрать принтер, но сначала я должен определить какой из принтеров сейчас в сети, а это для обычного юзера может стать неразрешимой задачей) Есть ли возможность добавить в форму статус принтера? Или это "много кода"))? В любом случае, Спасибо.

    3. Александр:

      Здравствуйте!
      Есть ли возможность создать TextBox в UserForm, и в зависимости от числа в TextBox (1, 2, 3...), выводить на печать соответствующее число копий?

    Поделитесь своим мнением

    Комментарии, не имеющие отношения к комментируемой статье, могут быть удалены без уведомления и объяснения причин. Если есть вопрос по личной проблеме - добро пожаловать на Форум


    Для оформления сообщений Вы можете использовать следующие тэги:
    <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

    Тренинги

    Заказать
    Юридическая информация

    Использование материалов сайта

    Политика Конфиденциальности

    ИП Щербаков Дмитрий Валентинович
    ОГРНИП: 318502700083307
    ИНН: 504013350772

    Наши партнеры

    Перейти

    Счетчики

    Рейтинг@Mail.ru Яндекс.Метрика
    © 2024 Excel для всех   Войти