Перейти из форума на сайт.

НовостиФайловые архивы
ПоискАктивные темыТоп лист
ПравилаКто в on-line?
Вход Забыли пароль? Первый раз на этом сайте? Регистрация
Компьютерный форум Ru.Board » Компьютеры » Прикладное программирование » Вопросы по Delphi (все версии) - часть 4

Модерирует : ShIvADeSt

ShIvADeSt (28-06-2009 02:10): Продолжение в http://forum.ru-board.com/topic.cgi?forum=33&topic=10477  Версия для печати • ПодписатьсяДобавить в закладки
Страницы: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101

   

ShIvADeSt



Moderator
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Maks150988
В том то и дело, что твои исходники я скачал и посмотрел. Увидел много похожего с моими сорсами, чтобы не искать ошибки у тебя - предложил тебе свои. В общем, несколько советов. Если тебе надо использовать переменные внутри только одной процедуры (функции), то объявляй их внутри этой процедуры. Никогда так не делай

Код:
 
procedure PaintImageFileButton(DC : HDC; RtBtn : TRect; szPathFile : WideString);
begin
  CompDC := CreateCompatibleDC(0);
  NewBmp := LoadImageW(hInstance, PWideChar(szPathFile), IMAGE_BITMAP, 0, 0, LR_DEFAULTSIZE or LR_LOADFROMFILE);
  OldBmp := SelectObject(CompDC, NewBmp);
  BitBlt(PS.hDC, 0, 0, RtBtn.Right - RtBtn.Left, RtBtn.Bottom - RtBtn.Top, CompDC, 0, 0, SRCCOPY);
  SelectObject(CompDC, OldBmp);
  DeleteDC(CompDC);
  DeleteObject(NewBmp);
end;
 

Для чего ты передаешь в процедуру указатель контекста, если рисуешь в итоге на другом. Я слегонца офигел, когда мой код не заработал как должен был, но когда глянул глобальные переменные - офигел еще больше В общем вот готовый пример, правда кнопку я таки сделал OWNERDRAW
Подробнее...
 
Добавлено:
Maks150988

Цитата:
И все-таки хочется чтобы Вы скачали проект по ссылке и посмотрели. А то все слова слова, а тут на деле сразу. И вот хотел узнать, Вы определяетев обоработчике еще и тип контрола через ODT_BUTTON. Я вроде как без него сделал, вроде картинки рисуются на кнопке. Стоит ли так выполнять отрисовку?  

В принципе не надо, если исходить из имен ресурсов, но к примеру у меня будет 20 кнопок с разными названиями, но одинакового поведения, тогда проще будет исходить из типа ресурса, а в обработчике отрисовки просто получать заголовки кнопок, так как только они отличаются.

----------
И создал Бог женщину... Существо получилось злобное, но забавное...

Всего записей: 3956 | Зарегистр. 29-07-2003 | Отправлено: 02:44 02-12-2008
Maks150988



Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
ShIvADeSt
Спасибо. А как тогда поступать, если хочется поболее кнопок разрисовать. Понимаю что глупо, но сделал вот так: Подробнее
 
Нужно в цикле как-нибудь пронумеровать DrawCloseButton для каждой кнопки или можно одну эту функцию использовать для всех кнопок или просто OldBtnProc в массив засунуть и для каждой кнопки засабклассить? А то сейчас, например, навели на кнопку курсор и нажали, цвет у другой сменился на активный, хотя не должно так быть.
Хочется универсального решения с минимальным кодом.

Цитата:
Для чего ты передаешь в процедуру указатель контекста, если рисуешь в итоге на другом.

То есть? Имеется ввиду PaintImageFileButton? Если да, то там рисуется на DC, а это уже может быть и PDRAWITEMSTRUCT и TPaintStruct. Вроде универсально...

Всего записей: 836 | Зарегистр. 23-12-2006 | Отправлено: 09:58 02-12-2008
ShIvADeSt



Moderator
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Maks150988

Цитата:
То есть? Имеется ввиду PaintImageFileButton? Если да, то там рисуется на DC, а это уже может быть и PDRAWITEMSTRUCT и TPaintStruct. Вроде универсально...

