none
Cómo crear un formulario tipo factura RRS feed

  • Pregunta

  • Hola todos, Soy nuevo en el foro pero me gusta consultarlo constantemente, Soy nuevo programando con vb 2010.

    Mi necesidad es esta: debo crear un formulario tipo factura, es decir, con tablas padre-hijo de tal manera que tenga su encabezado pero en el detalle sea dinámico: Que en cada registro de una grid pueda validad el codigo (por ejemplo del producto), tener un combobox en una columna (para elegir tipo de producto), cantidad, % Dscto, subtotal,  etc. Además, que pueda corregir antes de grabar y cuando haya ingresado todos los registros entonces grabar en mi db, todos los cambios realizados en la grid.

    ¿Es posible eso? ¿cómo lo haría? . Estoy trabajando con MySQL en una aplicación Windows Forms. Les agradezco su valiosa ayuda....

    lunes, 13 de febrero de 2012 16:58

Respuestas

  • Solph, todo lo expuesto es en referencia a mi formulario para crear una cotización usando una datagridview con ingreso de datos directamente en las celdas. Obviamente debes usar las ideas que puedan servirte.

    Mi programación es con n capas, por lo que las lecturas de datos se encuentran fuera de la interfaz de usuario, y desde el codigo se llaman las funciones que hacen las consultas.  Te darás cuenta de eso cuando revises el código.

    La imagen del formulario es la siguiente:

    primero construimos la grilla en base a un tipo personalizado. La definición de la Grilla está en la siguiente clase:

    Public Class DgvPlus
    
        Inherits DataGridView   'Heredar del DataGridView
    
        'en el 'processDialogKey'... cuando estamos en edicion
    
        Protected Overrides Function ProcessDialogKey(ByVal keyData As System.Windows.Forms.Keys) As Boolean
    
    
            If keyData = Keys.Enter Then                'Si es 'enter'
    
                SendKeys.Send(Chr(Keys.Tab))            'Enviar un 'Tab'
    
                Return True                             'Marcar como procesado
    
            Else                                        'en caso contrario
    
                Return MyBase.ProcessDialogKey(keyData) 'devolver KeyData
    
            End If
    
        End Function
    
    End Class

    Luego construimos la grilla:

     Private WithEvents Listado As New DgvPlus 

    Este código va al principio de la clase formulario (Public ClassCotizacion_nueva)

    Hacemos la llamada a la rutina que construye la grilla y la inserta dentro de un control, en este caso dentro de un Panel:

     Private Sub ConstruirGrilla()
    
            Listado.ColumnCount = 10
    
            Listado.Columns(0).HeaderText = "Código"
            Listado.Columns(1).HeaderText = "Descripción"
            Listado.Columns(2).HeaderText = "P.Unitario"
            Listado.Columns(3).HeaderText = "Costo"
            Listado.Columns(4).HeaderText = "Cantidad"
            Listado.Columns(5).HeaderText = "Total"
    
            Listado.Columns(6).HeaderText = "V.Unidad"
            Listado.Columns(7).HeaderText = "V.Metro/hoja"
            Listado.Columns(8).HeaderText = "Stock Disponible"
            Listado.Columns(9).HeaderText = "Unidad"
    
            Listado.Columns(0).Width = 60
            Listado.Columns(1).Width = 300
            Listado.Columns(2).Width = 80
            Listado.Columns(3).Width = 80
            Listado.Columns(4).Width = 80
            Listado.Columns(5).Width = 80
            Listado.Columns(6).Width = 90
            Listado.Columns(7).Width = 90
            Listado.Columns(8).Width = 120
            Listado.Columns(9).Width = 100
    
    
            'codigo
            Listado.Columns(0).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Descripcion
            Listado.Columns(1).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Precio Unitario
            Listado.Columns(2).DefaultCellStyle.Format = "N0"
            Listado.Columns(2).DefaultCellStyle.NullValue = "0"
            Listado.Columns(2).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(2).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Costo
            Listado.Columns(3).DefaultCellStyle.Format = "N0"
            Listado.Columns(3).DefaultCellStyle.NullValue = "0"
            Listado.Columns(3).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(3).ReadOnly = True
            Listado.Columns(3).Visible = True
    
            'Cantidad
            Listado.Columns(4).DefaultCellStyle.NullValue = "0"
            Listado.Columns(4).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(4).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Total
            Listado.Columns(5).DefaultCellStyle.Format = "N0"
            Listado.Columns(5).DefaultCellStyle.NullValue = "0"
            Listado.Columns(5).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(5).ReadOnly = True
    
            'V.Unidad
            Listado.Columns(6).DefaultCellStyle.Format = "N0"
            Listado.Columns(6).DefaultCellStyle.NullValue = "0"
            Listado.Columns(6).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(6).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'V. Metro/hoja
            Listado.Columns(7).DefaultCellStyle.Format = "N0"
            Listado.Columns(7).DefaultCellStyle.NullValue = "0"
            Listado.Columns(7).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(7).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'stock
            Listado.Columns(8).DefaultCellStyle.NullValue = "0"
            Listado.Columns(8).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(8).ReadOnly = True
    
            'Unidad
            Listado.Columns(9).ReadOnly = True
    
            Listado.BackgroundColor = Color.LightSteelBlue
    
            Panel2.Controls.Add(Listado)
            Listado.Dock = DockStyle.Fill
            Listado.AlternatingRowsDefaultCellStyle.BackColor = Color.AliceBlue
    
        End Sub

    Bien, con eso esta construida la grilla, ahora el manejo de los datos en las celdas:

    'cuando el usuario ha ingresado un dato en una celda
        Private Sub Listado_CellEndEdit(ByVal sender As Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs)
            Dim Precio As Integer = 0
    
            If e.ColumnIndex = 0 Then 'codigo
                Dim Codigo As String = Listado.CurrentCell.Value.ToString
                Dim p As New Producto
                p = [Global].Business.Conexion.GetProducto(Codigo) ' se busca el producto filtrando por código de producto
                If p IsNot Nothing Then
    
                    If p.Activo = 1 Then
                        Dim Mensaje As String = "El Código de Producto existe pero está inactivo."
                        Mensaje += "(" & p.Descripcion & ")"
                        MessageBox.Show(Mensaje, "Validación", MessageBoxButtons.OK, MessageBoxIcon.Information)
    
                        Exit Sub
                    End If
    
                    'como el producto existe, muestra sus datos en las respectivas celdas
                    Listado.Rows(e.RowIndex).Cells(1).Value = p.Descripcion
                    Listado.Rows(e.RowIndex).Cells(3).Value = p.PrecioCosto
                    Listado.Rows(e.RowIndex).Cells(9).Value = p.Unidad.Unidad
    
                    'rutina que determina el precio al que se venderá el producto.
                    Dim UltimoPrecio As Integer = 0
                    If txtRut.Text.Trim = String.Empty Then
                        UltimoPrecio = 0
                    Else
                        UltimoPrecio = TraerUltimoPrecio(Codigo, txtRut.Text)
                    End If
    
                    If UltimoPrecio <> 0 Then
                        Precio = UltimoPrecio
                    Else
                        Precio = CalcularPRecio(p)
                    End If
    
                    'coloca el precio determinado en la celda correspondiente
                    Listado.Rows(e.RowIndex).Cells(2).Value = Precio
    
                    'Calcula cantidad * precio
                    Multiplicar(e.RowIndex)
    
    
                End If
    
                ' si la celda que se ha modificado es la que contiene el precio de venta
            ElseIf e.ColumnIndex = 2 Then 'precio
    
                If IsNumeric(Listado.CurrentCell.Value) = False Then
                    Listado.CurrentCell = Listado.CurrentRow.Cells(2)
                    Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                    Listado.CurrentCell.Value = 0
                    Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    Exit Sub
                Else
                    If Listado.CurrentCell.Value > 0 Then
                        Listado.CurrentCell.ErrorText = String.Empty
                        If IsNumeric(Listado.CurrentCell.Value) = False Then Exit Sub
                        Dim Cantidad As Double = Listado.CurrentCell.Value
                        Multiplicar(e.RowIndex)
                    Else
                        Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                        Listado.CurrentCell.Value = 0
                        Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    End If
                End If
    
                ' si la celda que se ha modificado es la que contien la cantidad
            ElseIf e.ColumnIndex = 4 Then 'cantidad
    
                If IsNumeric(Listado.CurrentCell.Value) = False Then
                    Listado.CurrentCell = Listado.CurrentRow.Cells(4)
                    Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                    Listado.CurrentCell.Value = 0
                    Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    Exit Sub
                Else
                    If Listado.CurrentCell.Value > 0 Then
                        Listado.CurrentCell.ErrorText = String.Empty
                        If IsNumeric(Listado.CurrentCell.Value) = False Then Exit Sub
                        Dim Cantidad As Double = Listado.CurrentCell.Value
                        Multiplicar(e.RowIndex)
                    Else
                        Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                        Listado.CurrentCell.Value = 0
                        Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    End If
                End If
    
                'valida que el stock disponible sea suficiente para efectuar la venta
                Dim stockDisponible As Integer = Listado.Rows(e.RowIndex).Cells(8).Value
                If stockDisponible < Listado.CurrentCell.Value Then
                    MessageBox.Show("No hay stock suficiente.", "Validación", MessageBoxButtons.OK, MessageBoxIcon.Warning)
                    Listado.Rows(e.RowIndex).DefaultCellStyle.ForeColor = Color.Red
                    Exit Sub
                Else
                    Listado.Rows(e.RowIndex).DefaultCellStyle.ForeColor = Color.Black
                End If
    
    
            End If
            Sumar()
        End Sub

    Las rutinas relacionadas y que son llamadas del codigo anterior son:

    'obtiene el último precio del producto.
    'la consulta se encuentra en otra capa del proyecto.
    
    Private Function TraerUltimoPrecio(ByVal codigo As String, ByVal rut As String) As Integer
            Try
    
                Return [Global].Business.Conexion.GetUltimoPrecio(codigo, rut)
    
            Catch ex As Exception
                MessageBox.Show("Error al buscar último precio: " & ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error)
                Return 0
            End Try
    
        End Function


    'Multiplica la cantidad por el precio unitario y pone el total en la celda correspondiente.
    
    Private Sub Multiplicar(ByVal fila As Integer)
            Listado.Rows(fila).Cells(5).Value = Listado.Rows(fila).Cells(4).Value * Listado.Rows(fila).Cells(2).Value
        End Sub



      'suma el monto total de cada linea y calcula los impuestos.
        Private Sub Sumar()
    
            'valida la cantidad de líenas que acepta el documento
            If Listado.Rows.Count - 1 <= Integer.Parse(lblLineas.Text) - 1 Then
                Dim suma As Integer = 0
                Dim iva As Integer = 0
                Dim total As Integer = 0
                Dim factor As Double = Double.Parse(lblIVA.Text) / 100
                Try
                    For i As Integer = 0 To Listado.Rows.Count - 2
    
                        suma += Listado.Rows(i).Cells(5).Value
    
                    Next
    
                    iva = suma * factor
                    total = suma + iva
    
                    txtSumaAfecto.Text = String.Format("{0:n0}", suma)
                    txtSumaIva.Text = String.Format("{0:n0}", iva)
                    txtSumaTotal.Text = String.Format("{0:n0}", total)
    
                Catch ex As Exception
    
                End Try
            Else
                MessageBox.Show("La Cotización no acepta más lineas.", "Validación", MessageBoxButtons.OK)
                Listado.AllowUserToAddRows = False
                Listado.Refresh()
                Exit Sub
            End If
    
    
        End Sub

    Bueno, eso es todo, como puedes ver todos los cálculos se hacen en CellEndEdit,  dependiendo de que celda es la que ha utilizado el usuario.

    respecto de tu consulta  ¿Qué es mejor? ¿usar enlace a datos o realizr todo en forma programática? ¿y Por qué? yo creo que depende de cada uno. Para unos será más facil con enlace a datos y para otros será más facil de la forma dificil (jejejej).  En mi caso, como ya soy viejito, he programado siempre a codigo pelado...

    Finalmente, quedo a tus ordenes para cualquier consulta y, si esto te ha sido útil, márcala como resupesta.

    Atentamente


    Manuel Luengo


    • Editado manuel.softmedia martes, 14 de febrero de 2012 21:05 complementar
    • Marcado como respuesta Solp martes, 14 de febrero de 2012 21:20
    martes, 14 de febrero de 2012 21:02

