Форум по Delphi программированию

Delphi Sources



Вернуться   Форум по Delphi программированию > Все о Delphi > [ "Начинающим" ]
Ник
Пароль
Регистрация <<         Правила форума         >> FAQ Пользователи Календарь Поиск Сообщения за сегодня Все разделы прочитаны

Ответ
 
Опции темы Поиск в этой теме Опции просмотра
  #1  
Старый 09.08.2014, 23:28
Аватар для Electronic_Arts
Electronic_Arts Electronic_Arts вне форума
Местный
 
Регистрация: 13.07.2006
Адрес: на земле
Сообщения: 562
Версия Delphi: Delphi 11
Репутация: 18
Восклицание DBLookupcombobox как прокрутить или чем заменить?

Всем добрый день

Весь и-нет нарыл ни где не нашел нормальной информации почему не получается сделать прокрутку для DBLookupcombobox

Код:
procedure TCVForm.HandleMousewheel(var Msg: TMsg; var Handled: Boolean);
begin
   case Msg.message of
      WM_MOUSEWHEEL:
      begin
         if (Screen.ActiveForm.ActiveControl <> nil) and
            (Screen.ActiveForm.ActiveControl.ClassName = 'TDBLookupComboBox') then
         begin
            Msg.message := WM_KEYDOWN;
            Msg.lParam := 0;
            if Msg.wParam > 0 then
               Msg.wParam := VK_UP
            else
               Msg.wParam := VK_DOWN;
            Handled := False;
         end;
      end;
   end;
end;

Код хороший - но есть один минус почему то Msg.wParam не получает значение ниже ноля и прокрутка работает только вверх

Проверил что же творится в Msg.wParam оказалось
когда прокручиваешь колесо мышки вверх значение Msg.wParam равно 7864320 и не меняется а когда крутишь колесо вниз 4287102976
Что это такое?? почему так??

- При поиске даже обнаружил такие ответы как Delphi давно имеет эту проблему с прокруткой DBLookupcombobox и до сих пор не решили

Скажите плиз как вы справляетесь с такой проблемой?? чем заменить DBLookupcombobox???? есть ли альтернатива которая имеет возможность использовать прокрутку?
__________________
Нет ничего не возможного. Вопрос только во времени...
Ответить с цитированием
  #2  
Старый 10.08.2014, 00:39
Аватар для Bargest
Bargest Bargest вне форума
Профессионал
 
Регистрация: 19.10.2010
Адрес: Москва
Сообщения: 2,390
Версия Delphi: XE3/VS12/FASM
Репутация: 14665
По умолчанию

Слышал про дополнительный код? Про то, как хранятся в компьютере отрицательные числа? Переведи свои полученные 4 с гаком миллиарда в hex и увидишь, что это FF880000. Старший бит равен 1, значит число отрицательное и его "человеческое" значение - это 0x100000000 - 0xFF880000 = -7864320 (-0x00780000).
Что это за число?
Читаем msdn (вернее, его перевод)
Цитата:
wParam
Старшее слово указывает интервал, на который прокрутилось колесико, выраженный в нескольких или раздельных WHEEL_DELTA, число которых - 120. Положительное значение указывает, что колесико вращалось вперед, в сторону от пользователя; отрицательное значение указывает, что колесико вращалось назад, к пользователю.
Младшее слово указывает, находятся ли в нажатом состоянии различные виртуальные клавиши. Этот параметр может состоять из одного или нескольких ниже перечисленных значений.
То есть wParam делим на 2 части: 0x0078 и 0x0000. 0x78 = 120, как и ожидалось.
Таким образом, берем старшую часть wParam и смотрим старший бит:
Код:
if ((wParam shr 16) and 0x8000) = 0 then ; // > 0
// или эквивалент
if (wParam and 0x80000000) = 0 then ; // > 0
Можно "прямо" привести число к integer'у (integer(value)), и число само, так сказать, станет отрицательным, если было больше 0x80000000 (но говорить так не стоит, т.к. на самом деле разницы между положительными и отрицательными попросту нет, разве что в восприятии их человеком или компилятором). Но не люблю я это дело когда речь о битовых операциях. Хочешь - попробуй под отладкой сделать
Код:
if integer(wParam) < 0 then ...
Должно сработать.
Почаще заглядывай в "недра" кода и внимательней читай доки.
__________________
jmp $ ; Happy End!
The Cake Is A Lie.

