Отправляет email-рассылки с помощью сервиса Sendsay

Программирование на Delphi

  Все выпуски  

Программирование на Delphi (выпуск 43)


Программирование на DELPHI
Выпуск #43 (08 марта 2006 г.) 

Разделы сайта:

Новости сайта
Система "Эксперт"
Вопросы и Ответы
Отправить вопрос
Файловый архив
Статьи
Компоненты
Plug-in's
Документация
Исходники
Изображения
Игры
Программы
Форум
Гостевая книга
F.A.Q.
Архив рассылки
Каталог сайтов
Обратная связь
Хостинг



Связь:

Администратор
Система "Эксперт"
Информация

Доброго времени суток, уважаемые читатели!

При подготовке прошлого выпуска рассылки совсем вылетело из головы, что на сайте ExCode появился электронный журнал для программистов, и в первом выпуске этого журнала опубликовано мою интервью :-) Так что, кому интересно - почитайте на досуге. Сам журнал можно скачать здесь.

На сайте всё осталось по-прежнему - обновление системы регистрации ещё не завершено. К сожалению, эта система занимает большое место в структуре и работе всего сайта, поэтому многие изменения сделать прямо сейчас не удаётся. Думаю, к следующему выпуску рассылки всё будет завершено.

За прошедшие полторы недели пришло удивительно много вопросов. Эксперты - за работу!

Всех дам поздравляем с Международным Женским Днём!
Оставайтесь такими же, какие Вы есть!

И ещё пара замечаний экспертам, отвечающим на вопросы:
1) Не отправляйте ответы в формате html. Они неверно воспринимаются, т.к. многие почтовые клиенты совершенно неправильно генерируют html-код.
2) Не копируйте в тексты ответов огромные выдержки из MSDN - просто укажите раздел, где находится нужная информация.

Внимание! Вопросы и ответы для следующего выпуска рассылки принимаются до 17.03.2006 18:00.


Сайт "Программирование на Delphi": http://www.delphi.int.ru/ Форум нашего сайта: http://www.delphi.int.ru/forum/

До встречи!

Разделы рассылки:

Авторское слово
Новые вопросы
Ответы на вопросы
Статья по Delphi
Файловый архив
Друзья
Юмор


Количество читателей рассылки: 4114.


Подписка на рассылку:

Программирование на DELPHI


Подписаться почтой

Лидеры по количеству баллов:

Место
Имя
Баллы
Статус
1
Dron
323
Специалист
2
Ermakova Dasha
320
Специалист
3
Садовников Владимир
297
Практикант
4
Feniks
296
Практикант
5
Матвеев И.В.
260
Практикант
6
Iron Monk
200
Практикант
7
Антон Трапезников
173
Практикант
8
midav.land.ru
142
Студент
9
mvp
134
Студент
10
Лучников А.И.
131
Студент
11
Ершов Денис
125
Студент
12
PVS
124
Студент
13
Yurchik
100
Студент
14
VeroLom
90
Эксперт: 10-ый класс
15
Igor Danilevych
86
Эксперт: 9-ый класс

Некоторая статистическая информация (по системе "Эксперт"):

Статистика
На текущий момент
В прошлом выпуске
Динамика
Количество участников:
154
153
+1
Общее количество баллов:
4908
4762
+146 (!)
Средний балл:
32
31
+1
Максимальный балл:
323
320
+3
Минимальный балл:
3
3
-
Адресов в зоне .RU:
113
112
+1

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


Основные правила нашей рассылки:

1. Не присылайте ответов на вопросы вроде "да я не знаю" или "да/нет". Такие ответы не публикуются.
2. Вопросы, не касающиеся Delphi, не принимаются (для этого существуют другие рассылки).
3. Запрещено присылать вложенные файлы, объёмом выше установленного ограничения (ограничения указаны в правилах).
4. Не изменяйте тем присылаемых писем. Письма с "неправильными" темами не обрабатываются! Используйте текстовый (не HTML) формат писем. HTML-теги применяйте только в том случае, если Вы уже достигли статуса, где это разрешено (см. правила).
5. Запрещено задавать вопросы, содержащие два (или несколько) вопросов разной тематики. Каждый из таких вопросов должен быть оформлен отдельным письмом.

Задать вопрос в рассылку   |   Задать вопрос с помощью web-формы   |   Система "Эксперт"


Вопросы

Вопрос #252 (автор вопроса: Meirambek; вопрос отправлен: 26.02.2006 13:35):

Как можно на Delphi написать программу, которая даст возможность не распаковывая файлы из архива смотреть их дату создания?  [Ответить на вопрос]

Вопрос #253 (автор вопроса: Miron; вопрос отправлен: 26.02.2006 13:40):

На Delphi нужно сделать так, чтобы программа стартовала как сервисная служба Windows, или сделать сервис Windows который будет запускать программу. Можно ли решить эту проблему?  [Ответить на вопрос]

Вопрос #254 (автор вопроса: Miron; вопрос отправлен: 26.02.2006 13:44):

Как можно добавить в программу возможность оповещения по электронному адресу и по IP адресу (несколько адресов)?  [Ответить на вопрос]

Вопрос #255 (автор вопроса: RAI; вопрос отправлен: 26.02.2005 13:51):

Как с помощью ActiveX в Delphi осуществить доступ к сканеру?  [Ответить на вопрос]

Вопрос #256 (автор вопроса: Юрий Емельянов; вопрос отправлен: 27.02.2006 08:29):

Подскажите, чем открыть для редактирования файлы gdb (или хотя бы посмотреть)?  [Ответить на вопрос]

Вопрос #257 (автор вопроса: dar1; вопрос отправлен: 27.02.2006 11:51):

Уважаемые дельфяне! Есть проблема! Как писать текстовый файл с машины Win95 на машину с Windows2000 Server? Протокол только NetBios, имена и рабочая группа известы,частота записи от 3 сек и его обьём около 500 кБ. Этот файл с такой же частотой открывается для считывания информации другой программой. Может подскажете другой вариант передачи текстовой информации между данными машинами?  [Ответить на вопрос]

Вопрос #258 (автор вопроса: alex; вопрос отправлен: 28.02.2006 13:56):

Как запустить Delphi 6.0 под пользователем?  [Ответить на вопрос]

Вопрос #259 (автор вопроса: Алексей; вопрос отправлен: 28.02.2006 22:41):

Как скопировать часть текста из TRichEdit в TDBRichEdit, сохраняя форматирование?  [Ответить на вопрос]

Вопрос #260 (автор вопроса: Vital; вопрос отправлен: 02.03.2006 09:05):

Добрый день! Подскажите, пожалуйста, или дайте информацию по программированию весового контролера JagXtreme фирмы Mettler-Toledo на Delphi, или полное описание контроллера.  [Ответить на вопрос]

Вопрос #261 (автор вопроса: Игорь Середюк; вопрос отправлен: 02.03.2006 14:12):

Как определить перед открытием файла, является ли он .DBF-файлом для таблиц dBASE или FOXPRO, или нет? Если является, то определить есть ли в нем нужные поля. После этого надо его открыть и с ним работать.  [Ответить на вопрос]

