2014-12-05 8 views
5

Ich habe eine benutzerdefinierte Unterklasse von UIView zusammen mit einer XIB-Datei erstellt und IBOutlets und IBActions in der benutzerdefinierten Klasse deklariert.Benutzerdefiniertes UIView von Xib geladen

@interface ContactUsView : UIView 

@property (nonatomic, weak) IBOutlet UIButton *displayCloseButton; 

- (IBAction)callButtonPressed:(id)sender; 
- (IBAction)emailButtonPressed:(id)sender; 
- (IBAction)displayCloseButtonPressed:(id)sender; 

@end 

In der XIB-Datei habe ich eine UIView gezogen, um meine benutzerdefinierte Ansicht darzustellen. Ich habe ein:

  • Dateien owner = meine benutzerdefinierte Klasse
  • Haben die schleppt in UIView zu meiner benutzerdefinierten Klasse.

Ich habe dann verschiedene Tasten hinzugefügt, die an die 3 oben genannten Methoden angeschlossen sind.

Im Inneren des ContactUsView.m Ich habe folgendes:

- (id)initWithFrame:(CGRect)frame 
{ 
    if (self = [super initWithFrame:frame]) { 
     NSArray* array = [[NSBundle mainBundle] loadNibNamed:@"ContactUsView" owner:self options:nil]; 
     for (id object in array) { 
      if ([object isKindOfClass:[ContactUsView class]]) 
       self = (ContactUsView *)object; 
     } 
    } 
    return self; 
} 

Als ich gekommen, um diese Ansicht zu erstellen ich folgendes tun:

- (void)viewWillAppear:(BOOL)animated 
{ 
    ContactUsView *contactUs = [[ContactUsView alloc] initWithFrame:CGRectZero]; 

    CGPoint origin = self.view.frame.origin; 
    CGSize size = self.view.frame.size; 
    [contactUs setFrame:CGRectMake(origin.x, 
           CGRectGetMaxY(self.view.frame) - 100, 
           size.width, 
           contactUs.frame.size.height)]; 

    [self.view addSubview:contactUs]; 
} 

