Академический Документы
Профессиональный Документы
Культура Документы
/ Сканирование
ВНИЗ
CopyDiblntoImage(TestDib, Iraagel);
TWAIN_FreeNative(TestDib);
TestDib := 0;
end;
end;
В первой строке кода мы очищаем текущее содержимое компонента imagel.
Для этого присваиваем imagel. picture.Bitmap значение n i l .
Во второй строке вызывается TWAIN-функция TWAiN_AcquireNative. Этот
метод отображает стандартное окно сканирования для вашего сканера.
Пример моего окна для сканера Mustek 1200 ED вы можете увидеть на
рис. 6.21. На этом выполнение нашего кода приостановится и продолжится
только после окончания сканирования и закрытия появившегося окна.
Рис. 6.21. Стандартное окно сканирования для моего сканера— Mustek 1200 ED
Полезное
7.1. Конвертер
Первый полезный пример, который я хотел бы с вами обсудить — перевод
строк из Windows-кодировки в DOS и использование преобразований из
шестнадцатеричной системы исчисления в десятичную и обратно. Хотя это
достаточно просто, но почему-то начинающие пользователи почти всегда
становятся в тупик и пишут свои собственные сложные процедуры для пе-
ревода, хотя все проблемы решаются с помощью пары строчек кода.
Для иллюстрации я создал форму, которую вы можете увидеть на рис. 7.1.
Попробуйте и вы создать нечто похожее.
В обработчике события нажатия кнопки, предназначенной для перевода из
Windows-кодировки в DOS, напишите следующий код:
procedure TForml.CodeButtonClick(Sender: TObject) ;
var
s:array [0..255] of char;
324 Глава 7
begin
CharToOem(PChar(WindowsEdit.Text), s)
DOSEdit.Text:=s;
end;
Кодировка:
WindowsEdit DOS- JDDSEdT
Система исчисления:
var
s:array [0..255] of char;
begin
OemToChar(PChar(DOSEdit.Text) , s);
WindowsEdit.Text:=s;
end;
Здесь для преобразования используется функция OemToChar, которая произ-
водит преобразование из DOS-кодировки в кодировку Windows. У этой
функции так же два параметра, которые выполняют те же задачи.
• Строковая переменная, содержащая текст, который надо перекодировать
в Windows-кодировку.
П Переменная, которая будет содержать результат преобразования.
Здесь я также рекомендую использовать промежуточную переменную, чтобы
не было лишних проблем.
Для перекодирования текста из шестнадцатеричной системы в десятичную
напишем следующий код:
procedure TForml.HexToDecButtonClick(Sender: TObject);
var
index:Integer;
begin
index:=StrToInt('$'+HEXEdit.Text);
DECEdit.Text:=IntToStr{index);
end;
Вы, наверно, знаете, что для использования шестнадцатеричных чисел
в Delphi перед числом нужно указать знак $. Тот же знак нужно указывать и
для строковых переменных, и потом перекодировать их с помощью уже зна-
комой функции strToint. По этому знаку функция определит, что у нас
шестнадцатеричное число и корректно переведет его из строки в числовую
переменную.
В следующей строке кода полученное число просто переводится в строку, на
этот раз с использованием функции intTostr, которая воспримет перемен-
ную index как десятичное число.
Как же сделать так, чтобы переменная index воспринималась как шестна-
дцатеричное число, которое мы туда записали? Delphi автоматически произ-
водит преобразования, и вы можете прибавлять к переменной index шест-
надцатеричные, восьмеричные или даже двоичные числа. Вся арифметика
будет работать корректно. На самом деле все арифметические операции
происходят в двоичном исчислении, даже если вы указываете числа в дру-
гом виде. Просто большинство процедур и функций Delphi и API Windows
326 Глава 7
отображают числа в десятичном виде. Если мы хотим увидеть число как ше-
стнадцатеричное, ТО ДЛЯ ЭТОГО НуЖНО ВОСПОЛЬЗОВаТЬСЯ функцией IntToHex.
Функция IntToHex работает так же, как и intToStr. Разница в том, что вто-
рая возвращает нам строковое представление числа в десятичном виде,
a IntToHex — строку с числом в шестнадцатеричном виде.
Код для перевода десятичного числа в шестнадцатеричное выглядит так:
procedure TForml.DecToHexButtonClick(Sender: TObject);
var
index:Integer;
begin
index:=StrToInt(DECEdit2.Text);
HEXEdit2.Text:=IntToHex(index, 2);
end;
На рис. 7.2 вы можете увидеть пример работы программы. Обратите внима-
ние, что при перекодировании текста английский текст не изменяется. Это
связано с тем, что коды английских букв (латиницы) в обеих кодировках
одинаковы и проблема возникает только со знаками национальных языков,
например русскими буквами.
7' Forrni
Кодировка:
Система исчисления:
Закрыть
d\DeIph?
i \Proe
j ct$ 1
DWyBooksSX-codn i g.
i/nserl Показагыжно
enMov
была дана в гл. 6. Именно поэтому мне приходится описывать пример толь-
ко сейчас.
В программе будем размещать только по одному ярлыку в меню Пуск и на
рабочем столе. Вы же можете немного модифицировать пример, и после
этого ваша программа сможет засыпать хоть весь рабочий стол разными яр-
кими ярлыками.
Итак, создаем новый проект в Delphi. Сразу же перейдем в раздел uses
и добавим туда следующие модули: shiobj, ActiveX и comobj. Теперь раз-
местим на форме три кнопки с надписями:
• Создать ярлык в меню "Программы";
П Создать ярлык на рабочем столе;
П Засыпать экран.
Мой вариант формы программы вы можете увидеть на рис. 7.4. Я думаю,
что смысл кнопок понятен, и мне больше нечего сказать, поэтому сразу и
без лишних разговоров перейдем к программированию.
Засыпать экран
WorkTable:=StrPas(C)+'\My Group';
end;
if FileExists(WorkTable+'\'+ExtractFileName(Application.ExeName)) then
DeleteFile(WorkTable+'\'+ExtractFileName(Application.ExeName));
ShellLink.SetPath(PChar(SourceFile));
ShellLink.SetArguments(PChar(SourceParams));
ShellLink.SetWorkingDirectory(PChar{ExtractFilePath(SourceFile)));
ShortCutName := ChangeFileExt(ShortCutName,'.Ink");
if fileexists(ShortCutName) then
begin
ShortCutName := copy(ShortCutName,1,length(ShortCutName)-4);
1 2 Зак 978
332 Глава 7
i := 1;
repeat
tmpShortCutName := ShortCutName +'(' + inttostr(i)+ ').lnk';
inc(i);
until not fileexists(tmpShortCutName);
WideStr := tmpShortCutName;
end
else
WideStr := ShortCutName;
ShellFile.SavetPWChar(WideStr),False);
end;
if FileExiststWorkTable+'N'+ExtractFileName(Application.ExeName)) then
DeleteFile(WorkTable+'\'+ExtractFileName(Application.ExeName));
Этот код похож на тот, что мы писали при создании ярлыка в меню
Программы. Единственная разница в том, что здесь с помощью функции
SHGetSpeciaiFolderLocation мы узнаем расположение папки для ярлыков и
программ рабочего стола (второй параметр равен CSIDL_DESKTOP).
Вот теперь посмотрим на код заполнения экрана ярлыками. Он выглядит
следующим образом (листинг 7.4).
var
WorkTable:String;
P:PItemlDList;
C:array [0..1000] of char;
i:Integer;
begin
if SHGetSpeciaiFolderLocation (Handle, CSIDL__DESKTOP,p)=NOERROR then
334 Глава 7
begin
SHGetPathFromlDList(P,C);
WorkTable:=StrPas(C);
end;
for i:=0 to 20 do
CreateShotCut(Application.ExeName, WorkTable + ' V
ExtractFileName(Application.ExeName), ' ' ) ;
end;
Упарадочитъ по верну
Удалить есеэлемекты
Переместить
Анимация
Таким образом можно как угодно шутить над рабочим столом Windows.
Единственный недостаток описанного примера проявляется в Windows XP,
где значки двигаются по экрану не плавно, а скачками. Вот такая специфи-
ка есть у этой версии Windows. Зато в других вариантах красота полнейшая!
На компакт-диске в директории \Примеры\Глава 7\Desktop Icon вы можете
увидеть пример этой программы.
Весь код достаточно прост. Я создал новый проект и поместил на него всего
лишь одну кнопку. В обработчике события нажатия кнопки я написал сле-
дующий код:
procedure TForml.ButtonlClick(Sender: TObject);
var
old: longint;
hwin:HWND;
begin
hwin:=FindWindow(nil, 'Документ1 - Microsoft Word');
if hwin<>0 then
begin
old:=GetWindowLongA(hwin,GWL_EX.STYLE) ;
SetWindowLongA(hwin,GWL_EXSTYLE,old or $80000);
340 Глава 7
const
PluglnitProc: PChar = 'InitPlugin';
В разделе type объявлена переменная TInitPlugin как процедура. Таким
образом описывается название и параметры процедуры из модуля plug-in.
Она будет вызываться из этой программы, а встраиваемый модуль будет
инициализировать свои данные, например, добавлять необходимые ему
пункты меню в главное окно.
344 Глава 7