PDA

Ver la Versión Completa : Enviar resultado de operaciones a base de datos


The Cid James
15-11-2017, 09:17:50
Buenas gente, estoy tratando de calcular unos valor de unas operaciones a la base de datos pero el post "se hace en blanco"
Este es el código del botón que debería hacer el post a la base de datos pero al precionarlo no pasa nada ni siquiera sale un error.

procedure Tfcantidad.BCokClick(Sender: TObject);
var
a: integer; // Cantidad de Articulos
d: integer; // N° de venta anterior
e: integer; // N° de venta actual
f: integer; // Precio Unitario
g: integer; // Precio total por prdoducto

begin
fmodulo.tVentadetalle.Active := true;
fmodulo.tProductos.Active := true;
fmodulo.tVentadetalle.Insert;
if (strtoint(Ecantidad.Text)<=0)
then
begin
Application.MessageBox('El valor ingresado debe ser mayor a O', 'Drugstore',mb_yesno+mb_iconquestion);
end
else
if Ecantidad.Text = not null
then
begin
a := fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsInteger;
d := fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger;
e := (d + 1);
fmodulo.tVentadetalle ['id_ventas'] := IntToStr(e);
fmodulo.tVentadetalle ['id_producto'] := fmodulo.tProductos ['id_producto'];
f := fmodulo.tProductos.Fields.FieldByName('precio_vent').AsInteger;
g := (a * f);
fmodulo.tVentadetalle ['Precio_v'] := IntToStr(g);
fmodulo.tVentadetalle ['cantidad'] := IntToStr(a);
fmodulo.tVentadetalle.Post;
fmodulo.tVentadetalle.Refresh;
end;
self.Close;
end;

Como siempre muchas gracias

movorack
15-11-2017, 14:26:06
Haz un pequeño cambio para evaluar si el edit tiene algo digitado.


//if Ecantidad.Text = not null
if Length(Trim(Ecantidad.Text)) > 0


Si es XE3 o superior puede ser:

//if Ecantidad.Text = not null
if String(Ecantidad.Text).Trim.Length > 0

Caminante
15-11-2017, 14:41:09
Hola


if Ecantidad.Text = not null



Y esa linea te compila??? :confused::confused::confused::confused:

luisgutierrezb
15-11-2017, 15:11:37
Otra cosa, yo te recomendaria poner el insert junto al codigo donde asignas los valores a la tabla, porque primero haces el insert y luego tomas valores (pero los valores te los va a tomar en blanco porque esta el insert) y luego haces operaciones para guardar en la tabla... Saludos!

movorack
15-11-2017, 16:31:25
Y esa linea te compila??? :confused::confused::confused::confused:

Yo también quedé :confused::confused::confused: y repliqué eso en mi delphi. y Si! si compila y si haces debug cuando pones la expresión en el evaluador dice que la expresión es inválida.

alexcarballo
15-11-2017, 17:02:36
Eimina la línea:
fmodulo.tVentadetalle.Refresh;

El Refresh me ha dado ese error.

alexcarballo
15-11-2017, 17:04:27
Otra cosa, yo te recomendaria poner el insert junto al codigo donde asignas los valores a la tabla, porque primero haces el insert y luego tomas valores (pero los valores te los va a tomar en blanco porque esta el insert) y luego haces operaciones para guardar en la tabla... Saludos!
Ademas si la tabla ya viene con datos lo que debes hacer es un Edit no Insert

The Cid James
16-11-2017, 08:01:32
Haz un pequeño cambio para evaluar si el edit tiene algo digitado.


//if Ecantidad.Text = not null
if Length(Trim(Ecantidad.Text)) > 0


Si es XE3 o superior puede ser:

//if Ecantidad.Text = not null
if String(Ecantidad.Text).Trim.Length > 0

La pripiedad text del edit tiene valor por defecto 0 por lo cual no podria estar vacio de todas formas :confused:

Yo también quedé :confused::confused::confused: y repliqué eso en mi delphi. y Si! si compila y si haces debug cuando pones la expresión en el evaluador dice que la expresión es inválida.