Вопрос #262 (автор вопроса: LanKasper; вопрос отправлен: 03.03.2006 02:28):

При программном изменении настроек в Internet Explorer (допустим, убираем показ картинок) нужно также программно их применить (иначе изменения всупают в силу только после перезагрузки IE). Как быть?  [Ответить на вопрос]

Вопрос #263 (автор вопроса: Unknown; вопрос отправлен: 03.03.2006 12:48):

У меня есть плагин, который состоит из дочерней формы. Как ее запустить в открыть в родительской форме программы? Или плагин состоит из Фрейма. Как поместить этот фрейм в дочернюю форму программы?  [Ответить на вопрос]

Вопрос #264 (автор вопроса: Андрей Щеглов; вопрос отправлен: 03.03.2006 16:14):

Здраствуйте, господа! Подскажите, как узнать подробную информацию о процессе, если известно, допустим, EXE-имя и PID?  [Ответить на вопрос]

Вопрос #265 (автор вопроса: dar1; вопрос отправлен: 04.03.2006 07:38):

Подскажите, где можно найти описание кодов ошибок для MS Dos Client? Особенно интересует ошибка 5637.  [Ответить на вопрос]

Вопрос #266 (автор вопроса: SamProf; вопрос отправлен: 06.03.2006 02:02):

У меня вопрос следующего седержания: У Windows Media 9 и 10 есть такая фишка: правой кнопкой мыши на треепанели инструментовПроигрыватель Windows Media. Теперь, когда запускаешь проигрыватель и его сворачиваешь, появляется панелька с кнопоками управления проигрывателем! Насколко я понимаю - это какой-то ActiveX и что может его надо где-то зарегистрировать и тогда он там будет появлятся? Никто не может мне подсказать, как сделать примерный аналог этого? Спасибо!  [Ответить на вопрос]

Вопрос #267 (автор вопроса: drobbog; вопрос отправлен: 06.03.2006 23:04):

Здравствуйте, у меня такой вопрос: как можно с помощью Delphi организовать поисковую систему по FTP-ресурсам в локальной сети?  [Ответить на вопрос]


Ответы на вопросы

Вопрос #242:
Как подсчитать количество входящего/исходящего трафика с заданного IP адреса?

1. [Отвечает: Матвеев И.В. (статус: Практикант), 26.02.2006 22:09]: Во-первых Вы можете посчитать входящий/исходящий трафик только для своего IP, конечно если не рассматривать вариант снифинга, что повлечет за собой перевод сетевой карты в "слушающий" режим и очень большие сложности при написании системного драйвера.

Начните с обзора таких программ как:
- BWMeter - www.desksoft.com
- DUMeter - www.dumeter.com

Есть еще вариант - если предполагается считать трафик от Web-браузера, то можно написать локальный Proxy сервер и настроить все возможные приложения на использование Вашего локального прокси. Так, например, работает CoolProxy (если не ошибся в названии).

Оценка за ответ: 4.

2. [Отвечает: mvp (статус: Студент), 28.02.2006 9:46]: Никак обычными средствами. Нужно писать приложение, которое будет устанавливаться на машине и удалённо отсылать отчёты (backdoor какой-то, даже на трояна похоже). В этом приложении можно использовать библиотеку для подсчёта траффика (она есть на сайте сдесь - я высылал). Ну и на основе сокетов создаём клиент(на исходной машине)-сервер(на вашей) и контролируем. А так просто взять, да посчитать трафик любой машины в сети - невозможно.

Оценка за ответ: 4.

Вопрос #243:
Ребят, подскажите, как при запуске ехе-шника сделать его доступным для редактирования (если стоит пометка только чтение) и добавить некоторую информацию в реестр виндоуса и в сам ехе-шник? Как пишется код и где?

1. [Отвечает: Антон Трапезников (статус: Практикант), 26.02.2006 11:24]: Доброго времени суток! Для того чтобы убрать атрибут ReadOnly используйте следующий код:

// Если установлен атрибут "Только чтение"
if (FileGetAttr('SomeFile.exe') and faReadOnly) <> 0 then
SetFileAttributes('SomeFile.exe', 128);
// Снимаем все атрибуты

В файле SysUtils мнемоническому имени аттрибута соответствует числовой прототип (точнее наоборот, числовому значению параметра соответствует мнемонический прототип).

128 Нормальный
1 Только чтение
2 Скрытый
4 Системный
32 Архивный

Если необходимо сделать файл скрытым и системным то: SetFileAttributes('SomeFile.exe', 6);

Для записи в exe файл почитайте, для начала, о его формате, который называется PE. В com-файлах все было просто, т.к. этот устаревший формат фактически представлял собой оппкоды ассемблерных инструкций последовательно записанных в файл, причем файл состоял из одного сегмента, размером не более 64Кб. Pe - файлы имеет намного более сложную структуру и состоят из секций. Возможно, что Вам придется добавлять собственную секцию, а возможно, можно будет дописать что-либо к уже существующей (зависит от размера записываемой информации). Следует учесть что PE-файл может быть упакован (например, UPX-ом или ASPack-ом), тогда Вам необходимо произвести распаковку, а еще он может быть защищен (например, ASProtect'ом), тогда Ваша задача усложняется еще больше. И наконец, приложение может считать контрольную сумму, которая, разумеется, изменится при дописывании информации к файлу. О этих вещах можно прочитать на сайтах посвященных программированию на ассемблере (например www.wasm.ru), реверсу (www.cracklab.ru) или вирусологии (если Вы, конечно, виря и не пишете :) хотя на Delphi они не пишутся), на том же www.wasm.ru.

А вот пример записи в реестр бинарных данных, взятый из Delphiworld. Не забудьте добавить модуль Registry.

var
  Reg: TRegistry;
  buf : array [0..4] of byte;
  i: Integer;
begin
  Reg := TRegistry.Create;
  try
    Reg.RootKey := HKEY_CURRENT_USER;
    if Reg.OpenKey('\Software', True) then begin
      for i:=1 to 4 do buf[i]:=0;
      buf[0]:=1;
      Reg.WriteBinnaryData('Value', buf, sizeof(buf));
      Reg.CloseKey;
    end;
  finally
    Reg.Free;
    inherited;
  end;
  {...}
end;

Оценка за ответ: 5.

2. [Отвечает: Zeon (статус: Эксперт: 6-ой класс), 27.02.2006 1:12]: 1. Любой файл во время выполнения редактировать нельзя. Это не зависи от его атрибутов. Для редактирования нужно создать другую програму(процесс, службу), которая будет редактировать твой ехе-шник. ехе файлы являются не типизированными и работать с ними нужно соответственно. Обьявляем переменную как F: File;(например). И работаем с ней через BlockRead, BlockWrite; Перемещаемся по файлу процедурой Seek. Подробности найдешь в хэлпе.

2. Работать с реестром виндовса не сложно. Вот тебе небольшой пример:

uses
  Registry, Windows;
procedure TForm1.Button1Click(Sender: TObject);  
var  
  Registry: TRegistry;  
begin  
  { создаём объект TRegistry }
  Registry := TRegistry.Create;  
  { устанавливаем корневой ключ; напрмер hkey_local_machine или hkey_current_user }  
  Registry.RootKey := hkey_local_machine;  
  { открываем и создаём ключ }
  Registry.OpenKey('software\MyRegistryExample',true);  
  { записываем значение }
  Registry.WriteString('MyRegistryName','MyRegistry Value');  
  { закрываем и освобождаем ключ }
  Registry.CloseKey;  
  Registry.Free;  
end;

3. > Как пишется код и где?
Код пишется Руками. Красиво, правильно, не торопливо. Писать его можно во встроенном редакторе Delphi.

Оценка за ответ: 5.

3. [Отвечает: PVS (статус: Студент), 27.02.2006 9:56]: 1) Как при запуске ехе-шника сделать его доступным (если проблема только в атрибутах):

