Захватить все команды вывода
Я хочу захватить вывод cmd.exe и показать его в другом графическом интерфейсе, который я делаю. Я хочу сделать командный интерпретатор с расширенной функциональностью. Команда dir работает безупречно, проблема возникает, когда я пытаюсь выполнить другой процесс, такой как ipconfig.
Я не вижу вывод ipconfig. Есть ли обходной путь?
Я использую компонент TProcess от Lazarus (FreePascal)
proc := TProcess.Create(nil);
proc.Options:= [poUsePipes, poNoConsole];
proc.ShowWindow:= swoHIDE;
proc.Executable:= 'cmd';
Чтение выходного потока:
if (Length(cmd) > 0) then
begin
cmd := cmd + #13#10;
proc.Input.Write(cmd[1], Length(cmd)); // here I write command from user
strikes := 0;
end
else
if proc.Output.NumBytesAvailable > 0 then
begin
while proc.Output.NumBytesAvailable > 0 do
begin
FillChar(buf, sizeof(buf), #0);
proc.Output.Read(buf, sizeof(buf) - 1);
data := data + buf;
end;
// data gets echoed to user
2 ответа
Он отлично работает для меня (я использую FPC 3.1.1 и Lazarus 1.5, но я надеюсь, что это не имеет значения):
proc.Options:= [poUsePipes];
proc.ShowWindow:= swoHIDE;
proc.Executable:= 'cmd';
...
procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char);
var
cmd: String;
begin
if Key = #13 then
begin
Key := #0;
if not proc.Active then
proc.Active := True;
cmd := Edit1.Text + LineEnding;
proc.Input.Write(cmd[1], Length(cmd));
end;
end;
procedure TForm1.Timer1Timer(Sender: TObject);
var
buf: array[0..65535] of Char;
begin
if proc.Output.NumBytesAvailable > 0 then
begin
while proc.Output.NumBytesAvailable > 0 do
begin
FillChar(buf, sizeof(buf), #0);
proc.Output.Read(buf, sizeof(buf) - 1);
Memo1.Lines.Add(buf);
end;
end;
end;
Я думаю, что вы просто не улавливаете вывод процесса должным образом. Удачи.
PS: Если вам нужно создать какое-то консольное приложение для Windows, я думаю, что лучше всего использовать консольный API Windows вместо кроссплатформенных компонентов Lazarus.
PPS: Чтобы эмулировать внешний вид и поведение консоли с помощью Lazarus, используйте компонент CmdLine.
В общем, разумно сначала проверить, не решают ли короткие примеры проблему:
например
uses process;
var s : ansistring;
begin
runcommand('ipconfig',['/all'],s);
writeln(s);
end.
работает отлично, и избавляет от многих проблем. (FPC 2.6.2+, хотя)