Посмотри что передаешь и на чем рисуешь. Передаешь
Цитата:
PaintImageFileButton(DC : HDC;

а рисуешь
Цитата:
BitBlt(PS.hDC,
. А все из-за того, что очень много глобальных переменных, поэтому не ругалось.

Цитата:
Хочется универсального решения с минимальным кодом.  

Сам такое хочу найти Все что нашел в инете - это создавать класс кнопок, тогда у каждой кнопки будет свой MouseOver и соответственно только нужная кнопка будет отрисовываться.

----------
И создал Бог женщину... Существо получилось злобное, но забавное...

Всего записей: 3956 | Зарегистр. 29-07-2003 | Отправлено: 11:08 02-12-2008
delover

Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
А не подскажете, у меня тут программа написана вроде на i86, раньше она работала. она вызывает int 10 c ax 80 наверное переключает текстовый режим, на тот же самый текстовый режим, в результате чего консоль разворачивается на весь экран. А сейчас она не реботает. Незнаю почему, может можно как-то исправить прогу?

Всего записей: 1395 | Зарегистр. 25-06-2007 | Отправлено: 14:05 02-12-2008
Yozj



Junior Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
delover
Под какой ОС программа?
По моему Windows XP, Vista механизм прерываний полностью блокируют.

Всего записей: 125 | Зарегистр. 01-12-2004 | Отправлено: 14:17 02-12-2008
delover

Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Yozj
А под Windows 98 нормально работает. Понятно же что Virtual PC на домашнем Vista тоже синий экран может показывать. Как вот он это делает? И главно потом Alt-Tab не работает почему-то.

Всего записей: 1395 | Зарегистр. 25-06-2007 | Отправлено: 15:48 02-12-2008
Yozj



Junior Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
delover
Так Win98 - совсем другая архитектура ядра и понятия безопасности. А как обрабатывают  такие прерывания эмуляторы - вопрос к ним, далеко не факт что под ними это возможно.

Всего записей: 125 | Зарегистр. 01-12-2004 | Отправлено: 16:22 02-12-2008
akaGM

Platinum Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
delover
DosBox -- наше всё...
www.dosbox.com

Всего записей: 24232 | Зарегистр. 06-12-2002 | Отправлено: 17:30 02-12-2008
Maks150988



Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
ShIvADeSt
А у Вас случайно нет кода, как отрегионить кнопку по определенному цвету? И вот немного не понимаю как сделать такое. Имеем битмап, цвет для прозрачности фуксия, загружаем битмап и по этому цвету регионим кнопку, сама кнопка отображается нормально как надо - ее место в которое с регионами отцапано не "закрашивает" картинку диалога.
Сделал пока так http://webdrive.avtograd.ru/Download/Explorer/temp/hbutton.zip но это не выход красить задний неиспользуемый якобы фон самого битмапа кнопки. Ведь можно также фуксией закрасить и тогда квадратная кнопка будет в своей красе с прозрачностью что не гуд.

Всего записей: 836 | Зарегистр. 23-12-2006 | Отправлено: 20:50 02-12-2008
ShIvADeSt



Moderator
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Maks150988
Посмотри тут http://jhekasoft.narod.ru/rgn_btn.htm

----------
И создал Бог женщину... Существо получилось злобное, но забавное...

Всего записей: 3956 | Зарегистр. 29-07-2003 | Отправлено: 02:43 03-12-2008
sadasaf



BANNED
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Огромная просьба, помогите решить:  
Постановка задачи:  
1. Номер минимального по модулю элемента массива.  
2. Сумму модулей элементов массива, расположенных после первого отрица-тельного элемента.  
Сжать массив, удалив из него все элементы, величина которых находится в интервале [a,b]. Освободившиеся в конце массива элементы заполнить нулями




типовые задачи по паскалю (а тут голимый паскаль) вверху в прибитую тему

Всего записей: 216 | Зарегистр. 18-08-2008 | Отправлено: 02:45 03-12-2008 | Исправлено: ShIvADeSt, 06:55 03-12-2008
delover

Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
akaGM
Спасибо, скачал с исходниками, правда они на Си, а есть ли решение для Delphi Console Project? Вижу, что очень мощное средство, но пока проверить не могу, нет админских привелегий. А запуск dosshell.exe требует, кстати, нельзя что ли без admin?
 
Был бы благодарен за уточнения где смотреть...
Удачи.
 
Добавлено:
Yozj
Да не факт, наверное придётся делать по разному для Vista и Windows 98.

Всего записей: 1395 | Зарегистр. 25-06-2007 | Отправлено: 08:09 03-12-2008
Maks150988



Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
ShIvADeSt
Блин, да там VCL Я плохо разбираюсь в некоторых конструкциях кода - всякие TBitmap и подобные Image.Canvas.Pixels[0, y] смущают. Остальное впринципе не проблема под Апи переделать.
 
Значит, сделал вот так, подобие скина Винампа с кнопками Медиа плейера Виндовс. Вроде для примера смотрится очень даже ничего.
http://webdrive.avtograd.ru/Download/Explorer/temp/skincore.zip
Только есть вопросик. Почему не работают пункты системного контекстного меню - WM_CONTEXTMENU? Эм, без понятия если честно. False возвращаю, а толку... и еще одна особенность. После запуска программки если вызвать это меню - оно как-бы не поиницализировано чтоли - пункты без изменения и все активны. А вот если подвигать диалог программы - пункты принимают впринципе нормальный вид - пункт закрытия выделяется жирным шрифтом и другие пункты неактивны становятся. Но если жать на пункты - не работают. В чем собственно дело?
 
А функцию переделал так:
 

Код:
function BitmapToRgn(szPathFile: WideString): HRGN;
var
  Bitmap: HBITMAP;
  BmpInfo : TBitmapInfo;
  TmpRgn: HRGN;
  x, y: integer;
  ConsecutivePixels: integer;
  TranparentColor: COLORREF; //Прозрачный цвет
  CurrentPixel: COLORREF;
  CurrentColor: COLORREF;
  MskBmpDC:HDC;
begin
 
  Bitmap := LoadImageW(hInstance, PWideChar(szPathFile), IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
  GetObject(Bitmap, SizeOf(BmpInfo), @BmpInfo);
  Result := CreateRectRgn(0, 0, BmpInfo.bmiHeader.biWidth, BmpInfo.bmiHeader.biHeight);
  if (BmpInfo.bmiHeader.biWidth = 0) or (BmpInfo.bmiHeader.biHeight = 0) then
    exit;
  MskBmpDC := CreateCompatibleDC(0);
  SelectObject(MskBmpDC, Bitmap);
  TranparentColor := GetPixel(MskBmpDC, x, y);
  for y := 0 to BmpInfo.bmiHeader.biHeight - 1 do
    begin
      CurrentColor := GetPixel(MskBmpDC,0, y);
      ConsecutivePixels := 1;
      for x := 0 to BmpInfo.bmiHeader.biWidth - 1 do
      begin
        CurrentPixel := GetPixel(MskBmpDC,x, y);
        if CurrentColor = CurrentPixel then
          inc(ConsecutivePixels)
        else
          begin
            if CurrentColor = TranparentColor then
              begin
                TmpRgn := CreateRectRgn(x - ConsecutivePixels, y, x, y + 1);
                CombineRgn(Result, Result, TmpRgn, RGN_DIFF);
                DeleteObject(TmpRgn);
              end;
            CurrentColor := CurrentPixel;
            ConsecutivePixels := 1;
          end;
      end;
    end;
  DeleteObject(Bitmap);
  DeleteDC(MskBmpDC);
  if (CurrentColor = TranparentColor) and (ConsecutivePixels > 0) then
    begin
      TmpRgn := CreateRectRgn(x - ConsecutivePixels, y, x, y + 1);
      CombineRgn(Result, Result, TmpRgn, RGN_DIFF);
      DeleteObject(TmpRgn);
    end;
end;

Но походу неправильно переделал. Немного непонятно как часть кода перевести.

Всего записей: 836 | Зарегистр. 23-12-2006 | Отправлено: 22:53 03-12-2008 | Исправлено: Maks150988, 00:00 04-12-2008
ShIvADeSt



Moderator
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Maks150988
Вот мой код, в свое время сам переводил с ВБ на Дельфи битмапку в регион

Код:
 
function MakeRegion(DC:HDC):HRGN;
var
     x,y,StartLineX             :integer;
     FullRegion,LineRegion      :HRGN;
     TransparentColor           :COLORREF;
     InFirstRegion,_InLine      :Boolean;
     PicWidth,PicHeight         :integer;
begin
     DC:=DC;
     PicWidth:=96;
     PicHeight:=80;
     InFirstRegion:=True;
     _InLine:=False;
     StartLineX:=0;
     TransparentColor:=GetPixel(DC,0,0);
     for Y:=0 to PicHeight-1 do
        for X:=0 to PicWidth-1 do
            if (GetPixel(DC, X, Y)=TransparentColor)then begin
                if _InLine then begin
                    _InLine:=False;
                    LineRegion:=CreateRectRgn(StartLineX,Y,X,Y+1);
                    if InFirstRegion then begin
                        FullRegion:=LineRegion;
                        InFirstRegion:=False;
                       end
                      else begin
                        CombineRgn(FullRegion, FullRegion, LineRegion, RGN_OR);
                        DeleteObject(LineRegion);
                       end;
                   end
               end
           else
                If NOT _InLine then begin
                    _InLine:=True;
                    StartLineX:=X;
                   end;
    Result:=FullRegion;
end;
 


----------
И создал Бог женщину... Существо получилось злобное, но забавное...

Всего записей: 3956 | Зарегистр. 29-07-2003 | Отправлено: 04:37 04-12-2008
delover

Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Maks150988
В VCL объект TBitmap занимается хранением данных и тесно повязан на TIcon и TImageList. В случае с TIcon нужно рисовать транспаренту, а в случае с TImageList нужно уметь компоновать разные катинки в одну. Так что Pixels[] лучше использовать только для транспарента, есть же много Draw-ов. WM_CONTEXTMENU по идее должен соответствовать OnContextMenu любого TControl, опять же апи может непонимать контролов.

Всего записей: 1395 | Зарегистр. 25-06-2007 | Отправлено: 07:57 04-12-2008
ShIvADeSt



Moderator
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Maks150988

Цитата:
Только есть вопросик. Почему не работают пункты системного контекстного меню - WM_CONTEXTMENU? Эм, без понятия если честно. False возвращаю, а толку... и еще одна особенность.

попробуй системное меню через TrackPopupMenu вызывать. Я просто не помню, чтобы у меня такая проблема была с системным меню.

----------
И создал Бог женщину... Существо получилось злобное, но забавное...

Всего записей: 3956 | Зарегистр. 29-07-2003 | Отправлено: 09:36 04-12-2008
Maks150988



Advanced Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
delover
Дык я на чистом Апи делаю прогамму, мне эти ТБитмап не нужны. Мне б только знать как перевести некоторый код с этого дурацкого VCL. Вот например самое простое - Image.Width это можно через GetObject у загруженной картинки узнать, а Image.Canvas.Pixels[0, 0] я подумал что это в Апи GetPixel(MskBmpDC,0, y) куда предварительно поместил битмап через SelectObject. так вроде смотрю считай одно и тоже.
 
ShIvADeSt
Так я вызываю через ТрекПопапМеню.
 

Код:
hSysMenu := GetSystemMenu(hApp, FALSE);
//
    WM_CONTEXTMENU:
      begin
        GetCursorPos(lpPoint);
        GetWindowRect(hApp, lpRect);
        lpRect.Bottom := lpRect.Top + 18;
        //ClientToScreen(hApp, lpPoint);
        if PtInRect(lpRect, lpPoint) then
          begin
            SetForegroundWindow(hApp);
            TrackPopupMenu(hSysMenu, TPM_LEFTALIGN or TPM_LEFTBUTTON, lpPoint.X, lpPoint.Y, 0, hApp, nil);
            PostMessage(hApp, WM_NULL, 0, 0);
            //Result := 1;
          end;
        Result := 1;
      end;

 
Не работает код.
 
Ну и переделал ваш код:

Код:
procedure BitmapToRegion(hButton: Thandle; szPathFile: WideString);
var
     x,y,StartLineX             :integer;
     FullRegion,LineRegion      :HRGN;
     TransparentColor           :COLORREF;  
     InFirstRegion,_InLine      :Boolean;  
     PicWidth,PicHeight         :integer;
     DC:HDC;
     Bitmap:HBITMAP;
     BmpInfo : TBitmapInfo;
begin  
  Bitmap := LoadImageW(hInstance, PWideChar(szPathFile), IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
  GetObject(Bitmap, SizeOf(BmpInfo), @BmpInfo);
  DC := CreateCompatibleDC(0);
  SelectObject(DC, Bitmap);
     PicWidth:=BmpInfo.bmiHeader.biWidth;
     PicHeight:=BmpInfo.bmiHeader.biHeight;
     InFirstRegion:=True;  
     _InLine:=False;  
     StartLineX:=0;  
     TransparentColor:=GetPixel(DC,0,0);
     for Y:=0 to PicHeight-1 do  
        for X:=0 to PicWidth-1 do  
            if (GetPixel(DC, X, Y)=TransparentColor)then begin
                if _InLine then begin  
                    _InLine:=False;
                    LineRegion:=CreateRectRgn(StartLineX,Y,X,Y+1);
                    if InFirstRegion then begin  
                        FullRegion:=LineRegion;  
                        InFirstRegion:=False;  
                       end  
                      else begin
                        CombineRgn(FullRegion, FullRegion, LineRegion, RGN_OR);
                        DeleteObject(LineRegion);  
                       end;  
                   end
               end  
           else  
                If NOT _InLine then begin
                    _InLine:=True;  
                    StartLineX:=X;
                   end;  
SetWindowRgn(hButton, FullRegion, TRUE);
DeleteObject(FullRegion);
  DeleteObject(Bitmap);
  DeleteDC(DC);
end;

Вроде бы работает. Ммм, все ли потом корректно удаляется после создания? Немного смущает как-то что Делфи пишет что FullRegion не инициализирован будет.

Всего записей: 836 | Зарегистр. 23-12-2006 | Отправлено: 15:12 04-12-2008 | Исправлено: Maks150988, 16:17 04-12-2008
AlexIntegral



Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
Помогите пожалуйста с задачкой, она не сложная, но я затрудняюсь решить её. Она с использованием оператора if  
 

Код:
Составьте программу вычисления числа дней в месяце. Даны: номер месяца – целое число от 1 до 12, признак високосного года – целое число, равное 1 для високосного года и 0 в противном случае (признак високосного года – номер високосного года делится на 4 нацело).

Всего записей: 245 | Зарегистр. 31-05-2008 | Отправлено: 21:28 04-12-2008
Yozj



Junior Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
AlexIntegral
Модератор поправит, но тебе похоже в ветку с паскалем.
А по существу - на каком языке надо писать, Delphi или Turbo Pascal?

Всего записей: 125 | Зарегистр. 01-12-2004 | Отправлено: 21:34 04-12-2008 | Исправлено: Yozj, 21:35 04-12-2008
AlexIntegral



Member
Редактировать | Профиль | Сообщение | Цитировать | Сообщить модератору
На Delphi, передо мной среда разработки Delphi 7, а в мысли на счёт задачи никакой. Помогите кто чем

Всего записей: 245 | Зарегистр. 31-05-2008 | Отправлено: 22:05 04-12-2008
   

Страницы: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101

Компьютерный форум Ru.Board » Компьютеры » Прикладное программирование » Вопросы по Delphi (все версии) - часть 4
ShIvADeSt (28-06-2009 02:10): Продолжение в http://forum.ru-board.com/topic.cgi?forum=33&topic=10477


Реклама на форуме Ru.Board.

Powered by Ikonboard "v2.1.7b" © 2000 Ikonboard.com
Modified by Ru.B0ard
© Ru.B0ard 2000-2024

BitCoin: 1NGG1chHtUvrtEqjeerQCKDMUi6S6CG4iC

Рейтинг.ru