SetFileAttributes(
ParamStr(0),
GetFileAttributes(
ParamStr(0)
)or not(FILE_ATTRIBUTE_READONLY)
);

2) По реестру пишет TRegistry. Вот пример из Help'a Delphi

procedure TForm1.WMEndSession(var Message: TWMEndSession);
var
  Reg: TRegistry;
begin
  Reg := TRegistry.Create;
  try
    Reg.RootKey := HKEY_CURRENT_USER;
    if Reg.OpenKey('\Software\Microsoft\Windows\CurrentVersion\RunOnce', True) then
    begin
      Reg.WriteString('MyApp','"' + ParamStr(0) + '"');
      Reg.CloseKey;
    end;
  finally
    Reg.Free;
    inherited;
  end;
end;

Кроме WriteString есть еще WriteBinaryData, WriteBool, WriteCurrency, WriteDate, WriteDateTime, WriteExpandString, WriteFloat, WriteInteger, WriteTime так что писать можно что угодно.

3) С писанием в exe-шник не так просто, но и не слишком сложнее. Алгоритм такой: после кода можно писать все что угодно, потому просто надо определить где кончается код. Проще всего написать сначала все, что касается чтения/записи из ДРУГОГО файла начиная с определенной позиции (ее запомнить в константу) и скомпилировать. Получится программа как раз той длинны, после которой МОЖНО писать свои данные. Подставляем полученое значение в константу, меняем название файла на имя exe-шника и перекомпилируем. Размер изменится не должен (как ни странно, но иногда он не меняется даже при добвлении нескольких компонент на форму).

4) Где писать код: где надо :-) . Если серьезно, то изменение атрибутов, наверное в начале проэкта или в OnCreate главной формы. Нсколько я понял, остальное - это анализ запускалась ли програма ранее и какая-то первоначальная инициализация. В таком случае ее - туда же.

Оценка за ответ: 5.

4. [Отвечает: midav.land.ru (статус: Студент), 27.02.2006 11:24]: Официально делать запись в exe файл, который запущен нельзя. Это связано с особеностями работы ОС. Как варианты предлагали использовать автозагрузку, куда помещяется програмка, которая сделает все замены. Вариант два предполагает следующий ход. Программа сохраняет необходимые данные во временный файл. Потом запускает программу-спутник и завершает работу. Та, дождавшись завершения работы выаолняет нужные изменения и при необходимости перезапускает программу. Но есть одна военная хитрость, которая позволяет сделать всё проще. Для этого переименовываем exe-файл и делаем с ним всё что хотим. Только потом надо не забыть переименовать назад. Ну а если просто атрибут "только для чтения снять" (предупреждаю, в запущеного exe это делать запрещает операционная система), то тогда используем функцию SetFileAttributes(). Задаём ей два параметра: сначала имя файла, затем задаваемые атрибуты. Например, так можем файл сделать "только для чтения"

SetFileAttributes('C:\file.txt', faReadOnly);

Можно задавать следующие значения: faReadOnly,faHidden,faSysFile,faVolumeID,faDirectory,faArchive,faAnyFile

Оценка за ответ: 5.

Вопрос #244:
Как называется и как используется функция в Delphi, которая позволяет не писать например: абвг аБвг Абвг абВг абвГ АБвг АбВГ и т.д. Чтобы это сразу воспринималось программой как одно и то же слово?

1. [Отвечает: Антон Трапезников (статус: Практикант), 26.02.2006 11:33]: Я, обычно, привожу обе сравниваемые строки к верхнему или нижнему регистру, а только потом сравниваю. Для этого есть соответствующие функции, например:

function UpCase(Ch: Char): Char;

Которые, увы, наотрез отказываются работать с русскими буквами, поэтому используйте эти аналоги.

function UpCaseRus(ch: Char): Char;
asm
CMP AL,'a'
JB @@exit
CMP AL,'z'
JA @@Rus
SUB AL,'a' - 'A'
RET
@@Rus:
CMP AL,'я'
JA @@Exit
CMP AL,'а'
JB @@yo
SUB AL,'я' - 'Я'
RET
@@yo:
CMP AL,'?'
JNE @@exit
MOV AL,'?'
@@exit:
end;

function LoCaseRus( ch : Char ) : Char;
asm
CMP AL,'A'
JB @@exit
CMP AL,'Z'
JA @@Rus
ADD AL,'a' - 'A'
RET
@@Rus:
CMP AL,'Я'
JA @@Exit
CMP AL,'А'
JB @@yo
ADD AL,'я' - 'Я'
RET
@@yo:
CMP AL,'?'
JNE @@exit
MOV AL,'?'
@@exit:
end;

Или, если Вас не устраивает ассемблер, можете написать собственные функции перевода строк в верхний или нижний регистр. Удачи!

Оценка за ответ: 5.

2. [Отвечает: Садовников Владимир (статус: Практикант), 26.02.2006 10:51]: Используй сравнение без регистра StrIComp, либо напиши свою функцию сравнения. В крайнем случае можешь обе строки преобразовать в один регистр и сравнить.

Оценка за ответ: 4.

3. [Отвечает: Матвеев И.В. (статус: Практикант), 26.02.2006 21:41]: UpperCase - работает только для английского алфавита, поскольку во всех раскладках они расположенны одинаково, символы других языков могут располагаться в ASCII таблице где угодно.

Чтобы "поднимались" русские и английские символы используйте вот это:

function UppCase(Str: string): string;
var
  Ch: Char;
  L: Integer;
  Source, Dest: PChar;
begin
  L := Length(Str);
  SetLength(Result, L);
  Source := Pointer(Str);
  Dest := Pointer(Result);
  while L <> 0 do
  begin
    Ch := Source^;
    if ((Ch >= 'a') and (Ch <= 'z')) or
       ((Ch >= 'а') and (Ch <= 'я')) then Dec(Ch, 32);
    Dest^ := Ch;
    Inc(Source);
    Inc(Dest);
    Dec(L);
  end;
end;

Оценка за ответ: 5.

4. [Отвечает: Деревянко Евгений (статус: Эксперт: 6-ой класс), 26.02.2006 13:13]: Попробуй функции преобразования регистра:
UpperCase
LowerCase
ANSIUpperCase
ANSILowerCase

Условие ниже будет истинным: UpperCase(QwErTy) = UpperCase(qWeRtY).

Оценка за ответ: 5.