Todas las respuestas

  • Tal vez algo de esto te pueda orientar...

    http://social.msdn.microsoft.com/Forums/es-ES/vbes/thread/b0560a4c-6f59-4501-97d7-8941c0671b67

    Atentamente,


    Manuel Luengo

    lunes, 13 de febrero de 2012 21:20
  • Gracias Manuel por tu colaboración.

    No obstante, lo que quisiera es no utilizar unos texbox's que sirvan de captura y un datagridview que me los muestre, sino en la misma grilla poder realizar las modificaciones. En este momento se me ocurre algo, ustedes me dicen si es factible:

    cuando uno crea el datagridview tiene la opción de permitir actualizar o eliminar o adionar. utilizando estas propiedades, ¿se podría hacer lo que pienso? voy a probar. Si se puede por favor, les agradezco su colaboración.

    Atentemente, 

    Solph.

    martes, 14 de febrero de 2012 16:00
  • En el caso de que la grilla este enlazada a datos, es posible hacer lo que indicas.

    Yo, en lo personal no uso enlace a datos y realizo todas las operaciones en forma programática.
    Si quieres puedo dejarte algunos código de ejemplo para trabajar directamente sobre las celdas de la grilla, pero siempre programáticamente.

    Atentamente,


    Manuel Luengo

    martes, 14 de febrero de 2012 19:31
  • Gracias Manuel,

    Sí me interesa analizar los códigos que usas para no usar enlace a datos.

    Te pregunto una cosa: ¿Qué es mejor? ¿usar enlace a datos o realizr todo en forma programática? ¿y Por qué? ¿tiene inconvenientes usar enlace a datos? Hasta ahora en los formularios de captura básica, ej: productos, terceros, etc. lo he hecho en enlace a datos.

    Te agradezco tu ayuda.

    Atentamente,

    Solph.

    martes, 14 de febrero de 2012 20:24
  • Solph, todo lo expuesto es en referencia a mi formulario para crear una cotización usando una datagridview con ingreso de datos directamente en las celdas. Obviamente debes usar las ideas que puedan servirte.

    Mi programación es con n capas, por lo que las lecturas de datos se encuentran fuera de la interfaz de usuario, y desde el codigo se llaman las funciones que hacen las consultas.  Te darás cuenta de eso cuando revises el código.

    La imagen del formulario es la siguiente:

    primero construimos la grilla en base a un tipo personalizado. La definición de la Grilla está en la siguiente clase:

    Public Class DgvPlus
    
        Inherits DataGridView   'Heredar del DataGridView
    
        'en el 'processDialogKey'... cuando estamos en edicion
    
        Protected Overrides Function ProcessDialogKey(ByVal keyData As System.Windows.Forms.Keys) As Boolean
    
    
            If keyData = Keys.Enter Then                'Si es 'enter'
    
                SendKeys.Send(Chr(Keys.Tab))            'Enviar un 'Tab'
    
                Return True                             'Marcar como procesado
    
            Else                                        'en caso contrario
    
                Return MyBase.ProcessDialogKey(keyData) 'devolver KeyData
    
            End If
    
        End Function
    
    End Class

    Luego construimos la grilla:

     Private WithEvents Listado As New DgvPlus 

    Este código va al principio de la clase formulario (Public ClassCotizacion_nueva)

    Hacemos la llamada a la rutina que construye la grilla y la inserta dentro de un control, en este caso dentro de un Panel:

     Private Sub ConstruirGrilla()
    
            Listado.ColumnCount = 10
    
            Listado.Columns(0).HeaderText = "Código"
            Listado.Columns(1).HeaderText = "Descripción"
            Listado.Columns(2).HeaderText = "P.Unitario"
            Listado.Columns(3).HeaderText = "Costo"
            Listado.Columns(4).HeaderText = "Cantidad"
            Listado.Columns(5).HeaderText = "Total"
    
            Listado.Columns(6).HeaderText = "V.Unidad"
            Listado.Columns(7).HeaderText = "V.Metro/hoja"
            Listado.Columns(8).HeaderText = "Stock Disponible"
            Listado.Columns(9).HeaderText = "Unidad"
    
            Listado.Columns(0).Width = 60
            Listado.Columns(1).Width = 300
            Listado.Columns(2).Width = 80
            Listado.Columns(3).Width = 80
            Listado.Columns(4).Width = 80
            Listado.Columns(5).Width = 80
            Listado.Columns(6).Width = 90
            Listado.Columns(7).Width = 90
            Listado.Columns(8).Width = 120
            Listado.Columns(9).Width = 100
    
    
            'codigo
            Listado.Columns(0).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Descripcion
            Listado.Columns(1).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Precio Unitario
            Listado.Columns(2).DefaultCellStyle.Format = "N0"
            Listado.Columns(2).DefaultCellStyle.NullValue = "0"
            Listado.Columns(2).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(2).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Costo
            Listado.Columns(3).DefaultCellStyle.Format = "N0"
            Listado.Columns(3).DefaultCellStyle.NullValue = "0"
            Listado.Columns(3).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(3).ReadOnly = True
            Listado.Columns(3).Visible = True
    
            'Cantidad
            Listado.Columns(4).DefaultCellStyle.NullValue = "0"
            Listado.Columns(4).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(4).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Total
            Listado.Columns(5).DefaultCellStyle.Format = "N0"
            Listado.Columns(5).DefaultCellStyle.NullValue = "0"
            Listado.Columns(5).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(5).ReadOnly = True
    
            'V.Unidad
            Listado.Columns(6).DefaultCellStyle.Format = "N0"
            Listado.Columns(6).DefaultCellStyle.NullValue = "0"
            Listado.Columns(6).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(6).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'V. Metro/hoja
            Listado.Columns(7).DefaultCellStyle.Format = "N0"
            Listado.Columns(7).DefaultCellStyle.NullValue = "0"
            Listado.Columns(7).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(7).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'stock
            Listado.Columns(8).DefaultCellStyle.NullValue = "0"
            Listado.Columns(8).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(8).ReadOnly = True
    
            'Unidad
            Listado.Columns(9).ReadOnly = True
    
            Listado.BackgroundColor = Color.LightSteelBlue
    
            Panel2.Controls.Add(Listado)
            Listado.Dock = DockStyle.Fill
            Listado.AlternatingRowsDefaultCellStyle.BackColor = Color.AliceBlue
    
        End Sub

    Bien, con eso esta construida la grilla, ahora el manejo de los datos en las celdas:

    'cuando el usuario ha ingresado un dato en una celda
        Private Sub Listado_CellEndEdit(ByVal sender As Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs)
            Dim Precio As Integer = 0
    
            If e.ColumnIndex = 0 Then 'codigo
                Dim Codigo As String = Listado.CurrentCell.Value.ToString
                Dim p As New Producto
                p = [Global].Business.Conexion.GetProducto(Codigo) ' se busca el producto filtrando por código de producto
                If p IsNot Nothing Then
    
                    If p.Activo = 1 Then
                        Dim Mensaje As String = "El Código de Producto existe pero está inactivo."
                        Mensaje += "(" & p.Descripcion & ")"
                        MessageBox.Show(Mensaje, "Validación", MessageBoxButtons.OK, MessageBoxIcon.Information)
    
                        Exit Sub
                    End If
    
                    'como el producto existe, muestra sus datos en las respectivas celdas
                    Listado.Rows(e.RowIndex).Cells(1).Value = p.Descripcion
                    Listado.Rows(e.RowIndex).Cells(3).Value = p.PrecioCosto
                    Listado.Rows(e.RowIndex).Cells(9).Value = p.Unidad.Unidad
    
                    'rutina que determina el precio al que se venderá el producto.
                    Dim UltimoPrecio As Integer = 0
                    If txtRut.Text.Trim = String.Empty Then
                        UltimoPrecio = 0
                    Else
                        UltimoPrecio = TraerUltimoPrecio(Codigo, txtRut.Text)
                    End If
    
                    If UltimoPrecio <> 0 Then
                        Precio = UltimoPrecio
                    Else
                        Precio = CalcularPRecio(p)
                    End If
    
                    'coloca el precio determinado en la celda correspondiente
                    Listado.Rows(e.RowIndex).Cells(2).Value = Precio
    
                    'Calcula cantidad * precio
                    Multiplicar(e.RowIndex)
    
    
                End If
    
                ' si la celda que se ha modificado es la que contiene el precio de venta
            ElseIf e.ColumnIndex = 2 Then 'precio
    
                If IsNumeric(Listado.CurrentCell.Value) = False Then
                    Listado.CurrentCell = Listado.CurrentRow.Cells(2)
                    Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                    Listado.CurrentCell.Value = 0
                    Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    Exit Sub
                Else
                    If Listado.CurrentCell.Value > 0 Then
                        Listado.CurrentCell.ErrorText = String.Empty
                        If IsNumeric(Listado.CurrentCell.Value) = False Then Exit Sub
                        Dim Cantidad As Double = Listado.CurrentCell.Value
                        Multiplicar(e.RowIndex)
                    Else
                        Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                        Listado.CurrentCell.Value = 0
                        Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    End If
                End If
    
                ' si la celda que se ha modificado es la que contien la cantidad
            ElseIf e.ColumnIndex = 4 Then 'cantidad
    
                If IsNumeric(Listado.CurrentCell.Value) = False Then
                    Listado.CurrentCell = Listado.CurrentRow.Cells(4)
                    Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                    Listado.CurrentCell.Value = 0
                    Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    Exit Sub
                Else
                    If Listado.CurrentCell.Value > 0 Then
                        Listado.CurrentCell.ErrorText = String.Empty
                        If IsNumeric(Listado.CurrentCell.Value) = False Then Exit Sub
                        Dim Cantidad As Double = Listado.CurrentCell.Value
                        Multiplicar(e.RowIndex)
                    Else
                        Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                        Listado.CurrentCell.Value = 0
                        Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    End If
                End If
    
                'valida que el stock disponible sea suficiente para efectuar la venta
                Dim stockDisponible As Integer = Listado.Rows(e.RowIndex).Cells(8).Value
                If stockDisponible < Listado.CurrentCell.Value Then
                    MessageBox.Show("No hay stock suficiente.", "Validación", MessageBoxButtons.OK, MessageBoxIcon.Warning)
                    Listado.Rows(e.RowIndex).DefaultCellStyle.ForeColor = Color.Red
                    Exit Sub
                Else
                    Listado.Rows(e.RowIndex).DefaultCellStyle.ForeColor = Color.Black
                End If
    
    
            End If
            Sumar()
        End Sub

    Las rutinas relacionadas y que son llamadas del codigo anterior son:

    'obtiene el último precio del producto.
    'la consulta se encuentra en otra capa del proyecto.
    
    Private Function TraerUltimoPrecio(ByVal codigo As String, ByVal rut As String) As Integer
            Try
    
                Return [Global].Business.Conexion.GetUltimoPrecio(codigo, rut)
    
            Catch ex As Exception
                MessageBox.Show("Error al buscar último precio: " & ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error)
                Return 0
            End Try
    
        End Function


    'Multiplica la cantidad por el precio unitario y pone el total en la celda correspondiente.
    
    Private Sub Multiplicar(ByVal fila As Integer)
            Listado.Rows(fila).Cells(5).Value = Listado.Rows(fila).Cells(4).Value * Listado.Rows(fila).Cells(2).Value
        End Sub



      'suma el monto total de cada linea y calcula los impuestos.
        Private Sub Sumar()
    
            'valida la cantidad de líenas que acepta el documento
            If Listado.Rows.Count - 1 <= Integer.Parse(lblLineas.Text) - 1 Then
                Dim suma As Integer = 0
                Dim iva As Integer = 0
                Dim total As Integer = 0
                Dim factor As Double = Double.Parse(lblIVA.Text) / 100
                Try
                    For i As Integer = 0 To Listado.Rows.Count - 2
    
                        suma += Listado.Rows(i).Cells(5).Value
    
                    Next
    
                    iva = suma * factor
                    total = suma + iva
    
                    txtSumaAfecto.Text = String.Format("{0:n0}", suma)
                    txtSumaIva.Text = String.Format("{0:n0}", iva)
                    txtSumaTotal.Text = String.Format("{0:n0}", total)
    
                Catch ex As Exception
    
                End Try
            Else
                MessageBox.Show("La Cotización no acepta más lineas.", "Validación", MessageBoxButtons.OK)
                Listado.AllowUserToAddRows = False
                Listado.Refresh()
                Exit Sub
            End If
    
    
        End Sub

    Bueno, eso es todo, como puedes ver todos los cálculos se hacen en CellEndEdit,  dependiendo de que celda es la que ha utilizado el usuario.

    respecto de tu consulta  ¿Qué es mejor? ¿usar enlace a datos o realizr todo en forma programática? ¿y Por qué? yo creo que depende de cada uno. Para unos será más facil con enlace a datos y para otros será más facil de la forma dificil (jejejej).  En mi caso, como ya soy viejito, he programado siempre a codigo pelado...

    Finalmente, quedo a tus ordenes para cualquier consulta y, si esto te ha sido útil, márcala como resupesta.

    Atentamente


    Manuel Luengo


    • Editado manuel.softmedia martes, 14 de febrero de 2012 21:05 complementar
    • Marcado como respuesta Solp martes, 14 de febrero de 2012 21:20
    martes, 14 de febrero de 2012 21:02
  • Manuel, 

    he analizado rápidamente el código que me envió y creo que esto es lo que necesitaba

    voy adaptarlo a lo que quiero. Muchas gracias de antemano.

    Si necesito otra ayudita... apreciaría me tenga paciencia.

    Atentamente, 

    Solph.

    martes, 14 de febrero de 2012 21:23
  • Por supuesto, no dudes en consultar cualquier cosa que requieras, simpre que mis conocimientos alcancen.

    Saludos,


    Manuel Luengo

    martes, 14 de febrero de 2012 22:28
  • Manuel

    no hubiera sido mas practico subir el ejemplo de codigo en un zip a skydrive para que lo descargara

    en lugar de poner todo el codigo en el foro, digo creo que hubiera ayudado mas y no quedaria tan extenso


    Leandro Tuttini

    Blog
    Buenos Aires
    Argentina

    martes, 14 de febrero de 2012 23:23
  • Buena sugerencia, lo tendré presente para el futuro

    Gracias Leandro


    Manuel Luengo

    martes, 14 de febrero de 2012 23:36
  • Hola Buenos días Manuel,

    He estado adaptando el código. Tengo algunas dificultades... quizás por cuanto todavía no manejo lo de n-Capas.

    Es posible que usted me envíe el código empaquetado para mirar cómo están dispuestas las rutinas y analizar mejor?

    por ejemplo no entiendo el CellEndEdit, muy bien... Si es posible. Le agradezco.

    Atentamente,

    Solph.

    miércoles, 15 de febrero de 2012 16:18
  • Bien, prepararé un archivo y lo pondré a tu disposición.

    Te aviso por este medio cuando lo tenga listo.

    Saludos


    Manuel Luengo

    miércoles, 15 de febrero de 2012 16:42
  • Gracias... Disculpe la molestia...

    Aprecio mucho su disposición...

    Solph.

    miércoles, 15 de febrero de 2012 16:47
  • Solph,

    por favor dame un correo donde pueda enviarte el material.

    Atentamente,


    Manuel Luengo

    jueves, 16 de febrero de 2012 19:49
  • Manuel, cuánto le agradezco

    mi correo es: solphy@hotmail.com

    gracias,

    Solph.

    jueves, 16 de febrero de 2012 21:24
  • Te envié el correo.

    Suerte.


    Manuel Luengo

    jueves, 16 de febrero de 2012 21:50
  • Hola Solp,

    Ya he observado que Manuel te ha dado casi el trabajo hecho. Pero me gustaria añadir otra opción mucha más orientada a objetos y creo que de más fácil mantenimiento en un futuro.

    Podrias realizar lo mismo utilizando objetos enlazados al dataSource de un objeto BindingSource y luego ese objeto BindingSource asignarlo a la propiedad dataSource del DatagridView de la siguiente forma:

    this.MaestroBindingSource.DataSource = objectList;
    this.DetalleBindingSource.DataSource = MaestroBindingSource;
    this.DetalleBindingSource.DataMember = "Atributo del objectList";
    
    this.dataGridView1.DataSource = DetalleBindingSource;

    Creo que queda más limpio.

    Saludos.


    Albert Gassó
    Ingeniero Técnico en Informática
    Computer Software Engineer

    domingo, 19 de febrero de 2012 22:48
  • Gracias Albert por tu aportación, lo tendré en cuenta.

    No obstante, lo que necesito es poder editar la grilla, realizar los cambios (insertar, modificar,etc.) y finalmente guardar los cambios y además,

    Que en cada registro de una grid pueda validad el codigo (por ejemplo del producto), tener un combobox en una columna (para elegir tipo de producto), cantidad, % Dscto, subtotal,  etc. 

    Si tienes otra forma, te agradezco me lo envíes para comparar y realizar uno bastante acorde con lo que necesito.

    Muchas gracias,

    Solph.

    lunes, 20 de febrero de 2012 11:49
  • Hola Solp,

    Ya he observado que Manuel te ha dado casi el trabajo hecho. Pero me gustaria añadir otra opción mucha más orientada a objetos y creo que de más fácil mantenimiento en un futuro.

    Podrias realizar lo mismo utilizando objetos enlazados al dataSource de un objeto BindingSource y luego ese objeto BindingSource asignarlo a la propiedad dataSource del DatagridView de la siguiente forma:

    this.MaestroBindingSource.DataSource = objectList;
    this.DetalleBindingSource.DataSource = MaestroBindingSource;
    this.DetalleBindingSource.DataMember = "Atributo del objectList";
    
    this.dataGridView1.DataSource = DetalleBindingSource;

    Creo que queda más limpio.

    Saludos.


    Albert Gassó
    Ingeniero Técnico en Informática
    Computer Software Engineer

    Los objetos enlazados a datos facilitan mucho el trabajo es cierto, pero yo, que ya soy viejito en el tema, prefiero trabajar línea a línea. Siento que tengo dominio completo sobre el código y que el programa hace lo que quiero que haga.

    Obviamente cada uno verá como le acomoda más.


    Manuel Luengo

    lunes, 20 de febrero de 2012 12:04
  • Hola Albert,

    cuando dices que utilice: 

    this.MaestroBindingSource.DataSource = objectList;

    el "objectList"a qué te refieres?

    el "Atributo del objectList" en 

    this.DetalleBindingSource.DataMember = "Atributo del objectList";

    ¿qué es? es que soy nuevo programando en vb.net 2010

    En el formulario donde utilizo principalmente 1 tabla maestro y el datagridview contiene el detalle

    como se haría?

    podrías ponerme un ejemplo? las tablas que tengo son:

    en el maestro "Egresos" y el detalle es "det_egresos" la DatagridView es "dgvEgresos"

    Te agradezco la aclaración y la colaboración

    Solph.


    • Editado Solp lunes, 20 de febrero de 2012 23:02
    lunes, 20 de febrero de 2012 22:56
  • Hola Manuel,

    Trabajar con objetos no significa que pierdas dominio sobre el código, sinó todo lo contrario, y además de manera más estructurada, flexible y mantenible. Pero logicamente cada uno se encuentra más a gusto con un paradigma en concreto.

    Saludos


    Albert Gassó
    Ingeniero Técnico en Informática
    Computer Software Engineer

    martes, 21 de febrero de 2012 10:07
  • Hola Solp,

    Cuando pongo objectList me refiero a un objeto de tipo lista, te pongo un ejemplo muy sencillo, perfecto para el caso que estamos comentando:

    public class Object : IEditableObject
    {
    private int id;
    private List<objectdetail> liniasDetalle;
    }
    
    public class ObjectList : BindingList<object>
    {
    }
    
    public class ObjectDetail : IEditableObject
    {
    private int idLinia;
    }
    
    public class ObjectDetailList : BindingList<objectdetail>
    {
    }
    
    public partial class Form1 : Form
    {
    Maestrobindingsource.DataSource = ObjectList;
    Detallebindingsource.DataSource = Maestrobindingsource;
    Detallebindingsource.DataMember = liniasDetalle;
    dataGridView1.DataSource = Detallebindingsource;
    }</objectdetail></object></objectdetail>

    Espero te sirva.

    Nota: El código está en C# pero te será fácil traducirlo a VB

    Saludos


    Albert Gassó
    Ingeniero Técnico en Informática
    Computer Software Engineer


    • Editado Albert Gassó martes, 21 de febrero de 2012 11:46 Añadir Nota
    martes, 21 de febrero de 2012 10:16
  • Gracias Albert

    Solph.

    martes, 21 de febrero de 2012 20:04
  • hola man oe me puedes pasar el archivo comprimido en winzip.......porfavor......enviamelo a mi correo joseph_loveyou@hotmail.com


    Solph, todo lo expuesto es en referencia a mi formulario para crear una cotización usando una datagridview con ingreso de datos directamente en las celdas. Obviamente debes usar las ideas que puedan servirte.

    Mi programación es con n capas, por lo que las lecturas de datos se encuentran fuera de la interfaz de usuario, y desde el codigo se llaman las funciones que hacen las consultas.  Te darás cuenta de eso cuando revises el código.

    La imagen del formulario es la siguiente:

    primero construimos la grilla en base a un tipo personalizado. La definición de la Grilla está en la siguiente clase:

    Public Class DgvPlus
    
        Inherits DataGridView   'Heredar del DataGridView
    
        'en el 'processDialogKey'... cuando estamos en edicion
    
        Protected Overrides Function ProcessDialogKey(ByVal keyData As System.Windows.Forms.Keys) As Boolean
    
    
            If keyData = Keys.Enter Then                'Si es 'enter'
    
                SendKeys.Send(Chr(Keys.Tab))            'Enviar un 'Tab'
    
                Return True                             'Marcar como procesado
    
            Else                                        'en caso contrario
    
                Return MyBase.ProcessDialogKey(keyData) 'devolver KeyData
    
            End If
    
        End Function
    
    End Class

    Luego construimos la grilla:

     Private WithEvents Listado As New DgvPlus 

    Este código va al principio de la clase formulario (Public ClassCotizacion_nueva)

    Hacemos la llamada a la rutina que construye la grilla y la inserta dentro de un control, en este caso dentro de un Panel:

     Private Sub ConstruirGrilla()
    
            Listado.ColumnCount = 10
    
            Listado.Columns(0).HeaderText = "Código"
            Listado.Columns(1).HeaderText = "Descripción"
            Listado.Columns(2).HeaderText = "P.Unitario"
            Listado.Columns(3).HeaderText = "Costo"
            Listado.Columns(4).HeaderText = "Cantidad"
            Listado.Columns(5).HeaderText = "Total"
    
            Listado.Columns(6).HeaderText = "V.Unidad"
            Listado.Columns(7).HeaderText = "V.Metro/hoja"
            Listado.Columns(8).HeaderText = "Stock Disponible"
            Listado.Columns(9).HeaderText = "Unidad"
    
            Listado.Columns(0).Width = 60
            Listado.Columns(1).Width = 300
            Listado.Columns(2).Width = 80
            Listado.Columns(3).Width = 80
            Listado.Columns(4).Width = 80
            Listado.Columns(5).Width = 80
            Listado.Columns(6).Width = 90
            Listado.Columns(7).Width = 90
            Listado.Columns(8).Width = 120
            Listado.Columns(9).Width = 100
    
    
            'codigo
            Listado.Columns(0).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Descripcion
            Listado.Columns(1).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Precio Unitario
            Listado.Columns(2).DefaultCellStyle.Format = "N0"
            Listado.Columns(2).DefaultCellStyle.NullValue = "0"
            Listado.Columns(2).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(2).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Costo
            Listado.Columns(3).DefaultCellStyle.Format = "N0"
            Listado.Columns(3).DefaultCellStyle.NullValue = "0"
            Listado.Columns(3).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(3).ReadOnly = True
            Listado.Columns(3).Visible = True
    
            'Cantidad
            Listado.Columns(4).DefaultCellStyle.NullValue = "0"
            Listado.Columns(4).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(4).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'Total
            Listado.Columns(5).DefaultCellStyle.Format = "N0"
            Listado.Columns(5).DefaultCellStyle.NullValue = "0"
            Listado.Columns(5).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(5).ReadOnly = True
    
            'V.Unidad
            Listado.Columns(6).DefaultCellStyle.Format = "N0"
            Listado.Columns(6).DefaultCellStyle.NullValue = "0"
            Listado.Columns(6).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(6).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'V. Metro/hoja
            Listado.Columns(7).DefaultCellStyle.Format = "N0"
            Listado.Columns(7).DefaultCellStyle.NullValue = "0"
            Listado.Columns(7).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(7).DefaultCellStyle.BackColor = Color.LemonChiffon
    
            'stock
            Listado.Columns(8).DefaultCellStyle.NullValue = "0"
            Listado.Columns(8).DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
            Listado.Columns(8).ReadOnly = True
    
            'Unidad
            Listado.Columns(9).ReadOnly = True
    
            Listado.BackgroundColor = Color.LightSteelBlue
    
            Panel2.Controls.Add(Listado)
            Listado.Dock = DockStyle.Fill
            Listado.AlternatingRowsDefaultCellStyle.BackColor = Color.AliceBlue
    
        End Sub

    Bien, con eso esta construida la grilla, ahora el manejo de los datos en las celdas:

    'cuando el usuario ha ingresado un dato en una celda
        Private Sub Listado_CellEndEdit(ByVal sender As Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs)
            Dim Precio As Integer = 0
    
            If e.ColumnIndex = 0 Then 'codigo
                Dim Codigo As String = Listado.CurrentCell.Value.ToString
                Dim p As New Producto
                p = [Global].Business.Conexion.GetProducto(Codigo) ' se busca el producto filtrando por código de producto
                If p IsNot Nothing Then
    
                    If p.Activo = 1 Then
                        Dim Mensaje As String = "El Código de Producto existe pero está inactivo."
                        Mensaje += "(" & p.Descripcion & ")"
                        MessageBox.Show(Mensaje, "Validación", MessageBoxButtons.OK, MessageBoxIcon.Information)
    
                        Exit Sub
                    End If
    
                    'como el producto existe, muestra sus datos en las respectivas celdas
                    Listado.Rows(e.RowIndex).Cells(1).Value = p.Descripcion
                    Listado.Rows(e.RowIndex).Cells(3).Value = p.PrecioCosto
                    Listado.Rows(e.RowIndex).Cells(9).Value = p.Unidad.Unidad
    
                    'rutina que determina el precio al que se venderá el producto.
                    Dim UltimoPrecio As Integer = 0
                    If txtRut.Text.Trim = String.Empty Then
                        UltimoPrecio = 0
                    Else
                        UltimoPrecio = TraerUltimoPrecio(Codigo, txtRut.Text)
                    End If
    
                    If UltimoPrecio <> 0 Then
                        Precio = UltimoPrecio
                    Else
                        Precio = CalcularPRecio(p)
                    End If
    
                    'coloca el precio determinado en la celda correspondiente
                    Listado.Rows(e.RowIndex).Cells(2).Value = Precio
    
                    'Calcula cantidad * precio
                    Multiplicar(e.RowIndex)
    
    
                End If
    
                ' si la celda que se ha modificado es la que contiene el precio de venta
            ElseIf e.ColumnIndex = 2 Then 'precio
    
                If IsNumeric(Listado.CurrentCell.Value) = False Then
                    Listado.CurrentCell = Listado.CurrentRow.Cells(2)
                    Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                    Listado.CurrentCell.Value = 0
                    Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    Exit Sub
                Else
                    If Listado.CurrentCell.Value > 0 Then
                        Listado.CurrentCell.ErrorText = String.Empty
                        If IsNumeric(Listado.CurrentCell.Value) = False Then Exit Sub
                        Dim Cantidad As Double = Listado.CurrentCell.Value
                        Multiplicar(e.RowIndex)
                    Else
                        Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                        Listado.CurrentCell.Value = 0
                        Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    End If
                End If
    
                ' si la celda que se ha modificado es la que contien la cantidad
            ElseIf e.ColumnIndex = 4 Then 'cantidad
    
                If IsNumeric(Listado.CurrentCell.Value) = False Then
                    Listado.CurrentCell = Listado.CurrentRow.Cells(4)
                    Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                    Listado.CurrentCell.Value = 0
                    Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    Exit Sub
                Else
                    If Listado.CurrentCell.Value > 0 Then
                        Listado.CurrentCell.ErrorText = String.Empty
                        If IsNumeric(Listado.CurrentCell.Value) = False Then Exit Sub
                        Dim Cantidad As Double = Listado.CurrentCell.Value
                        Multiplicar(e.RowIndex)
                    Else
                        Listado.CurrentCell.ErrorText = "Solo números positivos mayores que cero."
                        Listado.CurrentCell.Value = 0
                        Listado.Rows(e.RowIndex).Cells(5).Value = 0
                    End If
                End If
    
                'valida que el stock disponible sea suficiente para efectuar la venta
                Dim stockDisponible As Integer = Listado.Rows(e.RowIndex).Cells(8).Value
                If stockDisponible < Listado.CurrentCell.Value Then
                    MessageBox.Show("No hay stock suficiente.", "Validación", MessageBoxButtons.OK, MessageBoxIcon.Warning)
                    Listado.Rows(e.RowIndex).DefaultCellStyle.ForeColor = Color.Red
                    Exit Sub
                Else
                    Listado.Rows(e.RowIndex).DefaultCellStyle.ForeColor = Color.Black
                End If
    
    
            End If
            Sumar()
        End Sub

    Las rutinas relacionadas y que son llamadas del codigo anterior son:

    'obtiene el último precio del producto.
    'la consulta se encuentra en otra capa del proyecto.
    
    Private Function TraerUltimoPrecio(ByVal codigo As String, ByVal rut As String) As Integer
            Try
    
                Return [Global].Business.Conexion.GetUltimoPrecio(codigo, rut)
    
            Catch ex As Exception
                MessageBox.Show("Error al buscar último precio: " & ex.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Error)
                Return 0
            End Try
    
        End Function


    'Multiplica la cantidad por el precio unitario y pone el total en la celda correspondiente.
    
    Private Sub Multiplicar(ByVal fila As Integer)
            Listado.Rows(fila).Cells(5).Value = Listado.Rows(fila).Cells(4).Value * Listado.Rows(fila).Cells(2).Value
        End Sub



      'suma el monto total de cada linea y calcula los impuestos.
        Private Sub Sumar()
    
            'valida la cantidad de líenas que acepta el documento
            If Listado.Rows.Count - 1 <= Integer.Parse(lblLineas.Text) - 1 Then
                Dim suma As Integer = 0
                Dim iva As Integer = 0
                Dim total As Integer = 0
                Dim factor As Double = Double.Parse(lblIVA.Text) / 100
                Try
                    For i As Integer = 0 To Listado.Rows.Count - 2
    
                        suma += Listado.Rows(i).Cells(5).Value
    
                    Next
    
                    iva = suma * factor
                    total = suma + iva
    
                    txtSumaAfecto.Text = String.Format("{0:n0}", suma)
                    txtSumaIva.Text = String.Format("{0:n0}", iva)
                    txtSumaTotal.Text = String.Format("{0:n0}", total)
    
                Catch ex As Exception
    
                End Try
            Else
                MessageBox.Show("La Cotización no acepta más lineas.", "Validación", MessageBoxButtons.OK)
                Listado.AllowUserToAddRows = False
                Listado.Refresh()
                Exit Sub
            End If
    
    
        End Sub

    Bueno, eso es todo, como puedes ver todos los cálculos se hacen en CellEndEdit,  dependiendo de que celda es la que ha utilizado el usuario.

    respecto de tu consulta  ¿Qué es mejor? ¿usar enlace a datos o realizr todo en forma programática? ¿y Por qué? yo creo que depende de cada uno. Para unos será más facil con enlace a datos y para otros será más facil de la forma dificil (jejejej).  En mi caso, como ya soy viejito, he programado siempre a codigo pelado...

    Finalmente, quedo a tus ordenes para cualquier consulta y, si esto te ha sido útil, márcala como resupesta.

    Atentamente


    Manuel Luengo



    sábado, 25 de febrero de 2012 23:01
  • Bien, prepararé la porcion de codigo y te lo enviaré al correo señalado. Debes tener en cuenta que lo expuesto es parte de un proyecto mucho más grande, por que habrán referencias que no tendrás disponible.

    ¿cual es tu nombre?

    Atentamente,


    Manuel Luengo

    sábado, 25 de febrero de 2012 23:24
  • Bien, prepararé la porcion de codigo y te lo enviaré al correo señalado. Debes tener en cuenta que lo expuesto es parte de un proyecto mucho más grande, por que habrán referencias que no tendrás disponible.

    ¿cual es tu nombre?

    Atentamente,


    Manuel Luengo

    Hola Manuel, primero gracias mil por todo tu apoyo desinteresado, no cualquier persona entrega lo que sabe con la sola idea de enseñar como tu lo haces constantemente (he visto mas de un Post tuyo). Yo no puedo ofrecerte Paellas, podría ofrecerte mi agradecimiento sincero y el poco conocimiento que tenga. También soy "Viejito", hace un tiempo decidí darle un giro a mi vida profesional, salir de la empresa para la que trabajé buena parte de mi vida profesional y empezar una nueva empresa. Estoy desarrollando en VB.net 2008-2010, realmente aprendiendo ya que soy de la época de COBOL / UNIX. Estoy viendo tu POst acerca de la generación de Facturas / pedidos etc. usando datagridview y aunque este post es de fecha 2012 (y si algún dia lo ves) agradecería enormemente me regales un poco de tu tiempo, llevo varios dias (meses y hasta años) trabajando en el desarrollo de un aplicativo de gestión comercial y esto viene como anillo a dedo. Mi correo es soycontactoarrobagmailpuntocom por si puedes enviarme parte de este contenido.Gracias de nuevo Ricardo V.
    miércoles, 27 de febrero de 2013 22:47
  • Manuel un placer, 

    Muy bueno tus aportes, si me puedes enviar ejemplo de ese form y su codigo,  al igual que tu modelo de factura para ver como lo adapto al mio.

    Un placer

    martes, 17 de septiembre de 2013 16:48