none
enlazar classe la ventana en xaml RRS feed

  • Pregunta

  • Hola,

    en mi caso temgo 2 clases:

                       MainWindow  (ventana)

                        Persona (con sus propiedades)

    desde el Mainwindow quiero acceder a propiedades de Persona...

    en el encabezado como de declara? este codigo no me encuentra la clase..:

    (tengo en la cabecera de xaml)

               Window.Resources>
           <ObjectDataProvider  x:Key="MyDataSource"  ObjectType="{x:Type src:Persona}"></ObjectDataProvider>
          </Window.Resources>

     

     

    martes, 28 de septiembre de 2010 11:47

Respuestas

  • Con esas dos líneas lo que estas haciendo es llenar un datatable con los datos de tu tabla de base de datos, y posteriormente, asignarle ese datatable a un Datagrid.

    Esta sería la forma más ruda. No sería necesario la clase Persona. Tus Binding deberían llamarse como los campos de tu tabla.

    Si deseas formatear (dar forma) a esa tabla lo más normal es hacer uso de tu clase Persona. La idea sería; grdDatos.ItemsSource=List(of Persona) conteniendo Persona los campos deseados. Estos campos son los que tu haces el Binding en el Datagrid. ¿Lllego a explicarme con claridad?

     ItemsSource="{Binding}"  en el XAML no lo necesitas porque lo asignas por código en el evento loaded.

    Si empleas la primera opción (la que yo te comentaba que es la más ruda) no es necesaria la clase persona (ni sus propiedades) porque directamente haces los Biding sobre los campos de la tabla (del datatable). Asi que los campos que no estén definidos en el datatable no puedes Bindearlos al XAML.

    Si quieres emplear la clase Persona (son las propiedades las que debes hacer Biding sobre el XAML). Pero entonces la estructura en el evento load no es: grdDatos.ItemsSource=Tu datatable sino que aqui sería una lista de objetos con la forma Persona (list(of Persona))

    Algo así como:

    Dim nListaPersona as new List(of Persona)

    nListaPersona.add(new Persona with{.Propiedad1=nPropiedad1, .Propiedad2=nPropiedad2}

    nPropiedad1, nPropiedad2 pueden ser directamente campos de tu datatable o calculados

    ¿Complejo?. Uhmmm, una vez de visto todo el mundo es listo ;-). Yo en tu caso empezaría haciendo cosas sencillas, y leyendo mucho (Haces muy bien en leer el blog de Yeray. Yo te lo recomiendo, asi como el de David). Y a medida que vayas asimilando conceptos me atrevería con cosas nuevas. Asi que tomate el tiempo que necesites. Yo también soy un novato, tengo mucho que aprender ;-) Y pregunta, pregunta, pregunta. No te quedes con las dudas, que muchas veces aprendemos de las preguntas de otros ;-)

    Revisa el enlace que te propuse en la anterior entrada: http://blogs.msdn.com/b/scmorris/archive/2008/03/27/defining-columns-for-a-silverlight-datagrid.aspx Mira cómo realiza la carga con una clase intermedia de formateo (dar forma).

    Un saludo,

    • Marcado como respuesta Spandau miércoles, 29 de septiembre de 2010 23:41
    miércoles, 29 de septiembre de 2010 11:58