5. [Отвечает: PVS (статус: Студент), 27.02.2006 9:57]: if ANSIUpperCase(myStr='АБВГ') Then <чего-то сделать>;

Оценка за ответ: 4.

6. [Отвечает: Alexey Lukyanenko (статус: Эксперт: 3-ий класс), 27.02.2006 10:05]: Есть два варианта:
1. if AnsiUpperCase(String1) = AnsiUpperCase(String2) then ...
2. if AnsiLowerCase(String1) = AnsiLowerCase(String2) then ...

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

P.S. для Unicode-строк нужно использовать те же функции, но вместо "Ansi" использовать приставку "Wide".

Оценка за ответ: 5.

7. [Отвечает: midav.land.ru (статус: Студент), 27.02.2006 11:29]: Не очень понятно, что именно вы хотели сказать, но думаю мои идеи направят вас на нужный путь. В 7 Делфи и старше есть функция SameText(s1,s2:string):boolean. Она стравнивает две строки без учёта регистра. Если же вам необходиммо самому реализовать что- то подобное, то это делается так. Первым долгом делают регистр буковок один у всех с помощью функций:
UpperCase() - верхний регистр или
LowerCase() - нижний.
А далее просто сравниваем.

Оценка за ответ: 5.

8. [Отвечает: Алекс Рыльков (статус: Эксперт: 2-ой класс), 28.02.2006 0:54]: Тут надо использовать функции стандартного модуля SysUtils:

//uppercase
procedure TForm1.Button1Click(Sender: TObject);
begin
if uppercase(s)='HELLO' then showmessage('Добро пожаловать!');
end;
//Lowercase
procedure TForm1.Button1Click(Sender: TObject);
begin
if Lowercase(s)='hello' then showmessage('Добро пожаловать!');
end;

Но они работают только для английского алфавита. Если нужно использовать русский шрифт то можно написать что то вроде этого:

function Upcaser(stroka:string):string;
var i:byte;
begin
result:='';
        for i:=1 to length(stroka) do
           case ord(stroka[i]) of
            97..122:result:=result+upcase(stroka[i]);//a..z
            224..255:result:=result+chr(ord(stroka[i])-32)//а..я
   кроме ё
           184: result:=result+chr(168);         //ё
           else result:=result+stroka[i];//остальные символы
        end;
end;

Оценка за ответ: 5.

9. [Отвечает: mvp (статус: Студент), 28.02.2006 9:49]: Используй функции uppercase, lowercase. Первая приводит всё к верхнему регистру (большие буквы), вторая - к нижнему (маленькие).

uppercase('абВг') даст АБВГ
lowercase('АБвг') даст абвг

В программе все строки сравнивайте, применяя приведение к одному регистру.

Оценка за ответ: 5.

Вопрос #245:
Доброго времени суток! Я познакомился с Делфи буквально пару дней назад. Поэтому, если что не так, то прошу извинить. Вопрос у меня такой: как с помощью Делфи можно выполнить перезагрузку Windows XP? Заранее спасибо.

1. [Отвечает: Dron (статус: Специалист), 26.02.2006 7:44]: Можно вот так например:

function RebootOS: Boolean;
begin
  Result := ExitWindows(EWX_Reboot);
end;

И дальше вызывать: RebootOS;

Оценка за ответ: 5.

2. [Отвечает: Антон Трапезников (статус: Практикант), 26.02.2006 11:56]: В Windows есть функция ExitWindowsEx, ниже пример использования для ребута машины. Необходимо, также, добавить модуль ShellAPI. Во вложении полное описание этой функции.

Для начала, опишите эту функцию:

function MyExitWindows(RebootParam: Longword): Boolean;
var
  TTokenHd: THandle;
  TTokenPvg: TTokenPrivileges;
  cbtpPrevious: DWORD;
  rTTokenPvg: TTokenPrivileges;
  pcbtpPreviousRequired: DWORD;
  tpResult: Boolean;
const
  SE_SHUTDOWN_NAME = 'SeShutdownPrivilege';
begin
  if Win32Platform = VER_PLATFORM_WIN32_NT then
  begin
    tpResult := OpenProcessToken(GetCurrentProcess(),
      TOKEN_ADJUST_PRIVILEGES or TOKEN_QUERY,
      TTokenHd);
    if tpResult then
    begin
      tpResult := LookupPrivilegeValue(nil,
                                       SE_SHUTDOWN_NAME,
                                       TTokenPvg.Privileges[0].Luid);
      TTokenPvg.PrivilegeCount := 1;
      TTokenPvg.Privileges[0].Attributes := SE_PRIVILEGE_ENABLED;
      cbtpPrevious := SizeOf(rTTokenPvg);
      pcbtpPreviousRequired := 0;
      if tpResult then
        Windows.AdjustTokenPrivileges(TTokenHd,
                                      False,
                                      TTokenPvg,
                                      cbtpPrevious,
                                      rTTokenPvg,
                                      pcbtpPreviousRequired);
    end;
  end;
  Result := ExitWindowsEx(RebootParam, 0);
end;

А затем, для перезагрузки, вызывайте ее следующим образом:

procedure TForm1.Button1Click(Sender: TObject);
begin
  MyExitWindows(EWX_REBOOT or EWX_FORCE);
end;

// В MSDN это раздел "System Shutdown Functions" (прим. редактора)

Оценка за ответ: 5.

3. [Отвечает: Садовников Владимир (статус: Практикант), 26.02.2006 10:56]: Похоже, такой вопрос уже был... Используй функцию ExitWindowsEx(flags,reserved).

reserved=0 - всегда
flags может принимать несколько значений, из них:
EWX_POWEROFF - выключение (как понял, для ATX-машин)
EWX_SHUTDOWN - выключение (как понял, для AT-машин)
EWX_REBOOT - soft-перезагрузка

Оценка за ответ: 5.

4. [Отвечает: Матвеев И.В. (статус: Практикант), 26.02.2006 22:59]: Для этого существует отдельная функция:

ExitWindowsEx(uFlags: UINT; dwReserved: DWORD);

Ее параметр uFlags задает режим выхода (см. справку), а dwReserved=0.

Например:

ExitWindowsEx(EWX_FORCE or EWX_REBOOT, 0);

Оценка за ответ: 5.

5. [Отвечает: Виктор Александрович Вдовиченко (статус: Эксперт: 3-ий класс), 26.02.2006 22:57]:

Начну с самого простого и дойду до самого надёжного дауна и ребута.

Ниже приведённые команды можно запускать в меню "Выполнить" (Run), кнопки Пуск <Win+R>.
А в Delphi они запускаются путём всем извесной команды:

winexec(Pchar('XYZ'),sw_Show);
где 'XYZ'- одна из нижних команд:
"rundll32 shell32,SHExitWindowsEx -1" - "Холодный" перезапуск Проводника
"rundll32 shell32,SHExitWindowsEx 1" - Выключить компьютер
"rundll32 shell32,SHExitWindowsEx 0" - Завершить сеанс текущего пользователя
"rundll32 shell32,SHExitWindowsEx 2" Быстрый перезапуск Windows9x
"rundll32 krnl386.exe,exitkernel" - Выход из Windows 9x без потверждения

