Saltar al contenido

FORMULARIO DE LOGIN

publicado

Hola a todos,

Tengo el siguiente problema: He creado un formulario para grabar contactos dentro de una hoja de datos llamada "CONTACTOS" y cada vez que introduzco algún dato incorrecto, de manera alguna el formulario vuelve a grabar el mismo registro tantas veces como haya fallado dentro de la hoja de datos.

Muestro por aquí mi formulario...

1.thumb.jpg.6b27d4814a9cc3c9a46e9f0eff5ba196.jpg

Como se puede observar en la imagen adjunta, tiene un casillero inicial para elegir el tipo de contacto ("Proveedor" o "Cliente") y el resto de los datos están dispuestos en modo multipágina. "Denominación" para grabar los datos fiscales, "Domiciliación" para los datos de localización y "Comunicación" para los datos de contacto.

Bueno, eso es lo de menos...

Fíjaros lo que me pasa. Lo explíco con un ejemplo: Supongamos que introduzco una cadena de caracteres en el casillero del "Código Postal", y me salta un mensaje de alerta que me notifica del error cometido, para lo cual vuelvo a introducir de nuevo los datos esta vez sí en formato numérico.

2.thumb.jpg.5d727e8385a38458e9a8766c44ac85f3.jpg

Nos vamos a la página de contactos. Y podemos observar que el mismo registro ha sido grabado dos veces. Esto se debe porque me he equivocado una vez al introducir un código postal con caracteres de texto en vez de con números. Si me hubiera equivocado tres veces, se grababa el mismo dato tres veces, y si fueran mil, pues mil veces...

3.thumb.jpg.06f61e095167ead87f0f844cfc778da9.jpg

Adjunto mi código aquí...

Option Explicit


Private Sub UserForm_Initialize()

   ' Adjuntamos la lista de perfiles...
   With tbContacto
      .AddItem "Proveedor"
      .AddItem "Cliente"
      .AddItem "Otro..."
   End With

   ' Y adjuntamos la lista de países...
   With tbPais
      .AddItem "Alemania"
      .AddItem "España"
      .AddItem "Estados Unidos"
      .AddItem "Francia"
      .AddItem "Gran Bretaña"
      .AddItem "Países Bajos"
   End With

End Sub


Private Sub cbGrabar_Click()

Application.ScreenUpdating = False

   ' Tratamos los errores de la aplicación ofimática...
   On Error GoTo error

   ' Declaramos las variables de ámbito local...
   Dim fila As Long
   Dim deseaContinuar As Byte