Ausgabe Wenn ich auf ein Drücken von die Tasten, mit denen die Anwendung abstürzt: Thread 1: EXC_BAD_ACCESS (Code = 2, Adresse = 0xb0c

Kann mir jemand dabei helfen. Ich habe das Gefühl, dass ich irgendwo einen Fehler mache, wenn ich benutzerdefinierte uiviews von xibs erstellen und laden möchte.

Wenn Sie weitere Informationen benötigen, lassen Sie es mich wissen. Danke vielmals.

Zukünftige Referenz Wenn Sie eine benutzerdefinierte Ansicht mit einem xib erstellen, legen Sie den Eigentümer der Dateien NICHT fest. Erstellen Sie stattdessen alle Ihre IBOutlets und IBActions wie gewohnt und öffnen Sie dann die Registerkarte "Dienstprogramme", um den Drag & Drop von dort aus zu steuern.

enter image description here

+0

Können Sie den ganzen Beitrag Error? Oder die Zeile, in der der Fehler tatsächlich passiert? Aktivieren Sie Haltepunkte bei Ausnahmen in XCode. – KerrM

+0

Wenn ich einen Unterbrechungspunkt in einer der Methoden, die aufgerufen wird, setzen, wird der Haltepunkt nie erreicht. Es stürzt nur mit dem obigen Code ab und nichts zeigt sich in der Ausgabe. Ich habe einen Breakpoint 'All exceptions' hinzugefügt und immer noch nichts in der Ausgabe angezeigt. – pls

Antwort

4

• Besitzer Files =

Wrong meiner benutzerdefinierten Klasse. Der Besitzer der Datei sollte leer sein. Die Ansicht selbst ist der Eigentümer der Dateien. Es bedeutet, dass Sie alle Aktionen und Ausgänge mit ContactUsView in Ihrem Xib verbinden sollten.

[[NSBundle main] loadNibNamed: @ "ContactUsView" Eigentümer: self Optionen: nil]

...

self = (ContactUsView *) Objekt;

Nachdem Sie self als owner Parameter übergeben. Du änderst es. Dies bedeutet, dass zuvor zugewiesene ContactUsView (self) zerstört werden, da -loadNibNamed:owner:options: nicht beibehalten werden.Wenn Sie mein erster Rat anwenden sollten Sie nil als owner Parameter

for Schleife hier senden nur array[0] nicht notwendig verwendet wird, da dies immer Ihre Ansicht ist, wenn Sie gültige Ansichten Hierarchie in Ihrem xib haben

+0

Vielen Dank Silmaril. Das hat mein Problem gelöst. Wenn Sie später eine benutzerdefinierte Ansicht erstellen möchten, müssen Sie das Tag "Dienstprogramme" öffnen und den Steuerbefehl von dort aus steuern. – pls

0

Sie Delegat für dieses verwenden können dieses ist, wie Sie das tun können,

 @protocol CustomViewDelegate <NSObject> 
- (void)callButtonPressed:(id)sender; 
- (void)emailButtonPressed:(id)sender; 
- (void)displayCloseButtonPressed:(id)sender; 

@end 

@interface ContactUsView : UIView 

@property (nonatomic, weak) IBOutlet UIButton *displayCloseButton; 

@property (nonatomic, weak) id<CustomViewDelegate> ButtonDelegate; 

- (IBAction)callButtonPressed:(id)sender; 

- (IBAction)emailButtonPressed:(id)sender; 
- (IBAction)displayCloseButtonPressed:(id)sender; 


@end 

und in.m-Datei

- (IBAction)callButtonPressed:(id)sender 
{ 
[self.ButtonDelegate callButtonPressed:sender]; 
} 

- (IBAction)emailButtonPressed:(id)sender{ 
[self.ButtonDelegate emailButtonPressed:sender]; 
} 

- (IBAction)displayCloseButtonPressed:(id)sender{ 
[self.ButtonDelegate displayCloseButtonPressed:sender]; 
} 

Danach setzen nur die Delegierten mit Viewcontroller refrence und verwenden, um die Delegierten hier

- (void)viewWillAppear:(BOOL)animated 

{

ContactUsView *contactUs = [[ContactUsView alloc] initWithFrame:CGRectZero]; 
contactUs.ButtonDelegate = self; 

CGPoint origin = self.view.frame.origin; 
CGSize size = self.view.frame.size; 
[contactUs setFrame:CGRectMake(origin.x, 
          CGRectGetMaxY(self.view.frame) - 100, 
          size.width, 
          contactUs.frame.size.height)]; 

[self.view addSubview:contactUs]; 

}

- (void)callButtonPressed:(id)sender 

{}

- (void)emailButtonPressed:(id)sender 

{}

- (void)displayCloseButtonPressed:(id)sender 

{}

ich dies getan haben, und arbeitet totlly feinen

+0

Danke für die Antwort. Laden Sie die Xib auf die gleiche Weise wie ich? Meine App stürzt ab, wenn ich auf eine Schaltfläche klicke, die an eine IBAction gebunden ist. Es stürzt jedoch sofort ab, was bedeutet, dass nichts in der Methode passiert. Es scheint mir, als ob etwas mit Speicher zu tun hat, wenn die Ansicht geladen ist. – pls

+0

Ja, ich mache das Gleiche. –

2

Wenn Sie eine UIView für eine xib Laden, dann sollten Sie eine Klassenmethode erstellen Lade die Ansicht.

In Ihrem customview.h

+(id)customView; 

& in Ihrem customview.m

+ (id)customView 
{ 
    CustomView *customView = [[[NSBundle mainBundle] loadNibNamed:@"CustomView" owner:nil options:nil] lastObject]; 
    if ([customView isKindOfClass:[CustomView class]]) 
     return customView; 
    else 
     return nil; 
} 

Sie können es initialisieren überall mit:

CustomView *myView = [CustomView customView]; 

EDIT: Stellen Sie sicher, habe die Klasse deiner customview in der Identität geändert Inspecter & auch sicherstellen, dass Ihre Verbindung von IBActions mit Methoden dieser Klasse sind. enter image description here

enter image description here

+0

Hallo Ajay. Ja, ich werde das wahrscheinlich als Klassenmethode implementieren. Der Code in Ihrer Methode entspricht jedoch meinem Code und verursacht immer noch den gleichen Absturz. – pls

+0

Überprüfen Sie meine aktualisierte Antwort – Ajay

+0

Silmaril Antwort machte mir klar, was ich falsch gemacht habe. Ich habe seine Antwort bereits angenommen, bevor ich Ihre bearbeitete Antwort gelesen habe, die dieselbe Lösung hat. Ich habe auch Ihre Antwort gewählt. Danke vielmals. – pls