Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   OOP (https://www.clubdelphi.com/foros/forumdisplay.php?f=5)
-   -   Problema con bucle. (https://www.clubdelphi.com/foros/showthread.php?t=53580)

rauros 24-02-2008 18:19:36

Problema con bucle.
 
Saldudillos. He creado un pequeño programa para abrir una pagina web cada 35 segundos. El problema es que se abren todas casi al inmediato. Os pongo el sistema de bucle: (PD: no hay errores de sintaxis)

Botón que hace empezar:

Código Delphi [-]
procedure TForm1.Button2Click(Sender: TObject);
begin
timer1.Enabled:=True;
timer1.Interval:=1
end;

Bucle de tipo timer:
Código Delphi [-]
procedure TForm1.Timer1Timer(Sender: TObject);
begin
y:=StrToInt(edit21.Text);
if x < y then begin
x:= x + 1;
case x of
1:  ShellExecute(Handle, 'open', PChar(edit1.text), nil, nil, SW_SHOWNORMAL);
2:  ShellExecute(Handle, 'open', PChar(edit2.text), nil, nil, SW_SHOWNORMAL);
3:  ShellExecute(Handle, 'open', PChar(edit3.text), nil, nil, SW_SHOWNORMAL);
4:  ShellExecute(Handle, 'open', PChar(edit4.text), nil, nil, SW_SHOWNORMAL);
5:  ShellExecute(Handle, 'open', PChar(edit5.text), nil, nil, SW_SHOWNORMAL);
6:  ShellExecute(Handle, 'open', PChar(edit6.text), nil, nil, SW_SHOWNORMAL);
7:  ShellExecute(Handle, 'open', PChar(edit7.text), nil, nil, SW_SHOWNORMAL);
8:  ShellExecute(Handle, 'open', PChar(edit8.text), nil, nil, SW_SHOWNORMAL);
9:  ShellExecute(Handle, 'open', PChar(edit9.text), nil, nil, SW_SHOWNORMAL);
10: ShellExecute(Handle, 'open', PChar(edit10.text), nil, nil, SW_SHOWNORMAL);
11: ShellExecute(Handle, 'open', PChar(edit11.text), nil, nil, SW_SHOWNORMAL);
12: ShellExecute(Handle, 'open', PChar(edit12.text), nil, nil, SW_SHOWNORMAL);
13: ShellExecute(Handle, 'open', PChar(edit13.text), nil, nil, SW_SHOWNORMAL);
14: ShellExecute(Handle, 'open', PChar(edit14.text), nil, nil, SW_SHOWNORMAL);
15: ShellExecute(Handle, 'open', PChar(edit15.text), nil, nil, SW_SHOWNORMAL);
16: ShellExecute(Handle, 'open', PChar(edit16.text), nil, nil, SW_SHOWNORMAL);
17: ShellExecute(Handle, 'open', PChar(edit17.text), nil, nil, SW_SHOWNORMAL);
18: ShellExecute(Handle, 'open', PChar(edit18.text), nil, nil, SW_SHOWNORMAL);
19: ShellExecute(Handle, 'open', PChar(edit19.text), nil, nil, SW_SHOWNORMAL);
20: ShellExecute(Handle, 'open', PChar(edit20.text), nil, nil, SW_SHOWNORMAL);
end;
timer1.interval:=35000;
end
else exit;
end;

Nota: También hay un error, que es que cuando acaba de abrir todas las páginas (cuando valor x llega a ser como valor y) no cierra (exit).

ixMike 24-02-2008 18:24:22

Hola.

1º fallo: eso no es un bucle. Sí lo son los whiles, repeat y for.

2º fallo: ¿dónde está declarada x? ¿Qué valor tiene al principio? Consejo: x:=x+1; se puede escribir Inc(x); (queda más bonito ;)).

3º fallo: Pon en Interval un valor de 35000 para que pasen 35 segundos.

4º fallo: ¿De qué debería salir exit;? Exit sirve para salir del procedimiento o función, no cierra la aplicación (que se haría con Close; del formulario principal, con Application.Terminate; o con Halt;), ni anula el evento OnTimer para la próxima vez (esto se hace Timer1.Enabled:=False;)

Salu2.

dec 24-02-2008 18:26:23

Hola,

Creo que deberías planteártelo de otro modo. En lugar de un "Timer" con un intervalo de tan sólo 1 milisegundo (como ahora lo haces) este intervalo podría ser de 35000 milisegundos, es decir, justo los 35 segundos que dices.

De ese modo el evento "OnTimer" se producirá cada 35 segundos, y ahí es donde tienes que hacer lo que creas oportuno: abrir las páginas que te sean menester.

PD. Se me adelantó el compañero ixMike. ;)

