2009-05-23 28 views
8

Tengo una clase implementada IValueConverter y necesito que se la inyecte usando mi contenedor DI (Ninject).Cómo inyectar un convertidor en XAML

El problema es que, en XAML, no hay una forma inmediata obvia de controlar la creación de instancias del objeto Converter.

Así que mi XAML contiene una línea como la siguiente:

Fuente = "{ruta de enlace = CurrentMessage, convertidor = {StaticResource ImagePathConverter}}"

Cuando, la voluntad ImagePathConverter ser creado para mí.

Supongo que podría crear una clase estática de "localizador de servicios" y llamarla para resolver mi dependencia y cambiar el StaticResource a una propiedad "MyServiceLocator.TheImageConverter", pero eso me da ganas de vomitar.

Espero que esta pregunta se pueda responder con unos pocos fragmentos de código que se dirijan específicamente al código proporcionado, y quizás un enlace de apoyo a un ejemplo. No es simplemente una recomendación para echar un vistazo a algún lado.

Además, muy importante, suponga que el XAML no tiene un código detrás - y que no puedo usar uno. Estoy creando un piel y no quiero un código detrás. Entonces no puedo establecer una variable de clase en el constructor de la clase y hacer referencia a ella. Quizás eso no sea razonable, todavía no estoy seguro.

+0

Estoy interesado en saber por qué necesita el convertidor para ser resueltos con DI ..? – NotDan

+0

Porque el convertidor usa (depende) de una clase de formato, que tiene dependencias propias y cada una de esas dependencias también puede tener dependencias. Este es el objetivo de DI: conectar todas estas dependencias por mí. Me pregunto si muchas personas solo lo están utilizando para objetos nuevos y no se dan cuenta del propósito principal? – PandaWood

Respuesta

8

Una forma común de manejar esto es que su convertidor sea también un MarkupExtension. Es decir:

public class MyConverter : MarkupExtension, IValueConverter 

Su método ProvideValue() puede devolver una instancia de su convertidor, por lo tanto lo que le permite utilizar de esta manera:

Source="{Binding CurrentMessage, Converter={local:MyConverter SomeParameterToConverter}}" 

Esto no es realmente nada que ver con DI, pero responde a su requerimiento de eliminar el código detrás. Realmente no veo el punto de tener convertidores registrados en su contenedor DI.

+1

Gracias, es una preocupación justa sobre los convertidores. Al no ver los puntos de tener convertidores registrados en el contenedor DI, creo que suponer que el contenedor DI solo se está utilizando para objetos 'nuevos'. El punto es que la clase Converter en cuestión tiene otras dependencias que solo pueden ser resueltas por el contenedor DI (por ejemplo, objetos de "configuración" registrados en el ámbito singleton) – PandaWood

+0

Creo que esta es una buena respuesta cuando puedo corregir el error ' Falta XmlNamespace, Assembly o ClrNamespace en la instrucción de mapeo 'Volveré a él (es decir, a pesar de agregar xmlns: local = "clr-namespace: MyNamespace" – PandaWood

+1

¡Entendido! Solucionado el error y funciona muy bien. Todavía tenía que llamar mi DI en una moda de localización de servicios en el método ProvideValue, pero no creo que haya forma de evitarlo) – PandaWood

Cuestiones relacionadas