Вы наверное догадались уже, что эти команды справедливы для окон семейства 9х. А как быть с окнами семейства NT?
можно программно вызвать окно завершения работы:
SendMessage (FindWindow ('Progman', 'Program Manager'), WM_CLOSE, 0, 0);

А если заглянуть в MSDN (база знаний Microsoft), там рекомендуют два способа:

1 способ:
The ExitWindows function logs the current user off.
BOOL ExitWindows(

DWORD dwReserved, // reserved
UINT uReserved // reserved
);
Parameters:
dwReserved
Reserved; must be zero.
uReserved
Reserved; must be zero.
...

2 способ:
The ExitWindowsEx function either logs off, shuts down, or shuts down and restarts the system.

BOOL ExitWindowsEx(

UINT uFlags, // shutdown operation
DWORD dwReserved // reserved
);
...

А теперь по русски:

Функция ExitWindows:

Описание:
Function ExitWindows
Иницииpует стандаpтную пpоцедуpу завершение сессии current (текущего) юзера (Log OFF).

Параметры:
dwReserved
Зарезервированно; должен быть нулевым.
uReserved
Зарезервированно; должен быть нулевым.

Возвращаемые Значения:
Если функция имеет успех, возвращаемое значение отлично от нуля.
Если функция завершилась ошибкой, возвращаемое значение нулевое.

Примеры использования:
ExitWindows(0,0); // завершение сеанса

Функция ExitWindowsEx:
ExitWindowsEx() представляет собой расширенный вариант ExitWindows().

Описание:
Функция ExitWindowsEx перезагружает(restart) или выключает систему (shutdown), а также может завершить сессию для текущего юзера(log off).

Параметры:
uFlags -- флаг завершения работы, может принимать следущие значения:
[quote]EWX_LOGOFF завершает сессию текущего пользователя.
EWX_POWEROFF выключает питание компьютера(компьютер должен поддерживать данную функцию).
EWX_REBOOT перезагружает систему.
EWX_SHUTDOWN завершает работу комьпьютера до того места, где он может быть безопасно выключен: сброшенны все файловые буферы на диск, завершает работу всех процессов.
dwReserved --Зарезирвированно для последующих нужд, параметр игнорируется. [/quote]

Возвращаемое значение:
Не ноль если всё прошло успешно

Пример использования:
ExitWindowsEx(EWX_SHUTDOWN,0);
Вышеописанные примеры действительны только для w9x/Me. В NT тоже работают, но крыво.

Дело в том, что, чтобы выполнить функциию в окнах семейства NT, нужно получить права на выполнение этой функции. Сделать это можно через AdjustTokenPriviligies.

И снова лезем в MSDN

BOOL AdjustTokenPrivileges(
HANDLE TokenHandle, // handle to token that contains privileges
BOOL DisableAllPrivileges, // flag for disabling all privileges
PTOKEN_PRIVILEGES NewState, // pointer to new privilege information
DWORD BufferLength, // size, in bytes, of the PreviousState buffer
PTOKEN_PRIVILEGES PreviousState, // receives original state of changed privileges
PDWORD ReturnLength // receives required size of the PreviousState buffer
);

А теперь на Delphi:

С помощью нижеприведённой функции можно получить любую привелегию, в т.ч. и привеленгию SeShutdownPrivilege, которая нужна для разрешения функции ExitWindows(Ex)

Function SetPrivilege(aPrivilegeName: String; aEnabled: Boolean ): Boolean;
Var TPPrev,
TP: TTokenPrivileges;
Token: THandle;
dwRetLen: DWord;
Begin
Result:=False;
OpenProcessToken(GetCurrentProcess,TOKEN_ADJUST_PRIVILEGES or TOKEN_QUERY, @Token );
TP.PrivilegeCount:=1;
IF LookupPrivilegeValue(nil,PChar(aPrivilegeName),TP.Privileges[0].LUID )) then
Begin
IF aEnabled then TP.Privileges[0].Attributes:=SE_PRIVILEGE_ENABLED
else TP.Privileges[0].Attributes:=0;
dwRetLen:= 0;
Result:=AdjustTokenPrivileges(Token,False,TP,SizeOf(TPPrev),TPPrev,dwRetLen);
End;
CloseHandle(Token);
End;

Пример использования для среды NT:
SetPrivilege('SeShutdownPrivilege',True);
ExitWindowsEx(EWX_SHUTDOWN,0);

В том-же MSDN можно узнать о вида привилегий! Пользуйтесь этой базой знаний от мелко-мягких!!! Не стесняйтесь. Там всё есть, что касается окон.
Вырезка с MSDN о привелегиях:

SE_ASSIGNPRIMARYTOKEN_NAME Required to assign the primary token of a process.
SE_AUDIT_NAME Required to generate audit-log entries. Give this privilege to secure servers.
SE_BACKUP_NAME Required to perform backup operations.
SE_CHANGE_NOTIFY_NAME Required to receive notifications of changes to files or directories. This privilege also causes the system to skip all traversal access checks. It is enabled by default for all users.
SE_CREATE_PAGEFILE_NAME Required to create a paging file.
SE_CREATE_PERMANENT_NAME Required to create a permanent object.
SE_CREATE_TOKEN_NAME Required to create a primary token.
SE_DEBUG_NAME Required to debug a process.
SE_INC_BASE_PRIORITY_NAME Required to increase the base priority of a process.
SE_INCREASE_QUOTA_NAME Required to increase the quota assigned to a process.
SE_LOAD_DRIVER_NAME Required to load or unload a device driver.
SE_LOCK_MEMORY_NAME Required to lock physical pages in memory.
SE_PROF_SINGLE_PROCESS_NAME Required to gather profiling information for a single process.
SE_REMOTE_SHUTDOWN_NAME Required to shut down a system using a network request.
SE_RESTORE_NAME Required to perform restore operations.
SE_SECURITY_NAME Required to perform a number of security-related functions, such as controlling and viewing audit messages. This privilege identifies its holder as a security operator.
SE_SHUTDOWN_NAME Required to shut down a local system.
SE_SYSTEM_ENVIRONMENT_NAME Required to modify the non-volatile RAM of systems that use this type of memory to store configuration information.
SE_SYSTEM_PROFILE_NAME Required to gather profiling information for the entire system.
SE_SYSTEMTIME_NAME Required to modify the system time.
...

И на последок хочу сказать, что Вы должны проверить версию окон и принять соответствующий метод дауна и ребута. Как узнать версию винды- это уже отдельная тема. Если нужно то расскажу. Как минимум, у меня имеется четыри метода и самый простой- это проверить наличие папки System32 которой нет в окнах семейства 9х
Удачного кодинга!!!

Оценка за ответ: 5.

6. [Отвечает: PVS (статус: Студент), 27.02.2006 10:00]: Есть такая хорошая функция ExitWindowsEx - она и выключает и перегружает и зависшие проги при выключении/рестарте убивает.

Оценка за ответ: 4.

7. [Отвечает: midav.land.ru (статус: Студент), 27.02.2006 11:30]: Вот вам два примерчика, предупреждаю сразу, вы должны иметь права на перегрузку.