inicio:
   ' Comprobamos que el cuadro combinado del código postal no está vacío...
   If (tbContacto = "Cliente" And tbCodigoPostal.Value = "") Or _
      (tbContacto = "Cliente" And IsNumeric(tbCodigoPostal.Value) = False) Then

      FormularioDeContactos.Hide
      MsgBox Prompt:="Upps, parece que hubo un error... Por favor, debe introducir un código postal " & _
                           "para ubicar al cliente.", _
             Buttons:=vbExclamation, _
             Title:="                                     CODIGO POSTAL INCORRECTO"
      FormularioDeContactos.Show
      GoTo inicio

   ' Comprobamos que el cuadro combinado de la provincia no está vacía...
   ElseIf tbProvincia.Value = "" Then

      FormularioDeContactos.Hide
      MsgBox Prompt:="Upps, parece que hubo un error... Por favor, debe introducir una provincia " & _
                           "para ubicar al " & _
                           IIf(tbContacto.Value = "Proveedor", "proveedor.", "cliente."), _
             Buttons:=vbExclamation, _
             Title:="                                          PROVINCIA INCORRECTA"
      FormularioDeContactos.Show
      GoTo inicio

   ' Comprobamos que el cuadro combinado del país no está vacío...
   ElseIf tbPais.Value = "" Then

      FormularioDeContactos.Hide
      MsgBox Prompt:="Upps, parece que hubo un error... Por favor, debe introducir un país " & _
                           "para ubicar al " & _
                           IIf(tbContacto.Value = "Proveedor", "proveedor.", "cliente."), _
             Buttons:=vbExclamation, _
             Title:="                                                 PAIS INCORRECTO"
      FormularioDeContactos.Show
      GoTo inicio

   End If

   ' Grabamos toda la información actual dentro de la hoja de contactos...
   fila = Sheets("CONTACTOS").Range("A1048576").End(xlUp).Row + 1

   With Sheets("CONTACTOS")
      .Cells(fila, 1) = tbContacto.Value           ' Tipo de contacto
      .Cells(fila, 2) = tbCodigo.Value             ' Código (PK)
      .Cells(fila, 3) = tbDniCif.Value             ' DNI / CIF
      .Cells(fila, 4) = tbNombre.Value             ' Nombre y apellidos / Nombre comercial
      .Cells(fila, 5) = tbNombreFiscal.Value       ' Nombre fiscal
      .Cells(fila, 6) = tbDireccionPostal.Value    ' Dirección postal
      .Cells(fila, 7) = tbCodigoPostal.Value       ' Código postal
      .Cells(fila, 8) = tbPoblacion.Value          ' Población
      .Cells(fila, 9) = tbProvincia.Value          ' Provincia
      .Cells(fila, 10) = tbPais.Value              ' País
      .Cells(fila, 11) = tbWeb.Value               ' Sitio web
      .Cells(fila, 12) = tbWeb2.Value              ' Otros sitios web
      .Cells(fila, 13) = tbEmail.Value             ' Correo electrónico
      .Cells(fila, 14) = tbTelefonoFijo.Value      ' Teléfono fijo
      .Cells(fila, 15) = tbTelefonoMovil.Value     ' Teléfono móvil
      .Cells(fila, 16) = tbFax.Value               ' Fax
   End With

   ' Ocultamos el formulario de contactos...
   FormularioDeContactos.Hide

   ' Mostramos un mensaje de alerta para notificar al usuario de que el registro se ha grabado correctamente...
   deseaContinuar = MsgBox(Prompt:="El contacto ha sido grabado correctamente." & vbCr & _
                                   "¿Desea continuar grabando datos?", _
                           Buttons:=vbYesNo + vbInformation, _
                           Title:="                                  AVISO IMPORTANTE")

   ' Si la respuesta es afirmativa...
   If deseaContinuar = vbYes Then

      ' Mostramos el formulario de contactos...
      FormularioDeContactos.Show

   ' Pero si la respuesta es negativa...
   Else

      ' Activamos la hoja correspondiente...
      Sheets("CONTACTOS").Activate

      ' Salimos del procedimiento...
      GoTo salir

   End If

salir:
   ' Y salimos del procedimiento...
   Exit Sub

error:
   ' Mostramos por pantalla el tipo de error y la descripción del mismo...
   MsgBox Prompt:="Upps, parece que hubo un error... Por favor, póngase directamente " & _
                  "en contacto con su programador informático." & vbCr & vbCr & _
                  "El error producido es: [" & Err.Number & "] - " & Err.Description, _
          Buttons:=vbCritical, _
          Title:="                                               AVISO IMPORTANTE"

   ' Sacamos el error fuera de la pila de errores...
   Resume salir

End Sub


Private Sub cbSalir_Click()

   ' Cerramos el formulario de contactos...
   Unload FormularioDeContactos

End Sub


Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)

   ' Habilitamos única y exclusivamente el control a través de los botones del formulario...
   If CloseMode = vbFormControlMenu Then
      MsgBox Prompt:="Por favor, utilice los botones 'Grabar' y 'Salir' para navegar por el formulario " & _
                     "de contactos.", _
             Buttons:=vbExclamation, _
             Title:="                                              AVISO IMPORTANTE"
      Cancel = True
   End If

End Sub

Normalmente, esto lo solucionaba con la propiedad variable.Cancel o variable.Default con valor igual a "True". Es decir, algo como esto...

...
	If (tbContacto = "Cliente" And tbCodigoPostal.Value = "") Or _
       (tbContacto = "Cliente" And IsNumeric(tbCodigoPostal.Value) = False) Then

      FormularioDeContactos.Hide
      MsgBox Prompt:="Upps, parece que hubo un error... Por favor, debe introducir un código postal " & _
                           "para ubicar al cliente.", _
             Buttons:=vbExclamation, _
             Title:="                                     CODIGO POSTAL INCORRECTO"
      FormularioDeContactos.Show

	  tbCodigoPostal.Default = True		' Reestablecemos la variable en el valor inicial por defecto...

      GoTo inicio
...

Por aquí continúa el código anterior...

Pero en esta ocasión, no me funciona.

Creo haberme explicado bien. Si necesitáis más detalles, dejadme un comentario.

Necesito que alguien me arroje algo de lucidez sobre este tema, porque el formulario funciona correctamente tal y como habéis visto. El problema es que cuando alguien comete un error al grabar los datos, es como si el mismo registro se grabara tantas veces como errores cometiera al grabar el registro.

 

Muchísimas gracias por vuestro tiempo.

Featured Replies

publicado

Hola

Te recomiendo usar el evento "change" del textbox, de tal manera que solo acepte valor numérico; investiga un poco sobre lo que te comento, aquí mismo en el foro, puedes buscar

Otra cosa por favor sube un archivo con el problema y el formulario, pues por lo menos yo, no estoy dispuesto siempre a ver todo el testamento e imágenes que has agregado al tema

 

Saludos!

publicado
  • Autor
Hace 10 horas, Gerson Pineda dijo:

Otra cosa por favor sube un archivo con el problema y el formulario, pues por lo menos yo, no estoy dispuesto siempre a ver todo el testamento e imágenes que has agregado al tema

Normalmente lo hago así para que la gente que lea el mensaje a través del foro, pueda ver el código sin necesidad de descargarse ningún fichero que pueda estar contagiado por algún virus, pues ya bastante tenemos con lo que tenemos... Jeje.

 

De todos modos y si así lo prefieres, te adjunto aquí el fichero:

Libro1.xlsm

 

SUPUESTO: Prueba a introducir una cadena de caracteres o dejar vacío el cuadro de texto del "Código Postal", y ya verás como el mismo registro se graba dos veces dentro de la hoja "CONTACTOS".

Si erráramos tres veces, pues se grabaría tres veces, y así sucesivamente...

 

Normalmente, ya digo que esto lo solucionaba con la propiedad .Cancel o .Default = True.

Pero en esta ocasión no funciona...

 

Gracias por tu tiempo.

publicado

Ese comportamiento lo provocas tu con la sentencia GoTo inicio, que se ejecuta tantas veces como errores encuentra al meterte en un bucle.

Sustituye GoTo inicio por Exit Sub y problema resuelto.

En otro orden de cosas, Microsoft se molestó en poner una cruz en la parte superior derecha para cerrar los formularios, no se porqué esa manía de deshabilitar ese botón y no me digas que es por seguridad, ya que es más fácil pulsar el botón Salir por error, que pulsar sobre la cruz.

 

publicado

Hola!

A mi gusto lo tienes mal planteado, te lo explico:

Si vas a utilizar multipage es preferible que los botones estén asignados por cada page, si no entonces debes asegurar que por cada page activo, el único botón "Grabar" audite los controles si están vacíos o según la restricción que dispongas, de lo contrario puedes usar los eventos del control, de manera que escriban en ellos lo que tu requieras

 

Saludos 

publicado
  • Autor
Hace 7 horas, Antoni dijo:

Sustituye GoTo inicio por Exit Sub y problema resuelto.

Solucionado! A veces me rompo la cabeza en encontrar la solución más complicada, y resulta ser la más fácil.

Muchas gracias, @Antoni. Funciona perfectamente, tal y como dices.

 

Hace 2 horas, Gerson Pineda dijo:

Si vas a utilizar multipage es preferible que los botones estén asignados por cada page, si no entonces debes asegurar que por cada page activo, el único botón "Grabar" audite los controles si están vacíos o según la restricción que dispongas, de lo contrario puedes usar los eventos del control, de manera que escriban en ellos lo que tu requieras

@Gerson Pineda, supongo que te refieres a aplicar un evento Private Sub textbox_Change(), sobre cada uno de los cuadros de texto. Efectivamente al tratarse de una multipágina es necesario que el evento Change reconozca que cada página correspondiente este activa.

Es una buena idea, pero no sé cómo hacerlo...

 

publicado
Hace 4 horas, paikerr dijo:

Efectivamente al tratarse de una multipágina es necesario que el evento Change reconozca que cada página correspondiente este activa.

Es una buena idea, pero no sé cómo hacerlo...

En efecto, y es posible, trata de estudiar a fondo el MultiPage, a mi ese control me ha encantado, lo he utilizado en proyectos para clientes, es bastante cómodo y ventajoso, porque te ahorra esa cantidad de formularios individuales y luego tienes que esconderlos o volverlo a llamar... en fin 

 

Saludos

Archivado

Este tema está ahora archivado y está cerrado a más respuestas.