Todas las respuestas

  • ¡Hola!

    Esta pregunta me suena y te veo muy atascado. Si te parece bien, comparte el código en el Skydrive. A ver si consigo hacer lo que deseas ;-).

    Un saludo

    martes, 28 de septiembre de 2010 14:56
  • Hola,

    tienes razon,

    estoy a punto de tirar la toalla....me gusta wpf,

    pero cuando las cosas se complican......

    dejo el enlace del proyecto y 2 archivos con lo que pretendo hacer,

    me queda la duda tambien de como distribuir clases,propertys,etc

    enlace:

      http://cid-b85627fda5bc8532.office.live.com/self.aspx/.Public/privada%20projectes/Proyecto.rar

    Gracias por adelantado
    martes, 28 de septiembre de 2010 22:27
  • ¡Hola!

    Aqui no abandona nadie. Que todos compartimos la misma pasión ;-).

    Lo miro y te comentó.

    Un saludo,

     

    miércoles, 29 de septiembre de 2010 6:35
  • ¡Hola!

     

    Lo he estado mirando. Jejeje. Que cacao ;-). No te asustes. Lo que vamos a hacer es ir haciéndolo poco a poco (los problemas de uno en uno). Si te parece bien.

    Lo primero. Si sólo vas a tener dos tablas con pocos registros. ¿No has pensado en sustituir tu base de datos por dos archivos XML?. De esta forma no tienes que tener un servidor SQL para hacer correr tu aplicación. El acceso a los datos es mas rápido que tener que hacer una conexión a SQL.

    Segundo. Emplea estructuras Try Catch en tu código para controlar los errores (muy importante)

    Bueno, ya entramos en el código. A la clase Persona cuando la instancia no le pases MainWindows (o cualquier otra ventana). Rompes con la filosofía de programación a objetos. Si necesitas saber quién ha llamado a ese objeto desde el objeto existe una propiedad en el objeto que es Parent.

    Resumiendo, comentamos ese New y la propiedad que recoge MainWindows

    Cuarto. Nos situamos en MainWindows en la parte de código.

    Dispones de dos New (ok, un new sobrecargado). No hagas dos InitializeComponent.

    Dejas el que viene por defecto como esta y en el tuyo que has sobre cargado llamas al primero. Así:

    Public Sub New(ByVal nomsencer As String)
    
     Me.new()
     Me.NomSencer = nomsencer
    
     End Sub
    

    Quinto: Si es posible diferencia la carga de los datos de la carga de controles gráficos (va a depender del tiempo que se tarde en cargar esos datos).

    Yo la carga de los datos lo haría en el evento loaded no vaya a ser que todavía se este diseñando el control y nosotros asignándole datos. Alguna vez he tenido esos problemas al programar PDAs.

    En resumen: En tu loaded pon  

    custamistats.Fill(dsamistats.amistats)
    
    grdDatos.ItemsSource = dsamistats.amistats
    

    Lo que te obliga a comentar la línea en el XAML: ItemsSource="{Binding}"

    Con esas dos líneas lo que estas haciendo es llenar un datatable con los datos de tu tabla de base de datos, y posteriormente, asignarle ese datatable a un Datagrid.

    Esta sería la forma más ruda. No sería necesario la clase Persona. Tus Binding deberían llamarse como los campos de tu tabla.

    Si deseas formatear (dar forma) a esa tabla lo más normal es hacer uso de tu clase Persona. La idea sería; grdDatos.ItemsSource=List(of Persona) conteniendo Persona los campos deseados. Estos campos son los que tu haces el Binding en el Datagrid. ¿Lllego a explicarme con claridad?

    Bueno, por el momento creo que he dejado ko, demasiadas cosas a la vez ;-). Asi que hacemos una pausa para que vayas rumiando, modifiques el código, hagas pruebas y comentes.

    Un saludo,

     

    • Propuesto como respuesta Josue YerayMVP, Moderator miércoles, 29 de septiembre de 2010 8:57
    • Votado como útil Spandau miércoles, 29 de septiembre de 2010 10:57
    • Marcado como respuesta Spandau miércoles, 29 de septiembre de 2010 11:23
    • Desmarcado como respuesta Spandau miércoles, 29 de septiembre de 2010 19:37
    miércoles, 29 de septiembre de 2010 7:44
  • PRIMERO DE  TODO MUCHAS GRACIAS   UNOS CONSEJOS SIEMPRE VAN MUY BIEN PARA LOS 'NOVATOS'

    -Lo del consejo de xml, más adelante lo provaré... gracias por el consejo... ya que tal como lo tengo..el  .mdf dentro de la carpeta... veo complicado modificar columnas..supongo que he de mirar de cargarlo al sqlserver para modificarlo...

    -Try Cath colocados

    -he creado el  evento loaded  con  el contenido  que me has aconsejado, ahora tengo:

        Private Sub MainWindow_Loaded(ByVal sender As Object, ByVal e As System.Windows.RoutedEventArgs) Handles Me.Loaded
            Try
                custamistats.Fill(dsamistats.amistats)
                grdDatos.ItemsSource = dsamistats.amistats 
            Catch ex As Exception
                MsgBox(ex.ToString)
            End Try
        End Sub

     

    el   ItemsSource="{Binding}"  ya lo tenia declarado en grdDatos:

     <DataGrid Name="grdDatos" Grid.Row="1" Margin="5" FontSize="18" FontFamily="Cambria"
                      VerticalAlignment="Stretch" HorizontalAlignment="Stretch"  
                      AutoGenerateColumns="False" IsSynchronizedWithCurrentItem="True"   ItemsSource="{Binding}" >

     

    y el primer paso que es la carga de la Propiedad Nomsencer() no me carga en la columna todavia...

    estoy repasando el codigo.... y a  ver...

               - en la clase  MainWindow.vb le digo al datagrid grdDatos que el origen es el Dataset.... tambien me reconoce a los propertys? quizà por aqui me venga el

                 error que no me cargue el Property, un  Multibinding si, pero  para el Property se tendria que enlazar de alguna manera con la clase  MainWindow. No sé...

    Si logro solucionar esto ya seguramente lo solucionaré todo...

    Me aconsejas hacer servir los Bindings y olvidarme de la clase Persona de momento si los bindings al dataset funcionan...

    Pero si quiero  trabajar con la clase Persona  haciendo los cambios que me propones me funcionaria?? no parece complicado.

     MILES  DE  GRACIAS

     

    miércoles, 29 de septiembre de 2010 11:23
  • Con esas dos líneas lo que estas haciendo es llenar un datatable con los datos de tu tabla de base de datos, y posteriormente, asignarle ese datatable a un Datagrid.

    Esta sería la forma más ruda. No sería necesario la clase Persona. Tus Binding deberían llamarse como los campos de tu tabla.

    Si deseas formatear (dar forma) a esa tabla lo más normal es hacer uso de tu clase Persona. La idea sería; grdDatos.ItemsSource=List(of Persona) conteniendo Persona los campos deseados. Estos campos son los que tu haces el Binding en el Datagrid. ¿Lllego a explicarme con claridad?

     ItemsSource="{Binding}"  en el XAML no lo necesitas porque lo asignas por código en el evento loaded.

    Si empleas la primera opción (la que yo te comentaba que es la más ruda) no es necesaria la clase persona (ni sus propiedades) porque directamente haces los Biding sobre los campos de la tabla (del datatable). Asi que los campos que no estén definidos en el datatable no puedes Bindearlos al XAML.

    Si quieres emplear la clase Persona (son las propiedades las que debes hacer Biding sobre el XAML). Pero entonces la estructura en el evento load no es: grdDatos.ItemsSource=Tu datatable sino que aqui sería una lista de objetos con la forma Persona (list(of Persona))

    Algo así como:

    Dim nListaPersona as new List(of Persona)

    nListaPersona.add(new Persona with{.Propiedad1=nPropiedad1, .Propiedad2=nPropiedad2}

    nPropiedad1, nPropiedad2 pueden ser directamente campos de tu datatable o calculados

    ¿Complejo?. Uhmmm, una vez de visto todo el mundo es listo ;-). Yo en tu caso empezaría haciendo cosas sencillas, y leyendo mucho (Haces muy bien en leer el blog de Yeray. Yo te lo recomiendo, asi como el de David). Y a medida que vayas asimilando conceptos me atrevería con cosas nuevas. Asi que tomate el tiempo que necesites. Yo también soy un novato, tengo mucho que aprender ;-) Y pregunta, pregunta, pregunta. No te quedes con las dudas, que muchas veces aprendemos de las preguntas de otros ;-)

    Revisa el enlace que te propuse en la anterior entrada: http://blogs.msdn.com/b/scmorris/archive/2008/03/27/defining-columns-for-a-silverlight-datagrid.aspx Mira cómo realiza la carga con una clase intermedia de formateo (dar forma).

    Un saludo,

    • Marcado como respuesta Spandau miércoles, 29 de septiembre de 2010 23:41
    miércoles, 29 de septiembre de 2010 11:58
  • He provado el ejemplo del enlace que me has pasado  y he intentado crear un List de Persona... y me pierdo....

    Necesito cosas mas 'simples'....

     

       me estoy desviando del tema que comencé.... pero creo que así lo puedo solucionar...

     

         hace unos meses nuestro compañero David me dio la solucion de cargar un Property en un Texbox:

             http://social.msdn.microsoft.com/Forums/es-ES/wpfes/thread/c4e05269-28a6-4ac7-aa42-55b3b0a7a0f8

     hace dias lo prové i me mostrava en la salida del Property a un texbox a veces false o a veces en blanco, me he dado cuenta  hoy que cuando me carga la ventana dicho texbox esta sin valor. También tengo el problema que cuando el texbox cambia de valor el property no se actualiza ....el que tengo de ejemplo:

        Public Property Prueba() As String
            Get
                _nom = txtnom.Text
                If _nom = "" Then
                    _nom = "null"
                End If
                Return _nom
            End Get
            Set(ByVal value As String)
            End Set
        End Property

    he provado de ir a eventos del  txtnom.Text i he provado con varios eventos changed y  dentro del evento que me lea el _nom... pero no cambia nada... Como lo solucionarias?

     

    Miles de gracias

    miércoles, 29 de septiembre de 2010 23:40
  • ¡Hola!

    He leído por encima el post que indicas (David es muy bueno ;-)).

    Analizo lo que hace tu propiedad:

       Public Property Prueba() As String
            Get
                _nom = txtnom.Text
                If _nom = "" Then
                    _nom = "null"
                End If
                Return _nom
            End Get
            Set(ByVal value As String)
            End Set
        End Property

    Tienes una propiedad llamada Prueba de lectura y escritura.

    Para leer lee del textboxt. Si recibe un "" pone a la variable _nom una cadena null (en vb.net en vez de emplear null como en C# se pone nothing) y retorna la variable _nom.

    Para escribir recibe el valor pero no lo escribe en ningún lado. Te falta poner _nom=value. De esta forma guarda el valor de prueba en la variable.

    Respecto al resto, me pierdo en lo que quieres hacer. ¿En un evento changed del textbox deseas recoger el cambio del valor en la propiedad?

    Uhmmm. Si me lo permites yo te aconsejaría que te hicieras con este libro, que es muy básico, pero que te va a dar unos buenos cimientos para hacer cosas más complejas: http://www.elguille.info/NET/MIVB2005/comprar.aspx

    Un saludo,

     

    jueves, 30 de septiembre de 2010 9:38
  • Hola yo tambien soy nuevo en esto y te animo a que continues!! sobre todo porque gracias a este foro todo se puede conseguir!!

     

    A mi lo que se me ocurre para que puedas acceder a los atributos de una clase desde una o cualquier pagina xaml es que te declares la case como estatica y asi podrás sin problemas.

     

    Un saludo

    jueves, 30 de septiembre de 2010 10:23
  • ¡Hola!

    Para acceder a las propiedades de una clase la instancias. No la crees estática en C# o Shared o en un módulo en VB.net porque si bien es accesible en todo el proyecto es un recurso que estaría en memoría durante toda la vida del proyecto.

    Saludos,

    jueves, 30 de septiembre de 2010 10:55
  • Hola Corsario,

    en mi ultima intervencion me he enrollado mucho..

    lo que me passa que el   property me lee de txtnom.Text  , y  me lo guarda, y me muestra el valor en otro texbox (mas adelante harà más cosas), pero el problema lo tengo que si cambio de registro y  por lo tanto el txtnom.Text cambia de contenido... el valor en el property no me cambia....(no se refleja en el texbox de salida a traves del binding)

    me falta algun detalle que al cambiar de valor en txtnom.Text me vuelva a leer el property...(pensava que por defecto lo haria)

     

    Gracias.

    jueves, 30 de septiembre de 2010 11:40
  • Ok.

    "Para escribir recibe el valor pero no lo escribe en ningún lado. Te falta poner _nom=value. De esta forma guarda el valor de prueba en la variable."

    Set(ByVal value As String)

    _nom=value

    End Set

    Además, tienes que poner en el evento change del textbox: Prueba=Textbox.text de esta manera cuando cambie el valor del textbox te cambiará la propiedad.

    Saludos,

     

    jueves, 30 de septiembre de 2010 12:05