{ **** UBPFD *********** by delphibase.endimus.com **** >> Перезагрузка в WinNT (Убивает процессы) Зависимости: Windows Автор:       DeMoN-777, DeMoN-777@yandex.ru, Санкт-Петербург Copyright:   @ Дата:        21 июня 2002 г. ***************************************************** }
procedure reboot2;
var
  hToken: THandle;
  tkp: _TOKEN_PRIVILEGES;
  DUMMY: PTokenPrivileges;
  DummyRL: Cardinal;
begin
  DUMMY := nil;
  if not OpenProcessToken(
    GetCurrentProcess(),
    TOKEN_ADJUST_PRIVILEGES or TOKEN_QUERY,
    hToken
    ) then
    raise TShutdownEx.Create('OpenProcessToken failed');
  if (not LookupPrivilegeValue(nil, 'SeShutdownPrivilege',
    tkp.Privileges[0].Luid)) then
    raise TShutdownEx.Create('LookupPrivilegeValue failed');
  tkp.PrivilegeCount := 1;
  tkp.Privileges[0].Attributes := $0002; //SE_PRIVILEGE_ENABLED = $00002
  AdjustTokenPrivileges(hToken, FALSE, tkp, 0, Dummy, DummyRL);
  if (GetLastError() <> ERROR_SUCCESS) then
    raise TShutdownEx.Create('AdjustTokenPrivileges failed');
  if (not ExitWindowsEx(EWX_REBOOT or EWX_FORCE, 0)) then
    raise TShutdownEx.Create('ExitWindowsEx failed');
end;
----------
{ **** UBPFD *********** by delphibase.endimus.com ****
>> Перезагрузка в WinNT (не убивает процессы)
Зависимости: Windows
Автор:       DeMoN-777, DeMoN-777@yandex.ru, Санкт-Петербург
Copyright:   @
Дата:        21 июня 2002 г.
***************************************************** }

procedure reboot;
var
  hToken: THandle;
  tkp: _TOKEN_PRIVILEGES;
  DUMMY: PTokenPrivileges;
  DummyRL: Cardinal;
begin
  DUMMY := nil;
  if not OpenProcessToken(
    GetCurrentProcess(),
    TOKEN_ADJUST_PRIVILEGES or TOKEN_QUERY,
    hToken
    ) then
    raise TShutdownEx.Create('OpenProcessToken failed');
  if (not LookupPrivilegeValue(nil, 'SeShutdownPrivilege',
    tkp.Privileges[0].Luid)) then
    raise TShutdownEx.Create('LookupPrivilegeValue failed');
  tkp.PrivilegeCount := 1;
  tkp.Privileges[0].Attributes := $0002; //SE_PRIVILEGE_ENABLED = $00002
  AdjustTokenPrivileges(hToken, FALSE, tkp, 0, Dummy, DummyRL);
  if (GetLastError() <> ERROR_SUCCESS) then
    raise TShutdownEx.Create('AdjustTokenPrivileges failed');
  if (not ExitWindowsEx(EWX_REBOOT, 0)) then
    raise TShutdownEx.Create('ExitWindowsEx failed');
end;

Оценка за ответ: 5.

8. [Отвечает: Алекс Рыльков (статус: Эксперт: 2-ой класс), 28.02.2006 1:18]: Для совершения перезагрузки или выключения компьютера необходимо установить SeShutdownPrivilege. Для примера приведу следущий код:

function SetPrivilege(aPrivilegeName : string;  aEnabled : boolean ):
boolean;
var
   TPPrev,
   TP         : TTokenPrivileges;
   Token      : THandle;
   dwRetLen   : DWord;
begin
   Result := False;
   OpenProcessToken(GetCurrentProcess,TOKEN_ADJUST_PRIVILEGES or
TOKEN_QUERY, Token );

   TP.PrivilegeCount := 1;
   if( LookupPrivilegeValue(nil, PChar( aPrivilegeName ),
                            TP.Privileges[ 0 ].LUID ) ) then
   begin
     if( aEnabled )then
       TP.Privileges[0].Attributes:= SE_PRIVILEGE_ENABLED
     else
       TP.Privileges[0].Attributes:= 0;

     dwRetLen := 0;
     Result := AdjustTokenPrivileges(Token,False,TP,
                                     SizeOf( TPPrev ),
                                     TPPrev,dwRetLen );
   end;

   CloseHandle( Token );
end;


function WinExit( iflags : integer ) : boolean;
//   Возможные флаги:
//   EWX_LOGOFF
//   EWX_REBOOT
//   EWX_SHUTDOWN
begin
   Result := True;
   if( SetPrivilege( 'SeShutdownPrivilege', true ) ) then
   begin
     if not ExitWindowsEx( iflags, 0 ) then
     begin
       Result := False;
     end;
     SetPrivilege( 'SeShutdownPrivilege', False )
   end
   else
   begin
     Result := False;
   end;
end;

procedure TForm1.RestartClick(Sender: TObject);
begin
if WinExit( EWX_REBOOT) then showmessage('Ошибка');
end;

Оценка за ответ: 5.

9. [Отвечает: Лучников А.И. (статус: Студент), 28.02.2006 11:40]:

Для этого есть ExitWindowsEx (uFlags:longint;dwReserved:Word); Посмотри в хелпе значения uFlags.

Оценка за ответ: 4.

Вопрос #246:
Доброго времени суток! У меня следующий вопрос: есть программа, которая выводит звуковой сигнал по заданному расписанию. Проблема в том, что необходимо определить количество звуковых карточек и програмным путем выводить звуковые потоки из форматов *.wav *.mp3. Пытаюсь реализовать задачу на компоненте FilterGraph из библиотеки DSPACK234 (т.к. мне необходим бесплатный компонент). Но готов принять любой пример на любом компоненте или WinAPI, реализующий данную задачу. Зарание спасибо.

1. [Отвечает: Антон Трапезников (статус: Практикант), 26.02.2006 13:55]: Подключите модуль MMSystem, после чего Вы можете использовать некоторые Win32 API функции, например, функция waveOutGetNumDevs, возвращает количество звуковых карт, установленных в Вашей системе.

Она описана следующим образом:

UINT waveOutGetNumDevs(VOID);
Т.е. она возвращает беззнаковое целочисленное значение, и не принимает
параметров.

uses
MMSystem;
...
var
AudioDevicesCount: Integer;
...
AudioDevicesCount := waveOutGetNumDevs;

Проиграть звук можно функцией sndPlaySound, вот простейший пример ее использования:

sndPlaySound('C:\wavefile.wav', SND_ASYNC);

Помимо этого можно использовать функцию PlaySound:

PlaySound("SoundName", hInst, SND_RESOURCE | SND_ASYNC);

Подробное описание функций смотрите в msdn (Platform SDK), также посмотрите функции, начинающиеся на waveOutGet***.

Оценка за ответ: 5.

Вопрос #247:
Как найти и установить в RaveReport свойства MasterDataView и MasterKey для подчиненной полосы данных? Я этих свойств просто не вижу. DetailKey - без проблем. Может не там ищу?

