Soy consciente de que esta pregunta se ha hecho antes, pero las respuestas son contradictorias y estoy confundido, así que no me llames.
Quiero tener una UIViewsubclase reutilizable en toda mi aplicación. Quiero describir la interfaz usando un archivo nib.
Ahora digamos que es una vista de indicador de carga con un indicador de actividad. Me gustaría en algún evento crear una instancia de esta vista y animarla en la vista de un controlador de vista. Podría describir la interfaz de la vista sin problemas mediante programación, creando los elementos mediante programación y estableciendo su marco dentro de un método de inicio, etc.
Sin embargo, ¿cómo puedo hacer esto usando una punta? Mantener el tamaño dado en el generador de interfaces sin tener que establecer un marco.
Me las arreglé para hacerlo así, pero estoy seguro de que está mal (es solo una vista con un selector):
- (id)initWithDataSource:(NSDictionary *)dataSource {
self = [super init];
if (self){
self = [[[NSBundle mainBundle] loadNibNamed:[NSString stringWithFormat:@"%@", [self class]] owner:self options:nil] objectAtIndex:0];
self.pickerViewData = dataSource;
[self configurePickerView];
}
return self;
}
Pero me estoy sobrescribiendo a mí mismo, y cuando lo instancia:
FSASelectView *selectView = [[FSASelectView alloc] initWithDataSource:selectViewDictionary];
selectView.delegate = self;
selectView.frame = CGRectMake(0, self.view.bottom + 50, [FSASelectView width], [FSASelectView height]);
Tengo que configurar manualmente el marco en lugar de que lo recojan de IB.
EDITAR: Quiero crear esta vista personalizada en un controlador de vista y tener acceso para controlar los elementos de la vista. No quiero un nuevo controlador de vista.
Gracias
EDITAR: No sé si esta es la mejor práctica, estoy seguro de que no lo es, pero así es como lo hice:
FSASelectView *selectView = [[[NSBundle mainBundle] loadNibNamed:[NSString stringWithFormat:@"%@",[FSASelectView class]] owner:self options:nil] objectAtIndex:0];
selectView.delegate = self;
[selectView configurePickerViewWithData:ds];
selectView.frame = CGRectMake(0, self.view.bottom + 50, selectView.width, selectView.height);
selectView.alpha = 0.9;
[self.view addSubview:selectView];
[UIView animateWithDuration: 0.25 delay: 0 options:UIViewAnimationOptionAllowUserInteraction |UIViewAnimationOptionCurveEaseInOut animations:^{
selectView.frame = CGRectMake(0, self.view.bottom - selectView.height, selectView.width, selectView.height);
selectView.alpha = 1;
} completion:^(BOOL finished) {
}];
Todavía se quiere la práctica correcta
¿Debería haberse hecho esto usando un controlador de vista e init con el nombre de nib? ¿Debería haber configurado la punta en algún método de inicialización de UIView en el código? ¿O está bien lo que he hecho?

initWithDataSource? De todos modos, esto funcionará incluso si le da propietario como 'Nil'.Respuestas:
Estoy usando esto para inicializar las vistas personalizadas reutilizables que tengo.
Tenga en cuenta que puede usar "firstObject" al final, es un poco más limpio. "firstObject" es un método útil para NSArray y NSMutableArray.
Aquí hay un ejemplo típico de cargar un xib para usarlo como encabezado de tabla. En su archivo YourClass.m
Normalmente, en el
TopArea.xib, haría clic en Propietario del archivo y establecería el propietario del archivo en YourClass . Entonces, en realidad, en YourClass.h tendrías propiedades IBOutlet. EnTopArea.xib, puede arrastrar los controles a esos puntos de venta.No olvides que en
TopArea.xib, es posible que tengas que hacer clic en la Vista y arrastrarla a alguna salida, para que tengas el control de ella, si es necesario. (Un consejo que vale la pena es que cuando está haciendo esto para las filas de celdas de la tabla, es absolutamente necesario que lo haga: debe conectar la vista a la propiedad relevante en su código).fuente
Si desea mantener su
CustomViewy suxibindependienteFile's Owner, siga estos pasosFile's Ownercampo vacío.xibarchivoCustomViewy establezca suCustom ClasscomoCustomView(nombre de su clase de vista personalizada)IBOutleten el.harchivo de la vista personalizada..xibarchivo de su vista personalizada, haga clic en Ver y accedaConnection Inspector. Aquí tendrás todos tus IBOutlets que definas en.harchivoen el
.marchivo de suCustomViewclase, anule elinitmétodo de la siguiente maneraAhora, cuando quieras cargar tu
CustomView, usa la siguiente línea de código[[CustomView alloc] init];fuente
-init. En su lugar, llamaráinitWithFrame:y-awakeFromNib. Si escribe el mismo código para cargar su vista que en el-initmétodo, ingresará un bucle infinito.Siga los siguientes pasos
UIView.MyView.xib.UIViewControllerfromNSObjectin xib. Ver la imagen de abajoConecte la vista del propietario del archivo a su vista. Ver la imagen de abajo
Cambie la clase de su Vista a
MyView. Igual que 3.Aquí está el código para cargar la Vista:
Espero eso ayude.
Aclaración :
UIViewControllerse usa para cargar su xib y la vista queUIViewControllertiene es realmente laMyViewque ha asignado en el xib de MyView.Demostración he hecho un robo de demostración aquí
fuente
Respondiendo a mi propia pregunta acerca de 2 años más tarde aquí, pero ...
Utiliza una extensión de protocolo para que pueda hacerlo sin ningún código adicional para todas las clases.
fuente
En Swift:
Por ejemplo, el nombre de su clase personalizada es
InfoViewAl principio, creas archivos
InfoView.xibyInfoView.swiftasí:A continuación, establezca
File's OwneraUIViewControllerdesea:Cambie el nombre de su
ViewaInfoView:Haga clic derecho
File's Ownery conecte suviewcampo con suInfoView:Asegúrese de que el nombre de la clase sea
InfoView:Y después de esto, puede agregar la acción al botón en su clase personalizada sin ningún problema:
Y el uso de esta clase personalizada en su
MainViewController:fuente
Bueno, podría inicializar el xib usando un controlador de vista y usar viewController.view. o hazlo de la forma en que lo hiciste. Hacer solo una
UIViewsubclase como controladorUIViewes una mala idea.Si no tiene salidas desde su vista personalizada, puede usar directamente una
UIViewControllerclase para inicializarla.Actualización: En su caso:
De lo contrario, tiene que hacer un personalizado
UIViewController(para convertirlo en el propietario del archivo para que las salidas estén correctamente conectadas).Donde quiera que desee agregar la vista, puede usarla.
Sin embargo, pasar el otro controlador de vista (que ya se está utilizando para otra vista) como propietario mientras se carga el xib no es una buena idea, ya que la propiedad de vista del controlador cambiará y cuando desee acceder a la vista original, no lo hará. tener una referencia a él.
EDITAR: Se enfrentará a este problema si ha configurado su nuevo xib con el propietario del archivo como la misma
UIViewControllerclase principal y ha vinculado la propiedad de la vista a la nueva vista xib.es decir;
El siguiente código causará confusión más adelante, si lo escribe dentro de la vista se cargó
YourMainViewController. Eso se debe a que aself.viewpartir de este punto se referirá a su vista personalizadafuente