No se donde lo habia leido mientras buscaba informacion y me funciono asi que lo deje :rolleyes:

Eimina la línea:
fmodulo.tVentadetalle.Refresh;

El Refresh me ha dado ese error.

No se que error te da pero a mi no me marca nada de echo creo que el error esta en las asignaciones de las variables porque sino hago los calculos si hace el post (obviamente con resultados no calculados que no me sirve)

Otra cosa, yo te recomendaria poner el insert junto al codigo donde asignas los valores a la tabla, porque primero haces el insert y luego tomas valores (pero los valores te los va a tomar en blanco porque esta el insert) y luego haces operaciones para guardar en la tabla... Saludos!
Tengo entendido que al poner la tabla en modo insert mientras dure el proceso no deberia causar problemas de echo tengo varias tablas que tengo en modo insert desde el momento que abro el form y postea bien

Ademas si la tabla ya viene con datos lo que debes hacer es un Edit no Insert
Cada dato se calcula y postea en ese momento, sino hubiera usado el edit si fuera el caso.

Gracias a todos por la ayuda gente el error como dije anteriormente esta en los cálculos porque si inserto otros datos en la tabla sin hacer los cálculos si lo toma normalmente. También he notado que en ningun momento le asigno el valor del Edit a la variable A para hacer los cálculos y la verdad que no se como hacerlo busque en la web pero siempre me sale algún error :confused::confused:

The Cid James
16-11-2017, 08:58:17
Probe lo que dijo movorack y efectivamente era eso, con eso postea los datos pero sigue sin hacer los calculos

begin
fmodulo.tVentadetalle.Active := true;
fmodulo.tProductos.Active := true;
fmodulo.tVentadetalle.Insert;
if (strtoint(Ecantidad.Text)<=0)
then
begin
Application.MessageBox('El valor ingresado debe ser mayor a O', 'Drugstore',mb_yesno+mb_iconquestion);
end
else
if String(Ecantidad.Text).Trim.Length > 0
then
begin
a := (StrToInt(Ecantidad.text));
a := fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsInteger;
d := fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger;
e := (d + 1);
fmodulo.tVentadetalle ['id_ventas'] := IntToStr(e);
fmodulo.tVentadetalle ['id_producto'] := fmodulo.tProductos ['id_producto'];
f := fmodulo.tProductos.Fields.FieldByName('precio_vent').AsInteger;
g := (a * f);
fmodulo.tVentadetalle ['Precio_v'] := IntToStr(g);
fmodulo.tVentadetalle ['cantidad'] := IntToStr(a);
fmodulo.tVentadetalle.Post;
fmodulo.tVentadetalle.Refresh;
end;
self.Close;
end;

end.