1. [Отвечает: Alexey Lukyanenko (статус: Эксперт: 3-ий класс), 27.02.2006 10:31]: Судя по всему, Вы случайно положили не DataBand, а просто Band.

Оценка за ответ: 5.

Вопрос #250:
Как в DataSet найти запись, которая была добавлена последней? Или найти значение максималького ключа?

1. [Отвечает: Деревянко Евгений (статус: Эксперт: 6-ой класс), 26.02.2006 13:34]: Недостаточно четкое описание вопроса. Если нужно найти последний автоматически сгенерированный сервером ключ, то тут нужно воспользоваться функциями SQL сервера. Для каждого сервера это по-своему. MySQL:
select LAST_INSERT_ID()
Чтобы просто найти запись с максимальным идентификатором, нужно отсортировать выборку по убыванию ключа и взять первую запись. Опять же для каждого диалекта SQL это по разному. MySQL:
SELECT * FROM table1 ORDER BY id DESC LIMIT 1
А конкретно для датасета можно сделать что-то типа:
IndexFieldNames := 'ID';
Last;
Курсор будет на последний записи (записи с макс. идентификатором). Но такой не всегда работает. Например, не сработает для UniDirectional датасетов.

Оценка за ответ: 5.

2. [Отвечает: PVS (статус: Студент), 27.02.2006 10:10]: Дело в том, что после добавления запись может "перепрыгнуть" соответственно сортировке или просто она может быть вставлена где-то посредине. Так что в любом случае надо искать максимальный ключ:

MyQry.SQL.Text:='select max(id) from mytable';
MyQry.Active:=True;
MaxID:=MyQry.Fields[0].AsInteger;

Оценка за ответ: 5.

3. [Отвечает: midav.land.ru (статус: Студент), 27.02.2006 11:37]: Так как в базах дата добавления записи обычно не указывается, а порядок записей в файле никак не связаны с реальным временем добавления то никак. Просто когда вы удуляете записб, то вместо неё в файле как бы образуется "дырка". В эту дырку потом может добавиться новая запись. А вот на вторую часть вопроса ответить легко. Это реализовывается в два SQL запроса. Если бы вы указали используемую СУБД, то можно было бы оптимизировать. Первый запрос вида
select max(id) from tablename - получим максимальный id.
Второй:
'select * from tablename where id='+id

Оценка за ответ: 5.

Вопрос #251:
Нужно передать данные из своего приложения в интернет (скрипту), который в последствии обработает эти данные. Скрипт получает данные из $_POST["x"]. Как организовать передачу, без использования WebBrowser и HTML? Допустим, данные вводятся в Memo1. Спасибо.

1. [Отвечает: PVS (статус: Студент), 27.02.2006 10:14]: 1) Перевести все в UNICODE.
2) Послать корректный HTTP пакет данных прямо в 80-й порт сервера используя сокеты (80-й - по умолчанию, может у Вас какой другой будет).

Оценка за ответ: 3.

2. [Отвечает: midav.land.ru (статус: Студент), 27.02.2006 11:39]: Юзать Indy. там есть компонент idHTTP. Там есть возможность работы с пост запросами.

Оценка за ответ: 4.

Все вопросы и ответы на них Вы всегда можете найти на нашем сайте в разделе "Delphi-Эксперт".


Статья по программированию

Копирование файлов

Автор: Ерёмин Андрей
Использованы материалы: http://dmitry9.nm.ru/

В данной статье показаны некоторые методы копирования файлов. Существуют и готовые функции - CopyFile(), CopyFileEx(), но порой они неприменимы. Например, при использовании функции CopyFile() с большими файлами мы не имеем доступа к процессу копирования, т.е. программа на некоторое время просто "зависает". Из методов, приведённых ниже, только первый позволяет контроллировать процесс копирования - можно добавить прогресс-индикатор выполнения или отображать объём скопированных данных.

1. Копирование методом Pascal.

type
  TCallBack=procedure (Position,Size:Longint); {Для индикации процесса копирования}

procedure FastFileCopy(Const InfileName, OutFileName: String; CallBack: TCallBack);
Const BufSize = 3*4*4096; { 48Kbytes дает прекрасный результат }
type
  PBuffer = ^TBuffer;
  TBuffer = array [1..BufSize] of Byte;
var
  Size             : integer;
  Buffer           : PBuffer;
  infile, outfile  : File;
  SizeDone,SizeFile: Longint;
begin
  if (InFileName <> OutFileName) then
  begin
   buffer := Nil;
   AssignFile(infile, InFileName);
   System.Reset(infile, 1);
   try
     SizeFile := FileSize(infile);
     AssignFile(outfile, OutFileName);
     System.Rewrite(outfile, 1);
     try
       SizeDone := 0; New(Buffer);
       repeat
         BlockRead(infile, Buffer^, BufSize, Size);
         Inc(SizeDone, Size);
         CallBack(SizeDone, SizeFile);
         BlockWrite(outfile,Buffer^, Size)
       until Size < BufSize;
       FileSetDate(TFileRec(outfile).Handle,
         FileGetDate(TFileRec(infile).Handle));
     finally
      if Buffer <> Nil then Dispose(Buffer);
      System.close(outfile)
     end;
   finally
     System.close(infile);
   end;
end else
  Raise EInOutError.Create('File cannot be copied into itself');
end;

2. Копирование методом потока.

procedure FileCopy(Const SourceFileName, TargetFileName: String);
var
  S,T   : TFileStream;
begin
S := TFileStream.Create(sourcefilename, fmOpenRead );
try
  T := TFileStream.Create(targetfilename, fmOpenWrite or fmCreate);
  try
    T.CopyFrom(S, S.Size ) ;
    FileSetDate(T.Handle, FileGetDate(S.Handle));
  finally
   T.Free;
  end;
finally
  S.Free;
end;
end;

3. Копирование методом LZExpand.

uses LZExpand;

procedure CopyFile(FromFileName, ToFileName  : string);
var
  FromFile, ToFile: File;
begin
  AssignFile(FromFile, FromFileName);
  AssignFile(ToFile, ToFileName);
  Reset(FromFile);
  try
   Rewrite(ToFile);
   try
    if LZCopy(TFileRec(FromFile).Handle, TFileRec(ToFile).Handle)<0 then
     raise Exception.Create('Error using LZCopy')
   finally
    CloseFile(ToFile);
   end;
  finally
   CloseFile(FromFile);
  end;
end;

4. Копирование методами Windows.

uses ShellApi;

function WindowsCopyFile(FromFile, ToDir : string) : boolean;
var F : TShFileOpStruct;
begin
  F.Wnd := 0; F.wFunc := FO_COPY;
  FromFile:=FromFile+#0; F.pFrom:=pchar(FromFile);
  ToDir:=ToDir+#0; F.pTo:=pchar(ToDir);
  F.fFlags := FOF_ALLOWUNDO or FOF_NOCONFIRMATION;
  result:=ShFileOperation(F) = 0;
end;

// Пример копирования:
procedure TForm1.Button1Click(Sender: TObject);
begin
if not WindowsCopyFile('C:\UTIL\ARJ.EXE', GetCurrentDir) then
   ShowMessage('Copy Failed');