rauros 24-02-2008 18:29:56

Ya pero, con el case, no tendría que hacer eso que quiero? Se activa el timer, y solo abre el que el case le diga, no? Y si no, no se como podría hacerlo. Porque si tengo que abrir edit(x).text no se como insertar x en vez de número. Y gracias de nuevo por la ayuda. Es casi inmediata.
Nota: He cambiado a halt. Ahora funciona el que se cierre la aplicación.

ixMike 24-02-2008 18:34:49

Vuélve a leer mi post, he cambiado una cosa que tenía mal :o.

Sobre el primer fallo, no era del código, sino una pequeña nota a lo que habías puesto, pues case no es un bucle, sino lo que se llama control de flujo. Sólo un pequeño detalle sobre el nombre de las cosas.

Sobre el segundo, no es un fallo, sino una pequeña duda que tengo.

El 3º es crucial para tu problema. No se abren todas de golpe, sino que con un milisegundo de diferencia, por eso no se aprecia. Cambia el valor a 35000 (35 mseg = 35 seg).

Cita:

Empezado por rauros (Mensaje 268280)
Y gracias de nuevo por la ayuda. Es casi inmediata.

Jeje, es que hoy es domingo :rolleyes:


Salu2.

Delphius 24-02-2008 18:34:50

El problema rauros es que tu en el evento OnClick del botón 2 estás pasando un intervalo de 1 milisegundo... debes indicarle que sea de 35 segundos.

Por lo otro que dices sobre Edit(X) no entiendo... ¿Que es lo que deseas?

Además no veo de donde sale x e y... ¿Para que son? Si explicases el problema...

Saludos,

ixMike 24-02-2008 18:38:12

Nos adelantamos dec y yo :D

Cita:

Empezado por Delphius (Mensaje 268282)
Por lo otro que dices sobre Edit(X) no entiendo... ¿Que es lo que deseas?

Además no veo de donde sale x e y... ¿Para que son? Si explicases el problema...

Según lo entiendo, en edit21 escribe la cantidad de páginas a abrir, en los otros edit están las direcciones de las páginas. "y" es el máximo de páginas a abrir (valor del edit21), y "x" sólo es un contador.

Según lo entiendo, claro. Por supuesto que hay mejores formas de hacer esto, pero dejemos respirar un poco a rauros ;)


Salu2.

rauros 24-02-2008 18:38:44

Okey. Voy a explicarlo todo lo que pueda:

Edit1 - Edit20 son huecos en los que se ponen los links que quiera abrir.
Edit21 es el número de páginas que vamos a abrir.
x es integer. Cada pagina abierta se le suma 1 para saber por que página va.
y es edit21 pero traducido a integer (StrToInt).

Función del programa:

Abrir páginas de una en una cada 35 segundos, a excepción de la primera, que será inmediata. El tiempo empieza a contar desde que aprieto el botón button2. Cuando acaba de abrirse todas las páginas, se cierra la aplicación.

rauros 24-02-2008 18:45:24

Vale parece que ya funciona. Cambié el milisegundo por los treinta y cinco mil.

Delphius 24-02-2008 18:48:50

Bueno rauros, debería funcionarte.
Con poner el intervalo en el button2 en 35 segundos debería funcionar.

Por el tema de cerrar la aplicación una vez que termine debes hacer algo asi:

Código Delphi [-]
if x > y
  then begin 
          Timer1.Enabled := False;
          Application.Terminate;
          // Exit sólo abandona el procedimiento o función!
         end;

Saludos,

rauros 24-02-2008 18:49:55

No hace falta, ya lo solucioné con halt; después de else pero gracias por la preocupación.

ixMike 24-02-2008 18:52:53

A ver si te gusta esta alternativa:

Coloca un TMemo, un TTimer y un TButton.

Código Delphi [-]
procedure TForm1.Button1Click(Sender: TObject);
begin
y:=Memo1.Lines.Count;
x:=0;
Timer1.Interval:=35000; //Esto se puede poner en tiempo de diseño.
Timer1.Enabled:=True;
end;