movorack
16-11-2017, 22:20:21
En este post (http://www.clubdelphi.com/foros/showthread.php?t=92497) ya AgustinOrtu te habia hecho comentarios sobre tu código.


De todos modos, el codigo que publicaste esta raro y por eso te da problemas.
Primero convertis de string a Integer el contenido del edit, y lo guardas en una variable.
Luego, en lugar de usar esa variable, volves a convertir para la validacion.
Y despues de validar, asignas en la misma variable el valor de un campo de la tabla, osea el valor que asignaste al principio nunca lo usaste. Creo que eso responde al "no se supone que le estoy dando valor?"

Imagino que no lo leíste pq no hiciste ningún cambio. Y de verdad el fue amable con decir "raro" ya que eso tiene apelativos de mucho mas calibre.

No se a que calculos te frefieres porque este hilo trata de que no podias guardar en la DB pero de verdad, Revisa bien tu código.

The Cid James
17-11-2017, 00:16:23
En este post (http://www.clubdelphi.com/foros/showthread.php?t=92497) ya AgustinOrtu te habia hecho comentarios sobre tu código.



Imagino que no lo leíste pq no hiciste ningún cambio. Y de verdad el fue amable con decir "raro" ya que eso tiene apelativos de mucho mas calibre.

No se a que calculos te frefieres porque este hilo trata de que no podias guardar en la DB pero de verdad, Revisa bien tu código.

Si lo lei y si lo cambie, en ese momento no estaba usando los valores de la variables y si controle lo de asignarle de no asignarlo mal si te fijas en el código del post lo cambie ... bastante de echo igual me voy a poner a leer lo que encuentre a ver como lo soluciono

Saludos

movorack
17-11-2017, 15:29:48
No se... Seguiste con las mismas asignaciones. lee los comentarios y entenderás un poco lo que trato de decirte


procedure TfCantidad.BCokClick(Sender: TObject);
var
//Mejor coloca nombres de variables que signifiquen algo
//a : Integer; // Cantidad de Articulos
CantArts: integer; // Cantidad de Articulos
begin
fmodulo.tVentadetalle.Active := true;
fmodulo.tProductos.Active := true;

//Esta validación la coloco acá porque la vienes haciendo en tu código,
//pero es innecesaria o no estás haciendo bien las cosas ya que en ningún lugar de tus cálculos usas el valor del
//TEdit Ecantidad. Si bien lo asignas a una variable mas adelante, enseguida a esa misma variable le asignas un
//valor traído del dataset
if (string(Ecantidad.Text).Trim.Length = 0)
or (not TryStrToInt(Ecantidad.Text, CantArts)) // <= Si la conversión es correcta, aquí ya se asigna el valor del edit a la variable
then
begin
Application.MessageBox('El valor ingresado debe ser mayor a O', 'Drugstore',mb_yesno+mb_iconquestion);
Exit;
end;

if fmodulo.tVentadetalle.State in [dsEdit, dsInsert] then
fmodulo.tVentadetalle.Cancel;

fmodulo.tVentadetalle.Insert;

{
a := (StrToInt(Ecantidad.text)); // Esta asignación la pierdes con la siguiente línea

//Y no es necesario asignar a variable todo lo del dataset. Puedes usar los valores directamente
a := fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsInteger;
d := fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger;
e := (d + 1);
fmodulo.tVentadetalle ['id_ventas'] := IntToStr(e);
fmodulo.tVentadetalle ['id_producto'] := fmodulo.tProductos ['id_producto'];
f := fmodulo.tProductos.Fields.FieldByName('precio_vent').AsInteger;
g := (a * f);
fmodulo.tVentadetalle ['Precio_v'] := IntToStr(g);
fmodulo.tVentadetalle ['cantidad'] := IntToStr(a);
}

//El consecutivo trata de no calcularlo en el programa y dejarlo a que lo calcule la DB. Cuando tengas varios clientes al mismo tiempo vendiendo esto será un dolor de cabeza
fmodulo.tVentadetalle.Fields.FieldByName('id_ventas').AsString := IntToStr(fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger + 1);
fmodulo.tVentadetalle.Fields.FieldByName('id_producto').Value := fmodulo.tProductos.Fields.FieldByName('id_producto').Value;
fmodulo.tVentadetalle.Fields.FieldByName('Precio_v').AsString := IntToStr(fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsInteger * fmodulo.tProductos.Fields.FieldByName('precio_vent').AsInteger);
fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsString := fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsString;
fmodulo.tVentadetalle.Post;
fmodulo.tVentadetalle.Refresh;

self.Close;
end;


He tratado de utilizar los mismos tipos de datos que al parecer tienes en tu dataset. pero cosas como el precio y cantidad es mejor que los coloques como float. EN un futuro pueden decirte que quieren vender medio paquete de cigarrillos o que el valor de un producto con oferta es de 9.99

The Cid James
20-11-2017, 11:04:24
No se... Seguiste con las mismas asignaciones. lee los comentarios y entenderás un poco lo que trato de decirte


procedure TfCantidad.BCokClick(Sender: TObject);
var
//Mejor coloca nombres de variables que signifiquen algo
//a : Integer; // Cantidad de Articulos
CantArts: integer; // Cantidad de Articulos
begin
fmodulo.tVentadetalle.Active := true;
fmodulo.tProductos.Active := true;

//Esta validación la coloco acá porque la vienes haciendo en tu código,
//pero es innecesaria o no estás haciendo bien las cosas ya que en ningún lugar de tus cálculos usas el valor del
//TEdit Ecantidad. Si bien lo asignas a una variable mas adelante, enseguida a esa misma variable le asignas un
//valor traído del dataset
if (string(Ecantidad.Text).Trim.Length = 0)
or (not TryStrToInt(Ecantidad.Text, CantArts)) // <= Si la conversión es correcta, aquí ya se asigna el valor del edit a la variable
then
begin
Application.MessageBox('El valor ingresado debe ser mayor a O', 'Drugstore',mb_yesno+mb_iconquestion);
Exit;
end;

if fmodulo.tVentadetalle.State in [dsEdit, dsInsert] then
fmodulo.tVentadetalle.Cancel;

fmodulo.tVentadetalle.Insert;

{
a := (StrToInt(Ecantidad.text)); // Esta asignación la pierdes con la siguiente línea

//Y no es necesario asignar a variable todo lo del dataset. Puedes usar los valores directamente
a := fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsInteger;
d := fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger;
e := (d + 1);
fmodulo.tVentadetalle ['id_ventas'] := IntToStr(e);
fmodulo.tVentadetalle ['id_producto'] := fmodulo.tProductos ['id_producto'];
f := fmodulo.tProductos.Fields.FieldByName('precio_vent').AsInteger;
g := (a * f);
fmodulo.tVentadetalle ['Precio_v'] := IntToStr(g);
fmodulo.tVentadetalle ['cantidad'] := IntToStr(a);
}

//El consecutivo trata de no calcularlo en el programa y dejarlo a que lo calcule la DB. Cuando tengas varios clientes al mismo tiempo vendiendo esto será un dolor de cabeza
fmodulo.tVentadetalle.Fields.FieldByName('id_ventas').AsString := IntToStr(fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger + 1);
fmodulo.tVentadetalle.Fields.FieldByName('id_producto').Value := fmodulo.tProductos.Fields.FieldByName('id_producto').Value;
fmodulo.tVentadetalle.Fields.FieldByName('Precio_v').AsString := IntToStr(fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsInteger * fmodulo.tProductos.Fields.FieldByName('precio_vent').AsInteger);
fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsString := fmodulo.tVentadetalle.Fields.FieldByName('cantidad').AsString;
fmodulo.tVentadetalle.Post;
fmodulo.tVentadetalle.Refresh;

self.Close;
end;


He tratado de utilizar los mismos tipos de datos que al parecer tienes en tu dataset. pero cosas como el precio y cantidad es mejor que los coloques como float. EN un futuro pueden decirte que quieren vender medio paquete de cigarrillos o que el valor de un producto con oferta es de 9.99

Muchas gracias por tomarte el tiempo de explicarme!
Ahora bien voy a seguir tus consejos pero me quedan las siguientes dudas:
Si me di cuenta que no estaba usando el valor de la asignacion por eso no hacia los calculos, aunque no tenia ni idea de como hacerlo iba a hacer ahora un post con eso ahora que me tengo tiempo xD
En el caso de
d := fmodulo.qnumventa.Fields.FieldByName('id_venta').AsInteger;
e := (d + 1);
Esto lo hacia porque uso un autoincremental en venta, pero el post se hace despues de que se realiza la venta por lo cual no se asigna igual no sabia que podía usar los datos directamente de la base de datos en tiempo de ejecución para hacer los cálculos.
Y la ultima duda que tengo es sobre
if fmodulo.tVentadetalle.State in [dsEdit, dsInsert] then
fmodulo.tVentadetalle.Cancel;

Este codigo es necesario? porque abro y cierro el modo insert en cada boton con el que trabajo o sirve como medida de seguridad si lo tengo abierto de otro lado?
Ademas probando el codigo me dice que dsEdit y dsInsert son variables no definidas (sera porque uso zeoslib?) y la "cantidad" se carga con el valor 1 y no con el valor que le estoy cargando el tedit