end;

Мной были сделаны некоторые эксперименты с данными функциями. Во всех случаях копировался один и тот же файл объёмом 122 Мб. Конечно, говорить о правильности результатов можно с трудом, ведь жёсткий диск работает по-разному - иногда быстрее, а иногда медленее. Но в любом случае, результаты есть:

Метод
Опыт 1 (сек.)
Опыт 2 (сек.)
Средняя скорость
1
3.355
3.515
3.435
2
4.467
4.286
4.377
3
3.545
3.395
3.470
4
3.696
5.478
4.587

Кажется, название функции FastFileCopy вполне оправдано. Впрочем, судить о том, какая из функций действительно работает быстрее, нужно по результатам экспериментов на большом числе компьютеров с разными конфигурациями. Но цель данной статьи была не выявить самый быстрый способ, а просто показать об этих способах. Использовать можно любой из методов, все они работоспособны.

Присылайте свои статьи по адресу info@delphi.int.ru с темой 'Articles' (без кавычек), и они будут опубликованы в ближайших выпусках рассылки и на сайте. Также вы можете заполнить вот эту форму. Большая просьба: статью оформляйте в -txt или -doc формате и используйте -zip или -rar сжатие (без самораспаковки).


Файловый архив.

Из данного раздела Вы можете скачать различные файлы: компоненты, plug-in'ы для Delphi, документацию по программированию, программы, игры, написанные на Delphi и всё остальное... Вы можете добавить свои файлы в данный раздел. Чтобы сделать это, пожалуйста, заполните форму на сайте.

К сожалению, новых файлов на сайте нет.

Название / описание файла
Категория
Объём
Ссылки

Чтобы перейти к разделу "Файловый архив" на сайте, нажмите на эту ссылку.

Дружественные сайты.

Здесь представлены ссылки на дружественные сайты. Обмен ссылками и баннерами всегда приветствуется. Здесь представлены самые последние ссылки:

На сайте собрана большая коллекция компонентов, исходников, статей, книг, что пригодится начинающему программисту. Всё это и многое другое вы найдёте на этом сайте.
http://romodos.pp.ru/
Romodos Software - Лучшие бесплатные программы, игры, музыка, рассылки, анекдоты, статьи, учебники по Delphi, HTML, JavaScript, Windows.
http://www.sassoft.narod.ru/
На данном сайте вы сможете найти разные полезные программы. Также имеется подписка на рассылку и разная полезная информация программисту.
http://www.excode.ru/
Статьи, исходники, компоненты, книги, кодерский магазин.
Рассылки Subscribe.Ru
Интернет для Delphi-программиста
Visual Basic для новичков и профессионалов
ExCode.ru - программирование на высоком уровне
   
 

Юмор.

Как известно, смертоносный вирус "Я люблю тебя" видоизменился, приняв новые обличия.
Он последовательно мутировал в вирусы:
"Ты мне нравишься"
"Ты, конечно, мне нравишься, но давай просто будем друзьями"
"Послушай, я просто хотела познакомиться..."
"Ладно, я думаю, нам нужно прервать всякие отношения!"
"Да я была просто пьяная!"
"Перестань мне звонить, идиот!"
"Ну все! Ты козел, папа твой козел и мама твоя дура!"
и, наконец, в вирус "Пошел на...!"

:))

Если взять цветной бумаги, ручку, ножницы и клей, да еще чуть-чуть отваги - можно сделать сто рублей...
... Не забудь еще одно в тюрьме: сыро и темно.

:))

Внимание! Вы изменили положение мыши. Для того, чтобы изменения вступили в силу, необходимо перезагрузить компьютер.

:))

Фармацевтика - наука о форматировании диска C.

:))

Сеть - это дырки, связанные веревками.

:))

Bpaч дeлaeт oбхoд, гpaдycники y бoльных coбиpaeт, пpoпиcывaeт лeчeниe, пoдхoдит к кoйкe oднoгo бoльнoгo и cпpaшивaeт сecтpy:
- Фaмилия бoльнoгo?
- Bиндoвc, тoлькo ceйчac пocтyпил.
- Имя oтчecтвo?
- Дeвянocтo восемь.
- Бoлeзнь?
- Хpoничecкиe зaвиcaния и cлaбocть yмa. Чeм бyдeм лeчить?
- Mopгoм.

:))

"...Для продолжения установки Win'2000 вставьте 45234-ю дискету..."

:))

- А чё UNIX, чё UNIX? - возмущался Вывоуз, - Малыш Билли ещё на Васике лопал, когда она уже была. Старушенция дряхлая!
- Ты бабушку не трогай! - серьёзно обиделся товарищ Команд ком, - Она тебе, глюкало переросток, ещё фору даст!!! - но, подумав, товарищ Ком помрачнел и добавил:
- Вот только какого демона она на мою территрию лезет!
И сплюнул:
- Оболочка дешевая.

:))

Периоды зачатия инетчика:
1. Connect
2. Download
3. Disconnect
4. UnZip (Estimated time: 9 месяцев)

:))

Интернетчик пишет объявление в конференцию:
- Девушки, выходите за меня замуж! Стране нужны хакеры.
Возникает флейм:
- Девушки, не верьте ему, он вас сломает, хакнет и выложит на ББС с паролем общего доступа,
а потом и вообще бросит. Все это ничего, он вас еще и вирусом заразит...

:))

Из диалога в аське:
- Котенка комy? Качественный. Почти не юзаный, 2 месяца всего. Укомплектованный. Есть шеpсть (веселенькой чеpно-белой окpаски), лапы (4шт), yсы (несчитанно) и ypчальник (встpоенный). Сабж обладает фyнкцией мочеиспyскания в тyалет, лежания на телевизоpе свесив хвост на экpан и неyемной жизнеpадостностью. Фyнкция питания отлажена пpосто на диво: с yдовольствием жpет даже хлеб и макаpоны. И все это счастье я отдаю пpосто так, для хоpоших людей не жалко!
- Бpандовый? Глюков нет? Апгpейдится? Манибек? Гаpантия? Мышь опознает?

:))

Разговор по аське:
- Что замолчал?
- Пальцы устали.

:))

Вопросы ламера:
1. Почему какой-то Disconnect мешает мне сидеть в Интернете, и пробовал ли кто-нибудь подавать на него в суд?
2. Кто такой "General Failure" и почему он считывает с моего винчестера?
3. Почему ДОС никогда не говорит "Excellent command or filename"?

:))

Умный программист всегда сумеет занять компьютер глупой работой.

Анекдоты прислал: bruder.

Присылайте свои анекдоты по этой ссылке: info@delphi.int.ru и они обязательно будут опубликованы. Желательно на компьютерную тему.

Товарищи программисты! Проявляйте свою активность. Давайте помогать друг другу! Если вы не нашли ответа на свой вопрос, не отчаивайтесь! Количество подписчиков постоянно растёт и, наверняка, найдётся тот человек, который поможет вам! а сегодня всё. До встречи через неделю!
Ведущий рассылки, Ерёмин Андрей.

Наши реквизиты в системе WebMoney: R379291065219, Z165075684614.


В избранное