Последний раз редактировалось Bargest, 10.08.2014 в 00:48.
Ответить с цитированием
Этот пользователь сказал Спасибо Bargest за это полезное сообщение:
Electronic_Arts (10.08.2014)
  #3  
Старый 10.08.2014, 12:20
Аватар для Electronic_Arts
Electronic_Arts Electronic_Arts вне форума
Местный
 
Регистрация: 13.07.2006
Адрес: на земле
Сообщения: 562
Версия Delphi: Delphi 11
Репутация: 18
Восклицание

Спасибо за наводку - сделал вот так и сработало...

Код:
procedure TCVForm.HandleMousewheel(var Msg: TMsg; var Handled: Boolean);
var
i : integer;
s : string;
begin
   case Msg.message of
      WM_MOUSEWHEEL:
      begin
         if (Screen.ActiveForm.ActiveControl <> nil) and
            (Screen.ActiveForm.ActiveControl.ClassName = 'TDBLookupComboBox') then
         begin
            Msg.message := WM_KEYDOWN;
            Msg.lParam := 0;
            s := '$' + inttohex(MSG.wParam, 1);
            i := StrToInt(s);
            if i > 0 then
             Msg.wParam := VK_UP
             else
             Msg.wParam := VK_DOWN;
             Handled := false;
         end;
      end;
   end;
end;
__________________
Нет ничего не возможного. Вопрос только во времени...
Ответить с цитированием
  #4  
Старый 10.08.2014, 13:22
Аватар для Bargest
Bargest Bargest вне форума
Профессионал
 
Регистрация: 19.10.2010
Адрес: Москва
Сообщения: 2,390
Версия Delphi: XE3/VS12/FASM
Репутация: 14665
По умолчанию

Жесть.
Код:
s := '$' + inttohex(MSG.wParam, 1);
i := StrToInt(s);
IntToHex - это цикл из shr, and и +. На 4-байтовое число примерно операций 80-100. + выделение памяти под строку (очень долго) и сложение строк.
StrToInt то же самое, только в обратную сторону (еще ~100 команд минимум).
В то время как (wParam and $80000000) = 0 компилируется в одну команду. И integer(wParam) > 0 тоже. Лучше поподробней разберись с этими вариантами, чтобы не мучить комп бесполезными вычислениями.
И вообще, в любом языке надо минимально пользоваться строками. Поскольку бинарные данные априори быстрее строк раз в 100 как минимум.
__________________
jmp $ ; Happy End!
The Cake Is A Lie.

Последний раз редактировалось Bargest, 10.08.2014 в 13:26.
Ответить с цитированием
Этот пользователь сказал Спасибо Bargest за это полезное сообщение:
Electronic_Arts (10.08.2014)
  #5  
Старый 10.08.2014, 17:26
Аватар для Electronic_Arts
Electronic_Arts Electronic_Arts вне форума
Местный
 
Регистрация: 13.07.2006
Адрес: на земле
Сообщения: 562
Версия Delphi: Delphi 11
Репутация: 18
Восклицание

займусь когда буду код доработать в конце пока мне нужно результат увидеть - а дальше уменьшу код
__________________
Нет ничего не возможного. Вопрос только во времени...
Ответить с цитированием
  #6  
Старый 10.08.2014, 17:36
Аватар для Electronic_Arts
Electronic_Arts Electronic_Arts вне форума
Местный
 
Регистрация: 13.07.2006
Адрес: на земле
Сообщения: 562
Версия Delphi: Delphi 11
Репутация: 18
Восклицание

Поменял эту часть кода
Код:
s := '$' + inttohex(MSG.wParam, 1);
i := StrToInt(s);
на это

Код:
integer(wParam) > 0

и все..
__________________
Нет ничего не возможного. Вопрос только во времени...
Ответить с цитированием
Ответ


Delphi Sources

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск
Опции просмотра

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы не можете редактировать сообщения

BB-коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход


Часовой пояс GMT +3, время: 01:29.


 

Сайт

Форум

FAQ

Соглашения

Прочее

 

Copyright © Форум "Delphi Sources" by BrokenByte Software, 2004-2025