VISXAN Пользователь Сообщений: 135 |
#1 10.09.2013 15:07:04 Здравствуйте. Подскажите пожалуйста, как открыть книгу через VBA, чтоб она открывалась в фоне, а не становилась активной. Код ниже открывает книгу и делает ее активной. А надо чтобы оставалась открытой в фоне.
|
||
Михаил С. Пользователь Сообщений: 10514 |
#2 10.09.2013 15:12:19
Изменено: Михаил С. — 10.09.2013 15:13:12 |
||
Юрий М Модератор Сообщений: 60575 Контакты см. в профиле |
Или активировать затем окно «основной» книги. |
VISXAN Пользователь Сообщений: 135 |
Понятно. Спасибо. Сделал книгу изначально скрытой, теперь при открытии она не мешает. Но в конце макроса мне надо написать код, чтоб сделать ее видимой. |
ber$erk Пользователь Сообщений: 2735 |
а как вы книгу делаете невидимой? Вот и идите от обратного Учимся сами и помогаем другим… |
VISXAN Пользователь Сообщений: 135 |
#6 10.09.2013 16:16:05 Невидимой сделал вручную и сохранил. А теперь с помощью кода надо сделать видимой.
не получается. Изменено: VISXAN — 10.09.2013 16:21:08 |
||
Hugo Пользователь Сообщений: 23251 |
#7 10.09.2013 16:20:38
|
||
VISXAN Пользователь Сообщений: 135 |
#8 10.09.2013 16:29:35
этот код открывает книгу скрытой (даже если она такой не является), поэтому от него отказался.
Далее, после определенной процедуры VBA (заполнения данной книги данными), нужно сделать книгу видимой. Этот код не помогает:
Изменено: VISXAN — 10.09.2013 16:31:03 |
||||||
KuklP Пользователь Сообщений: 14868 E-mail и реквизиты в профиле. |
#9 10.09.2013 16:39:06 Вы сами себя слышите?
Поэтому открываю книгу и тут же делаю ее невидимой
Мазохисты всех стран — объединяйтесь. А на вопрос ответил Hugo. Я сам — дурнее всякого примера! … |
||||
Hugo Пользователь Сообщений: 23251 |
Т.к. форум тормозит с screenupdating — диалог получается интересным |
VISXAN Пользователь Сообщений: 135 |
KuklP, да не делаю я ее скрытой. Она сама скрытая, куда ее еще скрывать. |
Михаил С. Пользователь Сообщений: 10514 |
#12 10.09.2013 16:49:43
Изменено: Михаил С. — 10.09.2013 16:52:46 |
||
VISXAN Пользователь Сообщений: 135 |
Михаил С., спасибо Вам большое. Четко и просто. |
KuklP Пользователь Сообщений: 14868 E-mail и реквизиты в профиле. |
#14 10.09.2013 16:57:50 Миша, мож так?
Я сам — дурнее всякого примера! … |
||
Без разницы. Но так наверно проще. Изменено: Михаил С. — 10.09.2013 17:02:47 |
|
VISXAN Пользователь Сообщений: 135 |
#16 10.09.2013 17:03:18 А что делает этот код?
|
||
удаляет GetObject. зы. ежели что — я сам ангелького не понимаю. Пользуюсь переводчиком Изменено: Михаил С. — 10.09.2013 17:08:35 |
|
VISXAN Пользователь Сообщений: 135 |
Ах да, ступил. Удаляет присвоенное значение. Ну или присваивает ничего)) Изменено: VISXAN — 10.09.2013 17:30:37 |
Максим Пользователь Сообщений: 268 |
#19 09.04.2019 20:00:14 подскажите пожалуйста как сделать чтобы не моргало на
Application.ScreenUpdating = False — не помогает Изменено: Максим — 09.04.2019 22:01:33 |
||
Максим Пользователь Сообщений: 268 |
#20 09.04.2019 20:42:23 пока решил так:
но что-то кажется что слишком тяжёлая артиллерия Изменено: Максим — 09.04.2019 20:42:55 |
||
Как при окрытии книги сделать ее «невидимой»? |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
||||||||
Ответить |
Время прочтения: 4 мин.
- в
каких случаях важно запускать макрос в «фоновом» режиме и почему необходимо
реагировать на действия пользователя; - пример
реализации работы «фонового» приложения (проверено на версиях c 2007); - актуализация
программного кода в приведенном примере к версиям 2013-2016.
Зачем скрывать приложение с экрана?
Приложение с
выполняющимся макросом имеет смысл переводить в «фоновый» режим, если
предполагается, что пользователь продолжит работать за компьютером, при этом
без необходимости контролировать работу макроса: скрытое с экрана приложение не
вызовет раздражение пользователя «непрорисованной» экранной областью, не
потребует ресурсов для такой прорисовки, не будет подвержено воздействию
пользователя на формирующуюся книгу (например, активацией объектов книги, использованием
буфера памяти приложения).
Как
реализовать?
Объектная модель Excel позволяет работать с несколькими книгами
(объектами Workbook)
в одном приложении (в объекте Application).
А значит, приложение, скрытое с экрана для выполнения макроса, может быть
вызвано операционной системой для попытки открыть в нем указанный пользователем
файл. В результате, попытка открытия файла либо будет безрезультатной, либо
пользователю придется ожидать окончания выполнения скрытого макроса для
возможности приступить к работе с файлом.
- Чтобы скрытое приложение могло реагировать должным образом на загрузку пользовательского файла, необходимо указать порядок действий в событиях приложения (события объекта Application) – реализую их в отдельном классе.
ExAppClass (class module)
'Переменная уровня приложения
Private WithEvents ExApp As Excel.Application
'Указывает объект для управления
Public Function SetExApp(ByVal NewExApp As Excel.Application) As Excel.Application
Set SetExApp = Nothing
If (NewExApp Is Nothing) Then
Exit Function
End If
If (Not ExApp Is Nothing) Then
Call ToNothingApp
End If
Set ExApp = NewExApp
Set SetExApp = ExApp
End Function
'Возвращает ссылку на управляемый объект
Public Function GetExApp() As Excel.Application
Set GetExApp = ExApp
End Function
'Заново открывает пользовательскую книгу в новом приложении
Private Sub ExApp_WorkbookOpen(ByVal Wb As Workbook)
Dim TransApp As Excel.Application
Dim TransWbName As String
'Запоминаю
TransWbName = Wb.FullName
Wb.Close False
Set Wb = Nothing
'Открываю заново
Set TransApp = New Excel.Application
TransApp.Visible = True
TransApp.Workbooks.Open TransWbName
Set TransApp = Nothing
End Sub
'Заново создает пустую книгу в отдельном приложении
Private Sub ExApp_NewWorkbook(ByVal Wb As Workbook)
'Реализация аналогична процедуре ExApp_WorkbookOpen()
End Sub
'Заново открывает пользовательскую книгу в новом приложении с режимом просмотра
'(реализация процедуры требуется при наличие данного события в версии Excel)
Private Sub ExApp_ProtectedViewWindowOpen(ByVal Pvw As ProtectedViewWindow)
Dim TransApp As Excel.Application
Dim TransWbName As String
'Запоминаю
TransWbName = Pvw.Workbook.FullName
Pvw.Workbook.Close False
Pvw.Close
Set Pvw = Nothing
'Открываю заново
Set TransApp = New Excel.Application
TransApp.Visible = True
TransApp.ProtectedViewWindows.Open TransWbName
Set TransApp = Nothing
End Sub
'Уничтожает ссылку на приложение
Public Sub ToNothingApp()
If (Not ExApp Is Nothing) Then
ExApp.Visible = True
Set ExApp = Nothing
End If
End Sub
'Уничтожает объект, управляющий приложением
Private Sub Class_Terminate()
Call ToNothingApp
End Sub
Стоит отметить, что в
подобных задачах часто реализуются возможности для управления «своим» или
«чужим» запущенным приложением Excel,
определяется количество допустимых для обработки книг, список допустимых к
открытию книг.
- Для
скрытия приложения с экрана и запуска в нем требуемого функционала, добавляю
программный модуль.
ExecModule (module)
'"Захватывает" приложение и запускает искомый макрос
Public Sub Exec()
Dim clsProgApp As New ExAppClass
With clsProgApp
'Начинаю управлять «своим» приложением
Call .SetExApp(NewExApp:=ThisWorkbook.Application)
'Скрываю приложение
.GetExApp.WindowState = xlMinimized
.GetExApp.Visible = False
'Запускаю макрос с искомым функционалом
Call ResultRun(.GetExApp)
'Отображаю приложение с искомым результатом
.GetExApp.Visible = True
.GetExApp.WindowState = xlNormal
'Перестаю управлять объектом Application
Call .ToNothingApp
End With
Set clsProgApp = Nothing
End Sub
Private Function ResultRun(ByVal ManagerExApp As Excel.Application) As Boolean
'Здесь реализуется какой-либо искомый функционал...
'Продолжительный по времени функционал
'должен периодически вызывать функцию DoEvents
'для реагирования процесса на действия пользователя
End Function
Что
актуализировать?
Приложение Excel, начиная с версии 2013, позволяет
пользователю работать с книгами в отдельных окнах (реализуя Single Document Interface). При этом, книги
фактически, как и в прежних версиях, могут быть загружены в коллекцию одного
приложения. Потому приведенный пример программного кода в целом остается
работоспособным за исключением обнаруженных на практике «специфического поведения»
приложения.
При попытке закрыть вызванный пользователем файл, происходит обращение к скрытому приложению, в котором он в данный момент загружен. Важно временно отобразить скрытое приложение, перед закрытием файла. Иначе в памяти остаются «висеть» ссылки на объекты закрываемого файла. Приведу пример исправления события.
ExAppClass (class module)
'(Для интерфейса SDI) заново открывает пользовательскую книгу в новом приложении
Private Sub ExApp_WorkbookOpen(ByVal Wb As Workbook)
Dim TransApp As Excel.Application
Dim TransWbName As String
Dim AppVersion As Integer
Dim SDIversion As Integer: SDIversion = 15
With ExApp
AppVersion = Fix(Replace(.Version, ".", ","))
If (AppVersion >= SDIversion) Then
'Временно отображаю скрытое приложение
.Visible = True
End If
'Запоминаю
TransWbName = Wb.FullName
Wb.Close False
Set Wb = Nothing
If (AppVersion >= SDIversion) Then
'Скрываю приложение
.Visible = False
End If
End With
'Открываю заново
Set TransApp = New Excel.Application
TransApp.Visible = True
TransApp.Workbooks.Open TransWbName
Set TransApp = Nothing
End Sub
Всегда избегайте выбора или активации чего-либо, будь то ячейка, диапазон, лист или рабочая книга.
Когда вы пишете свой код, обращайтесь к
Workbooks("freds wrk").Worksheets("Start").Cells(1, 1)
Workbooks("freds wrk").Worksheets("Start").Range("A1")
Вы также можете использовать команду С, чтобы сделать ее короче.
With Workbooks("freds wrk").Worksheets("Start")
.Cells(1, 1)
.Range("A1")
end with
Когда ваш код выполняется, конечный пользователь просто начнет нажимать кнопки, а затем все пойдет не так, потому что то, что вы считаете активным, больше не активно. И то, что вы думаете, выбрано уже не так.
Проблемы усугубляются, когда вы начинаете вызывать sub в середине вашего кода. Как вы можете узнать, какой лист сейчас будет активным, а какой сейчас выбран подпунктом, который вы только что назвали.
А оператор with заставит ваш код работать быстрее. Книга объектов Excel, рабочий лист, ячейка и диапазон удивительно медленны для компьютера.
На чтение 8 мин. Просмотров 5.3k.
VBA Immediate Window является удивительным инструментом, который позволяет получить моментальные ответы о ваших файлах Excel, и быстро выполнить код. Он встроен в редактор Visual Basic и имеет множество различных применений, которые могут быть очень полезны при написании макросов, отладке кода и отображении результатов кода.
Каждый пользователь Excel может получить выгоду от Immediate Window, даже если вы не пишете макросы. Эта статья расскажет про 5 различных применений Immediate Window. Как только вы поймете возможности этого инструмента, вы будете использовать его постоянно.
Содержание
- Где находитсяImmediate Window?
- Эта пустая коробка волшебна!
- Открепить Immediate Window
- Заключение
Immediate Window
находится в окне редактора Visual Basic.
Самый быстрый способ добраться до Immediate Window — это:
- Нажмите Alt + F11 (удерживая клавишу Alt, затем нажмите клавишу F11) из любой места Excel. Откроется окно редактора Visual Basic. (Mac версия Fn + Alt + F11)
- Нажатие Ctrl + G открывает окно Immediate и помещает текстовый курсор в него. Начните вводить свой код. (Версия для Mac — Ctrl + Cmd + G)
Когда вы откроете VB Editor (Alt + F11 ), вы можете увидеть, что Immediate Window автоматически появляется в правом нижнем углу. Это его местоположение по умолчанию. Если его там нет, вы можете нажать Ctrl + G или
меню View> Immediate Window.
Эта пустая коробка волшебна!
Когда вы щелкнете внутри Immediate Window, вы увидите пустое
поле с мигающим текстовым курсором. На первый взгляд это не слишком увлекательно,
но Immediate Window может быть очень мощным и полезным инструментом.
Думайте об этом, как о пустой ячейке на листе. Довольно скучно, пока вы не добавите формулу, верно?
Итак, давайте рассмотрим 5 примеров, которые помогут вам извлечь максимальную пользу из этой волшебной коробки.
# 1 — Получить информацию об активной книге
Простейшее использование Immediate Window — это быстрое получение информации о Excel-файле, который в данный момент открыт и активен в фоновом режиме. Вы можете проверить любую строку кода VBA в Immediate Window, и она сразу же даст вам результат.
Например, чтобы узнать, сколько листов в активной книге, введите следующую строку кода в Immediate Window и нажмите клавишу «Enter».
?Activeworkbook.Worksheets.Count
Ответ будет отображен в следующей строке Immediate Window,
прямо под кодом.
Задайте вопрос, любой вопрос …
Помещение знака вопроса (?) в начале оператора говорит Immediate Window, что мы задаем ему вопрос и ожидаем результата.
В следующем скриншоте показано несколько примеров того, как мы можем использовать Immediate Window для получения значения, формата чисел и цвета заливки активной ячейки.
Обратите внимание, что Immediate Window отображает интеллектуальные подсказки в тот момент, когда я печатаю. Intellisense — это раскрывающееся меню, в котором отображаются свойства и методы объекта, на который я ссылаюсь. Это позволяет очень быстро и легко вводить код в Immediate Window.
# 2 — Выполнить строку кода VBA
Вам не нужно писать целый макрос, если вам достаточно выполнить одну строку кода в вашей книге.
Удалите знак вопроса в начале оператора, и Immediate Window выполнит эту строку кода.
Selection.HorizontalAlignment = xlCenterAcrossSelection
На изображении выше показано, как отформатировать выделенные ячейки с помощью выравнивания по центру выделения.
Вы также можете использовать следующую строку кода, чтобы сделать лист «очень скрытым».
Worksheets("Лист1").Visible = xlVeryHidden
Другой пример — скрыть содержимое ячейки, сделав цвет шрифта
таким же, как цвет заливки (фона).
Range("A1").Font.Color = Range("A1").Interior.Color
Я использую эту строку кода в инструменте оглавления Tab Hound, чтобы скрыть некоторые настройки, хранящиеся в ячейке A1. Даже если пользователь изменит цвет заливки листа, содержимое в ячейке A1 все равно будет скрыто после выполнения кода.
# 3 — Запустить макрос
Вы можете запустить макрос из Immediate Window, введя имя
макроса (процедура) и нажав Enter.
Конечно, вы также можете сделать это, нажав клавишу F5 или
кнопку «Выполнить макрос» в VB Editor, но что если ваш макрос содержит
аргументы?
Макрос не может быть запущен изнутри процедуры, если он содержит аргументы. Тем не менее, вы можете вызвать макрос из непосредственного окна.
Пример ниже представляет собой простой макрос, который вводит текущую дату (сейчас) в ячейку и меняет цвет шрифта на синий (Color = vbBlue). Этот макрос требует, чтобы для запуска ему было передано два аргумента: имя листа и адрес ячейки, где будет введена отметка даты.
Для такого макроса вы обычно будете вызывать его из другого
макроса и указывать аргументы в макросе, который его вызывает. Но если вы
просто хотите протестировать макрос, содержащий аргументы, вы можете
использовать Immediate Window для его вызова.
Это отлично подходит для написания и отладки кода. Возможно,
вы не захотите запускать весь стек процедур (макросов) в коде, но вы можете
использовать Immediate Window, чтобы вызывать только тот конкретный макрос, над
которым вы работаете.
В приведенном выше примере показано, как можно указать
аргументы после имени макроса. Для аргументов, которые являются строковыми
переменными (текст), вам необходимо заключить переменную в кавычки.
Как вы можете видеть на изображении, интеллектуальный помощник доступен в Immediate Window, что позволяет легко указать аргументы для макроса.
# 4 — Просмотр информации об отладке
Вы когда-нибудь видели в Интернете код VBA, в котором есть строка, подобная следующей?
Debug.Print xxxxx
«xxxxx» являются некоторой переменной, которую код вычисляет или производит.
Debug.Print говорит VBA напечатать эту информацию в Immediate Window. Это может быть полезно, когда вы хотите увидеть значение переменной в определенной строке вашего кода, без необходимости хранить переменную где-то в рабочей книге или показывать ее в окне сообщения. Это особенно полезно, когда вы пишете или отлаживаете код.
Пример ниже представляет собой макрос, который проходит по всем листам в книге и проверяет, является ли каждый лист пустым (не используется). Если лист пустой, он отображается в окне Immediate Window с помощью Debug.Print.
Конечная цель этого макроса может состоять в том, чтобы удалить все пустые листы в книге, но мы могли бы сначала протестировать код перед тем, как фактически удалить какие-либо листы.
Строка Debug.Print создает список пустых листов в Immediate Window, и затем мы можем вручную проверить каждый из этих листов, чтобы убедиться, что они действительно пустые.
# 5 — Получить или установить значение переменной
Immediate
Window также можно использовать для получения ответов о выполняемой в данный
момент процедуре (макросе). Если вы просматриваете свой код (F8) или добавляете
точку останова (F9) или добавляете строку STOP в свой код, тогда код будет
приостановлен. Когда код приостановлен, вы можете использовать Immediate
Window, чтобы получить информацию о любых переменных или объектах, на которые
есть ссылки в коде.
В следующем примере показан макрос, который создает список
всех листов в активной книге. Существует множество различных способов написания
этого кода, но в этом примере я использую переменную «lSht» в цикле «For Next»
для циклического перемещения по рабочим листам, а затем добавляю имя листа на
активный лист.
Я добавил точку останова (F9) в коде, чтобы приостановить
код при выполнении этой строки. Когда код приостановлен, Immediate Window можно
использовать для оценки или изменения переменных. На изображении выше я
использовал знак вопроса, чтобы проверить значение переменной lSht. Затем я
использовал переменную, чтобы получить имя листа, который в данный момент
обрабатывается в цикле.
Наконец, я изменил переменную lSht на 5, используя знак равенства (lSht = 5). Это эффективно пропустит некоторые листы в цикле, потому что я изменил переменную с 2 на 5.
Это простой пример, но Immediate Window может пригодиться при пошаговом выполнении кода.
Если вы хотите узнать, как я заставил Immediate Window
плавать поверх приложения Excel на некоторых скриншотах.
Этот скринкаст покажет вам, как вы можете отсоединить
Immediate Window.
Вот
пошаговые инструкции:
- Щелкните левой кнопкой мыши и удерживайте
верхнюю панель Immediate Window. - Перетащите его из окна VB Editor. Immediate
Window становится свободным плавающим окном, которое вы можете поместить поверх
Excel. - Чтобы повторно закрепить его, дважды щелкните на
верхней панели окна.
Вы можете сделать это с любым из окон в редакторе VB,
включая окна Project, Properties, Locals и Watch. Многие разработчики
настраивают VB Editor не так, как макет по умолчанию. Некоторые предпочитают,
чтобы окна проекта и свойств располагались справа, а не слева. Окно VB Editor
дает вам большую гибкость для настройки вашего представления.
Заключение
Immediate Window — очень универсальный инструмент, который действительно может помочь при написании и отладке макросов. Это отличный способ получить быстрые ответы о вашем файле или приложении. Если вы новичок в VBA, Immediate Window будет очень полезен, когда вы начнете изучать и писать код.