Уважаемые форумчане, прошу помощи! В файле Excel разработал программу. В ней большая UserForm, много процедур. Работало все прекрасно, последние две недели при загрузке программы, Ексель уходит в ошибку. Если запускать программу пошагово [F8], загрузка выполняется без проблем. Исследуя код в поисках возможной ошибки обратил внимание, что все записи (во всех процедурах) со значением .Value изменены на .value редактор VBA сам приводит их к такому формату. Выложить файл не могу, он более 2 Мбайт весом.
Версия Windows 7 х64, Excel 2010.В программе используются функции API декларированные #If VBA7 Then #If Win64 Then #Else #End If #Else #End If Также ссылки на библиотеки: VBA|Visual Basic For Applications (VBE7.DLL); Excel|Microsoft Excel 14.0 Object Library; stdole|OLE Automation; Office|Microsoft Office 14.0 Object Library; MSForms|Microsoft Forms 2.0 Object Library; Word|Microsoft Word 14.0 Object Library; ADODB|Microsoft ActiveX Data Objects 6.0 Library; VBIDE|Microsoft Visual Basic for Applications Extensibility 5.3 (\VBE6EXT.OLB); MSHTML|Microsoft HTML Object Library; MSScriptControl|Microsoft Script Control 1.0
Подскажите, что произошло с программой, почему редактор VBA меняет код .value ?
' Public Declare PtrSafe Function DrawMenuBar Lib "user32" (ByVal hwnd As LongPtr) As LongPtr
' Public Declare PtrSafe Function GetSystemMenu Lib "user32" (ByVal hwnd As LongPtr, ByVal bRevert As LongLong) As LongLong
' Public Declare PtrSafe Function DeleteMenu Lib "user32" (ByVal hMenu As LongLong, ByVal nPosition As LongLong, ByVal wFlags As LongLong) As LongLong
' Public Declare PtrSafe Function EnableWindow Lib "user32" (ByVal hwnd As LongPtr, ByVal fEnable As LongLong) As LongLong
' Public Declare PtrSafe Function ExtractIcon Lib "shell32.dll" Alias "ExtractIconA" (ByVal hInst As LongLong, ByVal lpszExeFileName As String, ByVal nIconIndex As LongLong) As LongLong
' Public Declare PtrSafe Function SendMessage Lib "user32" Alias "SendMessageA" (ByVal hwnd As LongPtr, ByVal wMsg As LongLong, ByVal wParam As Integer, ByVal lParam As LongLong) As LongLong
' Public Declare PtrSafe Function LockWindowUpdate Lib "user32" (ByVal hWndLock As LongPtr) As LongPtr
'' Сделать ексель прозрачным во время работы с формой (быстро или постепенно)
' Public Declare Function GetWindowLong Lib "USER32" Alias "GetWindowLongA" (ByVal hWnd As LongPtr, ByVal nIndex As LongPtr) As LongPtr
' Public Declare Function SetWindowLong Lib "USER32" Alias "SetWindowLongA" (ByVal hWnd As LongPtr, ByVal nIndex As LongPtr, ByVal dwNewLong As LongPtr) As LongPtr
' Public Declare PtrSafe Function DrawMenuBar Lib "user32" (ByVal hwnd As Long) As LongPtr
' Public Declare PtrSafe Function GetSystemMenu Lib "user32" (ByVal hwnd As Long, ByVal bRevert As LongPtr) As LongPtr
' Public Declare PtrSafe Function DeleteMenu Lib "user32" (ByVal hMenu As LongPtr, ByVal nPosition As LongPtr, ByVal wFlags As LongPtr) As LongPtr
' Public Declare PtrSafe Function EnableWindow Lib "user32" (ByVal hwnd As Long, ByVal fEnable As LongPtr) As LongPtr
' Public Declare PtrSafe Function ExtractIcon Lib "shell32.dll" Alias "ExtractIconA" (ByVal hInst As LongPtr, ByVal lpszExeFileName As String, ByVal nIconIndex As LongPtr) As LongPtr
' Public Declare PtrSafe Function SendMessage Lib "user32" Alias "SendMessageA" (ByVal hwnd As Long, ByVal wMsg As LongPtr, ByVal wParam As Integer, ByVal lParam As LongPtr) As LongPtr
' Public Declare PtrSafe Function LockWindowUpdate Lib "user32" (ByVal hWndLock As LongPtr) As LongPtr
'' Сделать ексель прозрачным во время работы с формой (быстро или постепенно)
' Public Declare Function GetWindowLong Lib "USER32" Alias "GetWindowLongA" (ByVal hWnd As Long, ByVal nIndex As Long) As Long
' Public Declare Function SetWindowLong Lib "USER32" Alias "SetWindowLongA" (ByVal hWnd As Long, ByVal nIndex As Long, ByVal dwNewLong As Long) As Long
Если объявляете через PtrSafe, то LonlLong и Long лишнее - надо везде объявлять как LongPtr, VBA сам преобразует в нужный тип. А у Вас каша какая-то: то LongPtr, то LongLong, то Long. Либо уж убирайте PtrSafe и назначайте конкретные типы: Long и LongLong(но для этого надо очень хорошо знать входной тип каждой функции для каждой системы).
Добрый день, уважаемые форумчане. Хочу выразить благодарность Всем, кто откликнулся, благодаря вашим подсказкам декларации WinApi более детально изучены и переосмыслены.
Что касается первого поста с основным вопросом по сбою программы, была проведена работа по поиску возникающей ошибки: - переписаны WinApi, также в процессе было полное отключение всех WinApi вместе с вызовами их функций, форма стала менее красивой и функциональной, но сбой остался, могу с уверенностью сказать WinApi были не причем; - частично изменен и переписан код (логика) загрузки формы, не помогло (прикольно смотреть на свой код спустя несколько лет, думаю сейчас лучше стало, но время покажет.); - написан класс логирования загрузки программы, который помог найти участок кода со странной на мой взгляд причиной, а именно после инициализации и загрузки формы выполнялась загрузка данных в листбоксы и комбобоксы, в один из листбоксов загружался текст
.cmbxOptionService.AddItem "Витяг з Річного плану закупівель по підрозділам"
.cmbxOptionService.AddItem "Зміни в річний план закупівель"
.cmbxOptionService.AddItem "Звіт по проведеним договорам"
.cmbxOptionService.ListIndex = 0
EndIf
Где len ("Витяг з Річного плану закупівель по підрозділам") = 47 на этой строке возникал сбой Заменив строку на .cmbxOptionService.AddItem "Витяг з РПЗ по підрозділам" len ("") = 26 Также
Закоментировав данный участок кода Программа стала работать без сбоев, полет нормальный с 15.02.2021.
Есть загрузка в другие листбоксы, где len = 46 и сбой не возникает, изменив на большую длину текста до 50 символов, тоже возникает сбой, свойства контролов стандартные, ограничений на длину текста нет.
Смущает факт того, что сбой возникает, только когда проект закрыт паролем для просмотра и редактирования, при удалении защиты все работает. Если честно, я не понимаю взаимосвязи возникающей ошибки и защиты с паролированием проекта, но возможно, кто-то из гуру форума подскажет в чем кроется данная ошибка.