Привет всем! У меня снова чайниковский вопрос. Осваиваю функцию AnimateWindow и есть кое-какие вопросы. (Блин, я наверное никогда не перестану задавать вопросы) Как я понял из МSDN функция AnimateWindow используется, когда необходимо изобразить анимацию при закрытиии или отображении окна. Из того же MSDN прочитал что при открытии окна для появления анимации вместо ShowWindow необходимо использовать AnimateWindow. Лады, пробуем... Был кусок в проге: invoke ShowWindow,hWnd, 1 invoke UpdateWindow,hWnd Насколько я понимаю этот код и используется для отображения созданного окна. Так, дальше... меняем ShowWindow на AnimateWindow: invoke AnimateWindow,hWnd,1000,AW_CENTER invoke UpdateWindow,hWnd Получаем... Косяк! Окно отбражается сразу, а не так как положено (разворачиваясь из центра) Гонял под отладчиком. Оказалось, что окно каким-то неведомым образом отображается раньше, чем выполняется функция AnimateWindow. При этом, если AnimateWindow использовать со следующими параметрами, то все происходит как надо invoke AnimateWindow,hWnd,1000,AW_BLEND+AW_HIDE invoke UpdateWindow,hWnd Окно постепенно исчезает. Подскажите пожалуйста, как использовать эту функцию, и где я ошибся?
Чтобы окно не отображалось сразу после создания нужно чтобы в CreateWindowEx не было флага WS_VISIBLE - возможно дело в этом.
Слушай, да, действительно!! Все получилось. Только опять остались непонятки. Написано же везде, что функция CreateWindowEx служит для создания окна. А для отображения окна на экране используют функцию ShowWindow (или соответственно AnimateWindow)?
Только все равно праблы. Теперь рисунок в окне, который я выводил с помощью BitBlt не отображается. Наверное как-то перестроить порядок вызова функций?
CreateWindowEx может создавать окно видимым или невидимым на усмотрение программера, в последнем случае его нужно показывать самому (как раз для AnimateWindow или когда между созданием и показом окна нужно что нибудь настроить). А BitBlt надеюсь используешь в WM_PAINT, а не просто после создания окна ?)
То есть полчается, что ShowWindow можно и не использовать, если в свойствах окна указывать WS_VISIBLE? BitBlt вызываю таким образом: Код (Text): WndProc proc hWin :DWORD, uMsg :DWORD, wParam :DWORD, lParam :DWORD ............... ............... .elseif uMsg == WM_PAINT invoke Paint_Proc1,hWin ............... ............... WndProc endp ............... ............... Paint_Proc1 proc hWin:DWORD LOCAL hDC1 :DWORD LOCAL hOld1 :DWORD LOCAL memDC1 :DWORD LOCAL ps1 :PAINTSTRUCT invoke BeginPaint,hWnd,ADDR ps1 mov hDC1, eax invoke CreateCompatibleDC,hDC1 mov memDC1, eax invoke SelectObject,memDC1,hBmp1 mov hOld1, eax invoke BitBlt,hDC1,50,54,550,175,memDC1,0,0,SRCCOPY invoke SelectObject,memDC1,hOld1 invoke DeleteDC,memDC1 invoke EndPaint,hWin,ADDR ps1 ret Paint_Proc1 endp Вот, приаттачил асмовский листинг, посмотри, если не сложно. Буду премного благодарен.
Совершенно точно, но есть случаи (например, DirectDraw окна) когда такой подход уронит прогу )) В коде крамолы не увидел (правда я вместо UpdateWindow предпочитаю InvalidateRect, hWnd, 0, False - может быть в данном случае это поможет), еще тяжелые команды CreateCompatibleDC, SelectObject, DeleteDC стоит размещать в WM_CREATE, WM_DESTROY, но это больше для красоты на работоспособность влиять не должно
Y_Mur Да. Это помогло. Хотя я бы даже не подумал так сделать. За погляд и совет большое спасибо! Хочется научиться писать не просто работающие проги, а правильно и грамотно составленные, чтобы хоть самому не путаться. Большое спасибо еще раз!!!
Раз уж то грабли тут такие: В WM_CREATE делаем: Код (Text): invoke GetDC, [hwnd] mov edi, eax ; edi = временный h_DC invoke CreateCompatibleDC, eax mov [h_memDC], eax invoke ReleaseDC, [hwnd], edi ; h_DC больше не нужен invoke BitmapFromResource, [h_proc], ID_BitMap ; грузим изображение из ресурсов mov edi, eax ; edi = временный h_BitMap invoke SelectObject, [h_memDC], edi ; Это КОПИРОВАНИЕ + ПРЕОБРАЗОВАНИЕ BitMap (потому и медленно) invoke DeleteObject, eax ; вытесненный BitMap не понадобится invoke DeleteObject, edi ; временный h_BitMap скопирован в memDC и больше не нужен Временные Handle можно размещать в регистрах ebx, edi, esi (API их сохраняют) [h_memDC] соответсвенно не должен быть в локальной (стековой) переменной Теперь BitMap оформленный как контекст можно BitBlt, пока его не убъёт invoke DeleteDC, [h_memDC] в WM_DESTROY