Компьютерный форум OSzone.net  

Компьютерный форум OSzone.net (http://forum.oszone.net/index.php)
-   Microsoft Office (Word, Excel, Outlook и т.д.) (http://forum.oszone.net/forumdisplay.php?f=115)
-   -   [решено] Проверка значения переменной wBook (http://forum.oszone.net/showthread.php?t=303987)

corbis 14-08-2015 19:57 2541727

Проверка значения переменной wBook
 
Задача такая:
Из одной книги перебрасываем данные в другую. Переброс может быть разовым или многоразовым.
Для этого есть кнопка, при нажатии на которую происходит копирование некоторых ячеек в активной строке.
Нужно проверить открыта ли вторая книга. Если открыта, то проверить: открыта она пользователем или из кода VBA.
Если пользователем, то просим закрыть (вдруг там данные нужные какие не сохранены), если из кода (значит, переменная уже инициализирована wBook = ActiveWorkbook ), тогда копируем.

Код:

Function IsBookOpen(wbFullName As String) As Boolean
    Dim iFF As Integer
    iFF = FreeFile
    On Error Resume Next
    Open wbFullName For Random Access Read Write Lock Read Write As #iFF
    Close #iFF
    IsBookOpen = Err
End Function

Private Sub Button_Click()
flag = 0
       
  If (IsBookOpen("C:\test.xlsx")) Then
          If wBook *не знаю, что тут проверить* Then
              MsgBox ("Закрой test'")
          Else
              MsgBox ("Можно копировать")
          End If
         
    Else
      Workbooks.Open Filename:="C:\test.xlsx"
      Set wBook = ActiveWorkbook
  End If
End Sub


NickM 14-08-2015 20:50 2541738

А если обойтись без проверки? Просто вывешивать сообщение, что книга будет закрыта с сохранением всех внесенных изменений, ожидать несколько секунд и в коде закрывать сохраняя изменения.

corbis 14-08-2015 20:52 2541740

а как закрыть книгу из кода, которую отрыл пользователь из проводника?

NickM 14-08-2015 21:26 2541747

Хмм, озадачили. Если смотреть на Ваш код, то проверка открытия как бы намекает, что книга может быть открыта из общего доступа с любого компьютера сети. Тогда, исходя из этого закрыть приложение на др. компьютере не получиться по причине того, что определить его не представится возможным.
С др. стороны возможно узнать имя пользователя открывшего общую/расширенную книгу и уже пользователю направить сообщение с помощью того же net send(msg), который в корпоративной/доменной сети доставит его в сеанс пользователя.

corbis 14-08-2015 21:51 2541756

Не совсем то, что требуется. Вроде обманул, только не знаю, насколько грамотно такое решение:

Код:

Public wBook As Workbook

Function IsBookOpen(wbFullName As String) As Boolean
    Dim iFF As Integer
    iFF = FreeFile
    On Error Resume Next
    Open wbFullName For Random Access Read Write Lock Read Write As #iFF
    Close #iFF
    IsBookOpen = Err
End Function

Private Sub Button_Click()
flag = 0
       
  If (IsBookOpen("C:\test.xlsx")) Then

          If VarType(wBook) <> 9 Then
              MsgBox ("Закрой test'")
                          Else
              MsgBox ("Можно копировать")
          End If
         
    Else
      Workbooks.Open Filename:="C:\test.xlsx"
      Set wBook = ActiveWorkbook
  End If
End Sub


NickM 14-08-2015 22:32 2541761

corbis, извините Меня, но смогу подержать Вас только теорией.
Ситуацию вижу так: определиться каким образом открыта книга:
1. Локально, в единственном сеансе пользователя - тогда и решение простое. Ввиду того, что в сеансе у приложения Эксель может быть одновременно открыта одна единственная книга/файл с одинаковым именем независимо от пути, то просто закрыть книгу по имени с сохранением внесенных изменений;
2 и 3. Книга открыта в терминальной сессии и/или с др. компьютера сети как книга общего доступа. Тут уже сложнее. Здесь придется с помощью кода VBA узнать имя пользователя/пользователей работающих с книгой, после с помощью системных, сторонних утилит(например от sysinternals) определить сессию/компьютер на котором залогинен пользователь занявший книгу, которому в последствии отправить сообщение. Также следует учесть/отвести время на реакцию пользователя после чего, при неисполнении требуемого действия предусмотреть возможность принудительного закрытия книги. А вот тут еще один момент - с помощью системных, сторонних утилит приложение в сессии/на удаленном компьютере можно просто "кильнуть", но ессно о никакой сохранности речи не идет, если сохранность нужна по зарез можно и заморочиться и реализовать ее.

corbis 15-08-2015 21:10 2542033

Нашёл толковый способ, может пригодится кому

Код:

Dim wBook As Workbook
Set wBook = GetObject(ПутьКфайлу)

        If Windows(wBook.Name).Visible = False Then
          Windows(wBook.Name).Visible = True
        End If

Если книга открыта, тогда просто с ней работаем. Если была закрыта - открываем и делаем её видимой.
Почему-то по дефолту она скрыта.

NickM 15-08-2015 23:26 2542076

corbis, толковый в каком смысле?

corbis 16-08-2015 03:17 2542115

Без всяких выдумывании. Одной командой решается поставленная задача.


Время: 13:54.

Время: 13:54.
© OSzone.net 2001-