procedure TForm1.Timer1Timer(Sender: TObject);
begin
If y>x then
  begin
  ShellExecute(Handle, 'open', PChar(Memo1.Lines[x]), nil, nil, SW_SHOWNORMAL);
  Inc(x);
  end
 else
  Close;
end;


Ahora sólo tendrás que escribir las páginas en el Memo1 (sin dejar renglones en blanco). No tendrás la limitación de 20 páginas, ni tendrás que escribir la cantidad en un edit. Además, podrías poner otro edit, para indicar el tiempo (en segundos) de espera. Sólo tendrías que cambiar una cosa:

Código Delphi [-]
Timer1.Interval:=StrToInt(EditTiempo.Text)*1000; //multiplico *1000 porque está es segundos

¿Te gusta?

Salu2 ;)

Delphius 24-02-2008 18:59:13

Y bueno ya que andamos... también podemos usar otra variante (aprovechando el Memo): abrir un archivo que contenga estos datos.

E incluso podemos eliminar el timer y aún asi hacer que cada 35 segundos se visite una página. ¿O no ixMike;)?

Saludos,

rauros 24-02-2008 19:04:03

Bueno bueno, ya terminé de compilarlo y todo. He visto tu código ixMike, pero como hay cosas que no comprendo aun lo he dejado como yo lo he hecho. Muchísimas gracias.

ixMike 24-02-2008 19:19:22

Cita:

Empezado por Delphius (Mensaje 268291)
Y bueno ya que andamos... también podemos usar otra variante (aprovechando el Memo): abrir un archivo que contenga estos datos.

E incluso podemos eliminar el timer y aún asi hacer que cada 35 segundos se visite una página. ¿O no ixMike;)?

Saludos,


y también hacer un programa sin ventana, que lea de un archivo los datos, tanto las páginas como el tiempo de espera. Sería algo así: dos archivos, MiniUnidad.pas, y MuestraPaginas.dpr

Código Delphi [-]
unit MiniUnidad;

interface

//Para ahorrarnos Windows.pas
const
  SW_SHOWNORMAL = 1;

//Para ahorrarnos ShellApi.pas y Windows.pas
function ShellExecute(hWnd: Integer; Operation, FileName, Parameters,
  Directory: PChar; ShowCmd: Integer): Integer; stdcall;
procedure Sleep(dwMilliseconds: Integer); stdcall;

//Para ahorrarnos SysUtils.pas
function StrToInt(const S: String): Integer;

implementation

function ShellExecute; external 'shell32.dll' name 'ShellExecuteA';
procedure Sleep; external 'kernel32.dll' name 'Sleep';

function StrToInt(const S: String): Integer;
var n, r, m: integer;
begin
r:=0;
m:=1;
for n:=Length(S) downto 1 do
  begin
  Inc(r, (Ord(S[n])-48)*m);
  m:=m*10;
  end;
Result:=r;
end;

end.

Código Delphi [-]
program MuestraPaginas;

uses MiniUnidad;

var
  F: TextFile;  //Archivo de texto
  L: String;  //Página a abrir
  T: Integer; //Tiempo a esperar

begin
AssignFile(F, ParamStr(0)+'.txt'); //Abre el archivo MuestraPaginas.exe.txt
Reset(F);
ReadLn(F, L);
T:=StrToInt(L);
while not EOF(F) do
  begin
  ReadLn(F, L);
  ShellExecute(0, 'open', PChar(L), nil, nil, SW_SHOWNORMAL);
  Sleep(T);
  end;
CloseFile(F);
end.

No lo he comprobado, pero debería funcionar. :D


Salu2 ;)

rauros 24-02-2008 19:22:10

No se que decir. Bravo xD. Y como funcionaría? Debo crear un archivo de texto y ponerle que nombre? Y cada linea sería una página web?

ixMike 24-02-2008 19:37:08

Bueno, tiene algún fallo, pues no se ejecuta nada, ¿a alguien se le ocurre qué puede ser?:o

rauros 24-02-2008 19:48:32

No se. Yo desde cero solo se hacer programas con Turbo Pascal XD... Los demás tienen que tener las propiedades principales de unit y eso creadas ya.


La franja horaria es GMT +2. Ahora son las 18:19:25.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi