alberto-moyano   28-12-2024, 22:34
#1
Hola gente, espero hayan tenido buenas fiestas.

Siguiendo la sugerencia de Tincho estoy haciendo una actualización en mi aplicación, pasando las consultas al evento data, este es el código

Código:
Public Sub VListaBIB_Data(Row As Integer, Column As Integer)

  If ContenidoBibTotal = Null Then Return
  If Row < 0 Or Row >= ContenidoBibTotal.Count Then Return
  ContenidoBibTotal.MoveTo(Row)

  Select Case Column
    Case 0
      VListaBIB.Data.Text = ContenidoBibTotal["id"]
    Case 1
      VListaBIB.Data.Text = ContenidoBibTotal["author"]
    Case 2
      VListaBIB.Data.Text = ContenidoBibTotal["editor"]
    Case 3
      VListaBIB.Data.Text = ContenidoBibTotal["title"]
    Case 4
      VListaBIB.Data.Text = ContenidoBibTotal["journalTitle"]
    Case 5
      VListaBIB.Data.Text = ContenidoBibTotal["yearY"]
    Case 6
      VListaBIB.Data.Text = ContenidoBibTotal["dateD"]
    Case 7
      VListaBIB.Data.Text = ContenidoBibTotal["publisher"]
  End Select

End

el evento funciona sin problemas, ahora bien cuando hago click en cualquiera de las filas pretendo que se muestren en los textbox correspondientes los datos de la fila seleccionada, este es el código que escribi

Código:
Public Sub VListaBIB_RowClick(Row As Integer)

  ' configurar como se muestran los botones
  btnGuardarCambios.Visible = True
  BtnEliminarBib.Visible = True
  btnAgregarCitationKey.Visible = True
  btnGuardar.Visible = False
  btnAgregarKeyBIB.Visible = True
  BtnRefrescarBib.Visible = True

  ' Asegura de que hay una fila seleccionada
  If Row < 0 Or Row >= VListaBIB.Count Then Return

  ' Rellenar los campos de texto con los valores de la fila seleccionada
  txtIDbibtex.Text = VListaBIB[Row, 0].Text
  ComboBox1.Text = VListaBIB[Row, 1].Text
  txtCLAVEbib.Text = VListaBIB[Row, 2].Text
  txtKEYWORDS.Text = VListaBIB[Row, 3].Text
  txtAUTHOR.Text = VListaBIB[Row, 4].Text

... siguen campos

End
Ahora no obtengo error alguno, quiero decir, puedo seleccionar cualquier fila del grid, la aplicación no se cuelga pero no se reflejan en los textbox los datos de la fila seleccionada.

Y este es el código que diseña el grid en el evento open del formulario

Código:
  ' Ejecutar las consultas SQL
  ContenidoBibTotal = meConn.Exec("SELECT * FROM bibtex ORDER BY id DESC")
  VListaBIB.Rows.Count = ContenidoBibTotal.Count
 
  ' Configurar diseño del GridView
  With VListaBIB
    .Header = True
    .Grid = True
    .Columns.Count = 8 ' Ajusta según las columnas necesarias
    .Columns[0].Title = "Id"
    .Columns[0].Width = 0

    .Columns[1].Title = "Autor"
    .Columns[1].Width = 250

    .Columns[2].Title = "Editor"
    .Columns[2].Width = 250

    .Columns[3].Title = "Título"
    .Columns[3].Width = 600

    .Columns[4].Title = "Revista"
    .Columns[4].Width = 250

    .Columns[5].Title = "Año"
    .Columns[5].Width = 70

    .Columns[6].Title = "Fecha"
    .Columns[6].Width = 120

    .Columns[7].Title = "Editorial"
    .Columns[7].Width = 250
  End With

Estoy medio perdido, porque lei en algun lugar a Shordi decir que el evento data no trabaja con filas, alguno tiene idea de por donde vienen los tiros.

Saludos
Última modificación: 28-12-2024, 22:41 por alberto-moyano.
guizans   29-12-2024, 11:49
#2
Creo que el problema es el evento VListaBIB_RowClick. Supongo que estas usando un GridView por el evento _Data. Yo lo que hago sería algo así:
Código:
VListaBIB_Click()

Con esto se dispara el evento al hacer click en el GridView. A continuación muevo el puntero del resultado de la base datos a la fila que ha sido seleccionada con:
Código:
ContenidoBibTotal.Moveto(VListaBIB.Row)

y a partir de ahi rellenar todos los textbox.

Creo que es algo así.

Otra cosa. Yo el evento Data lo relleno de esta forma, me parece más limpia:

Código:
Public Sub VListaBIB_Data(Row As Integer, Column As Integer)
  
    Dim a as String[]=["id","author","editor","title","journalTitle","yearY","dateD","publisher"]
    ContenidoBibTotal.MoveTo(Row)
    VListaBIB.Data.Text = ContenidoBibTotal[a[Column]]
End
   
Cuando hago una consulta a la base de datos a continuación redimensiono el GridView con la cantidad de datos que he obtenido:
Código:
VListaBIB.Rows.Count = ContenidoBibTotal.Count
Y después refresco el GridView, y así me evito las dos líneas del principio que tienes en tu evento Data.

Un saludo.
Última modificación: 29-12-2024, 11:59 por guizans.
Harpo   09-01-2025, 15:42
#3
Saludos,

Seguramente el problema, al cargar los TextBox, esté en el código que se ejecuta entre la carga del GridView, al abrir el formulario, y el evento RowClick. Revisando el código no veo porqué no debería mostrar los datos siempre que el Result ContenidoBibTotal tenga datos, en algún momento debe pasar a ser nulo.

Por otro lado, y en mi humilde opinión, yo en el evento RowClick haría la carga de los TextBox directamente desde el Result ContenidoBibTotal, no desde la propiedad Text de la celda, por cómo funciona el control GridView.

GridView tiene una clase interna para manejar los datos de las celdas (_GridView_Data) y una clase para las celdas (_GridView_Cell). Y los valores de cada celda los almacena en un objeto Collection ($cCells), donde la clave es Fila-Columna y el valor un _GridView_Data. Cuando se usa el evento Data cargamos la propiedad Data del GridView, que es un _GridView_Data que el control después desecha, no almacena nada en $cCells.

Por tanto, en el evento Data el control no almacena los datos para futuros usos, y cuando se le pide el valor de la propiedad Text de una celda vuelve a llamar a ese evento para recuperarlos.

Por ejemplo, en el código que propone Guizans, donde crea e inicializa un String[] con los nombres de los campos, está creando e inicializando esa variable para cada celda. Y cuando recupera información de una celda, nueva llamada al evento. Personalmente utilizaría una variable de ámbito superior accesible desde el evento para evitar crear e inicializar una variable tantas veces.

Un saludo, Harpo.
alberto-moyano   10-01-2025, 19:50
#4
Gracias guizans y Harpo, ya solucioné el tema revisando el comentario de guizans, algo que encontré en la red del compañero Julio y otro tanto reviendo algunos videos de Shordi, llegue a esto que funciona bien (y muy rápido)

el evento open contiene esto
Código:
Mod_Funciones.ConfigurarGridView(VListaBIB)

el evento data, quedo así

Código:
Public Sub VListaBIB_Data(Row As Integer, Column As Integer)
  If (ContenidoBibTotal <> Null) Then
    If Row >= 0 Then
      ContenidoBibTotal.moveTo(Row)
      Try VListaBIB.Data.Text = Str(ContenidoBibTotal[Column])
    Endif
  Endif
  If row Mod 2 = 0 Then
    VListaBIB.Data.Background = Color.RGB(230, 230, 230)
  Endif
End


el evento click, quedo así

Código:
Public Sub VListaBIB_Click()' grid en el formulario principal
  ' configurar como se muestran los botones
  btnGuardarCambios.Visible = True
  BtnEliminarBib.Visible = True
  btnAgregarCitationKey.Visible = True
  btnGuardar.Visible = False
  btnAgregarKeyBIB.Visible = True
  TabPanel2.Index = 0

  Mod_Funciones.VerBibTeXenVListaBIB()
End


y la función que diseña el grid así
Código:
' en el módulo de funciones
Public Sub ConfigurarGridView(grid As GridView)

  With grid
    .Header = True
    .Grid = True
    .Columns.Count = 112

    ' Configuración de columnas
    For i As Integer = 0 To 111
      Select Case i
        Case 0
          .Columns[i].Title = "Id"
          .Columns[i].Width = 0
        Case 4
          .Columns[i].Title = "Autor/a/es"
          .Columns[i].Width = 250
        Case 6
          .Columns[i].Title = "Editor/a/es"
          .Columns[i].Width = 250
        Case 24
          .Columns[i].Title = "Título principal"
          .Columns[i].Width = 600
        Case 29
          .Columns[i].Title = "Revista"
          .Columns[i].Width = 200
        Case 43
          .Columns[i].Title = "Año"
          .Columns[i].Width = 70
        Case 44
          .Columns[i].Title = "Fecha"
          .Columns[i].Width = 120
        Case 53
          .Columns[i].Title = "Editorial"
          .Columns[i].Width = 200
        Case Else
          .Columns[i].Title = ""
          .Columns[i].Width = 0
      End Select
    Next
  End With

End


se muestran los datos en los campos con este código que está en un módulo
Código:
Public Sub VerBibTeXenVListaBIB()

  ' Rellenar los campos de texto con los valores de la fila seleccionada
  FMain.txtIDbibtex.Text = FMain.VListaBIB[FMain.VListaBIB.row, 0].Text
  FMain.ComboBox1.Text = FMain.VListaBIB[FMain.VListaBIB.row, 1].Text
  FMain.txtCLAVEbib.Text = FMain.VListaBIB[FMain.VListaBIB.row, 2].Text
  FMain.txtKEYWORDS.Text = FMain.VListaBIB[FMain.VListaBIB.row, 3].Text
  FMain.txtAUTHOR.Text = FMain.VListaBIB[FMain.VListaBIB.row, 4].Text
  FMain.txtBOOKAUTHOR.Text = FMain.VListaBIB[FMain.VListaBIB.row, 5].Text
  FMain.txtEDITOR.Text = FMain.VListaBIB[FMain.VListaBIB.row, 6].Text
... siguen campós
End

Harpo, voy a intentar entender lo que dices, es demasiado para mí, pero no le escapo al bulto.

Gracias y saludos
Última modificación: 10-01-2025, 19:54 por alberto-moyano.
Harpo   11-01-2025, 14:10
#5
Saludos,

Lo que intentaba explicar es que cuando se carga un GridView con el evento Data el control no guarda los datos de las celdas internamente en un Collection que tiene para eso ($cCells). 

Y cuando en nuestro código escribimos:
Código:
Textbox1.Text = GridView1[iRow, iCol].Text

Como GridView no tiene guardado ningún dato vuelve disparar el evento Data para recuperar el texto de la celda que le estamos pidiendo.

En su código cuando carga los TextBox lo que ocurre es:
- El GridView busca si existe la celda para la fila y columna solicitada. No lo encuentra internamente.
- GridView lanza el evento Data y carga la propiedad Text de la celda desde la base de datos.
- GridView le devuelve el valor Text de la celda y se carga en el TextBox.

En su caso cómo solo carga una fila, aunque sean 112 columnas, no tiene problemas. Si cargara 1.000 filas ejecutaría 112.000 veces el evento Data del GridView, y ahí sí tendría un problema de rendimiento. Por eso le comentaba que, en mi humilde opinión, es más práctico que la carga de los TextBox la hiciera desde el Result de la base de datos, elimina las llamadas al evento Data que es un mero intermediario entre los TextBox y la base de datos.

Un par de recomendaciones:

Código:
Mod_Funciones.VerBibTeXenVListaBIB(VListaBIB.row)  ''En el evento Click de la celda pasar como parámetro la fila

Public Sub VerBibTeXenVListaBIB(iRow as integer)  ''Recoger la fila como parámetro en la función del módulo, se ahorra recuperar 112 veces su valor desde el Gridview


Un último apunte, en el evento Data no es necesario controlar si la fila es mayor o igual a cero, tampoco la columna. GridView antes de lanzar el evento Data controla que la fila y la columna son correctas. 

Espero haberme explicado mejor, un saludo.
Harpo.
guizans   11-01-2025, 21:39
#6
Efectivamente Harpo, si solución es si el GridView tiene pocos datos a mostrar. Otra solución es hacer una consulta a la base de datos con los datos a mostrar en el GridView y otra consulta que es la que tiene todos los datos que se usarán para mostrar en los TextBox.

No se cual puede ser más eficiente en casos de muchas entradas, nunca se me ha dado el caso.

Un saludo.

Efectivamente Harpo, mi solución es si el GridView tiene pocos datos a mostrar. Otra solución es hacer una consulta a la base de datos con los datos a mostrar en el GridView y otra consulta que es la que tiene todos los datos que se usarán para mostrar en los TextBox.

No se cual puede ser más eficiente en casos de muchas entradas, nunca se me ha dado el caso.

Un saludo.
Última modificación: 11-01-2025, 21:40 por guizans.
  
Usuarios navegando en este tema: 2 invitado(s)
Powered By MyBB, © 2002-2025 MyBB Group.
Made with by Curves UI.