2010-01-14 7 views
5

Creo que me falta algo fundamental y por eso quiero pedir ayuda a la comunidad. Estoy construyendo una aplicación basada en una aplicación de utilidad básica de iPhone. Mi MainView y FlipsideView comparten algunos elementos, así que he creado ViewControllers y archivos de punta separados para esas piezas. Para hacer esto, he hecho lo siguiente: 1. Creé un controlador de visualización llamado searchDateViewController que es el propietario del archivo de searchDateView.xib 2. searchDateView.xib es básicamente una UIView con un UILabel adentro, la vista está conectada correctamente 3. Dentro tanto MainViewController.m y FlipsideViewController.m agrego una subvista como folllows:superview y parentviewcontroller nil después de agregar una subvista

- (void)loadView{ 
    [super loadView]; 
    searchDateViewController = [[SearchDateViewController alloc] initWithNibName:@"SearchDateView" bundle:nil]; 
    [[searchDateViewController view] setFrame:[searchDateView frame]]; 
    [[self view] addSubview:[searchDateViewController view]]; 

... 
} 

Todo pantallas y funciona muy bien. Básicamente, dependiendo de las acciones que suceden en cada una de las vistas principal y lateral, se cambia el UILabel de la punta. Sin embargo, quería hacer algo ligeramente diferente si searchDateViewController se carga desde MainView o FlipsideView. Sin embargo, no puedo entender qué ViewController está agregando la subvista searchDateViewController.

En searchDateViewController me trataron:

- (void)viewDidLoad { 
    [super viewDidLoad]; 
    NSLog(@"superview %@", self.view.superview); 
    NSLog(@"parentviewcontroller %@", self.parentViewController); 
} 

En ambos casos me sale nula.

Así que mi pregunta es: ¿puedo averiguar qué ViewController está agregando searchDateViewController en una subvista? ¿Si es así, cómo? O si mi lógica aquí está completamente desordenada, ¿cómo debería estar haciendo esto?

Gracias!

Respuesta

2

viewDidLoad se invoca cuando el controlador de vista se ha cargado su punto de vista. En su caso, que happends en esta línea:

[[searchDateViewController view] setFrame:[searchDateView frame]]; 

En ese momento, todavía no han llamado addSubview: por lo que no es de extrañar supervista de la vista es nula.

Para resolver su problema, debe definir una propiedad dentro de SearchDateViewController para distinguir entre los diferentes casos. A continuación, el controlador principal que crea la instancia de SearchDateViewController establecerá esta propiedad.

Generalmente, no creo que sea una buena idea usar una subclase UIViewController como controlador para una vista que se utiliza como subvista de una o varias vistas a pantalla completa en lugar de usarse como una vista de pantalla completa. Gran parte de la lógica de UIViewController se basa en la suposición de que se usa para administrar una vista de pantalla completa. Por ejemplo, con su diseño, creo que es posible que SearchDateViewController modifique el marco de la vista cuando cambia la orientación del dispositivo, etc.Como no necesita toda esta funcionalidad para una subvista que no sea de pantalla completa, le sugiero que subclassifique su SearchDateViewController directamente desde NSObject.

+0

De acuerdo, gracias por apuntarme en la dirección correcta con respecto a las subvistas y las subclases UIViewController. Si hago de SearchDateViewController una subclase de NSObject, ¿cómo va a afectar la forma en que estoy agregando las subvistas y comenzando con el plumín? No he encontrado ejemplos de subvistas como nsobjects en lugar de viewcontrollers, pero quiero comenzar a adoptar cualquier práctica estándar en este caso. Avísame si tienes más consejos, ¡gracias! Además, ambos sugirieron usar parentcontroller, lo cual tiene sentido, pero ¿qué papel desempeña Superview? ¿Sería eso más apropiado aquí? – deadroxy

+0

Convertir SearchDateViewController en una subclase de NSObject no elimina su problema, simplemente evita problemas futuros porque UIViewControllers no están destinados a ser utilizados para vistas que no ocupan toda la ventana en mi humilde opinión. Para resolver su problema, su código de personalización de vista no debe depender de self.parentViewController o view.superview en absoluto. En su lugar, defina una propiedad en SearchDateViewController (podría ser un BOOL o una enumeración) que luego consulta para decidir cómo personalizar la vista. El objeto que crea SearchDateViewController debe establecer la propiedad. –

+0

Hice exactamente lo que dijiste al crear una propiedad en la clase SearchDateViewController que funcionó bien. Sin embargo, todavía estoy desconcertado sobre cómo hacer la transición de la subclase de UIViewController a UIView/NSObject. Específicamente, ¿quién se convierte en el propietario del archivo de SearchDateView? Intenté de todas maneras y todo lo que hice dio como resultado errores ... – deadroxy

-2

ViewController y las vistas están completamente separadas.

En la mayoría de los casos, cuando agrega una subvista a una vista principal, no agrega su controlador al viewController del padre. La excepción a esta regla es el controlador de navegación que agrega el controlador en lugar de la vista para mantener una jerarquía de controladores de vista.

Tu SearchDate viewController no puede encontrar un controlador primario porque nunca lo asignaste y el sistema no lo hace automáticamente. Puede asignar un controlador principal cuando evoque la vista desde otro controlador.

searchDateViewController.parentController=self; 
+0

Tengo entendido que parentViewController está listo solo para que no pueda configurarlo (de hecho, me sale un error cuando lo intento). – deadroxy

+0

Seguimiento rápido: supongo que quiso decir lo mismo que Ole para crear una nueva propiedad dentro del SearchDateViewController para contener esta información. Eso funciona, pero sigo teniendo preocupaciones sobre el comentario de Ole sobre esta estrategia (de usar UIViewControllers como subvistas) que van en general en contra de los buenos principios de diseño ... – deadroxy

+0

Su derecho es de solo lectura. Simplemente asumí que era de lectura/escritura porque el controlador de navegación establece el atributo. Me pregunto cómo el controlador de navegación establece el atributo? Ole está en lo cierto al decir que tener múltiples controladores en la misma pantalla visible es una mala práctica. La API no es compatible con eso fácilmente. – TechZen

Cuestiones relacionadas