Переменные в отдельном классе возвращают значение null

#objective-c #macos #class #variables

#objective-c #macos #класс #переменные

Вопрос:

Хорошо, я думаю, что вопрос, который у меня здесь возник, был многословным и трудным для понимания. Я упрощу свой вопрос:

  • У меня есть класс под названием InController.
  • У InController есть вызываемый метод, nextPage который сообщает переменной int, inPageNumber , добавить ее к себе и вызвать другой вызываемый метод InController updateTable .
  • updateTable очищает таблицу, InTable, от ее текущих данных и заполняет ее данными, относящимися к номеру страницы, с которой она извлекается inPageNumber .
  • Таблица, InTable, содержится внутри NSBox с особыми требованиями к печати.
  • Я выделил подкласс NSBox в класс под названием CustomViewPagination для удовлетворения этих требований к печати, переопределив его методы разбивки на страницы. В принципе, когда требуется новая страница для печати, она пытается снова напечатать ту же область, но вызывает nextPage для заполнения таблицы данными последующей страницы.

Со мной до сих пор?

Один из методов разбивки на страницы, который я переопределил в CustomViewPagination, beginPageInRect , по умолчанию автоматически вызывается для каждой печатной страницы. Из-за этого я разместил вызов моего метода InController nextPage , чтобы изменить данные InTable, для текущей страницы печати.

Моя проблема заключается в том, что я вызываю nextPage (который является методом в InController) из моего класса CustomViewPagination. Это ничего не дает, и когда я его отлаживаю, я обнаруживаю, что все переменные, требуемые в методе, равны нулю. Тем не менее, они являются правильными значениями, когда я вызываю nextPage изнутри InController.


Извлечения из файла:

InController.h:

 #import <Cocoa/Cocoa.h>
#import "CustomViewPagination.h"

@interface InController : NSObject {
    IBOutlet NSWindow *inPreview;
    IBOutlet CustomViewPagination *inSheet;
    NSArray *iSelectedIn;
    NSMutableArray *records;
    int inPageNumber;
}
@property (nonatomic, retain) NSArray *iSelectedIn;
@property (nonatomic, retain) NSMutableArray *records;
  

InController.m:

 #import "InController.h"

@implementation InController

@synthesize iSelectedIn, records;

- (IBAction) inNextPage:(id)sender {
    inPageNumber = inPageNumber   1;
    NSLog(@"inPageNumber called ok");
    [self updateIn];
}


- (IBAction)updateInvoice:(id)sender {
    //wipe all current records and refresh empty table
    [records removeAllObjects];
    [inPreviewTable reloadData];
    for (NSArray *s in [[iSelectedIn valueForKey:@"inJobList"] lastObject]) {
        NSString *jLT = [s valueForKey:@"inJT"];
        NSString *jLH = [s valueForKey:@"inJHo"];
        NSString *jLC = [s valueForKey:@"inJC"];
        // etc.
        // if CustomViewPagination called this, records is nil, so nothing
        // is cleared, and there's no *s for iSelectedIn as iSelectedIn
        // is found to be nil. If InController called this, it works fine.
  

CustomViewPagination.h:

 #import <Cocoa/Cocoa.h>

@class InController;

@interface CustomViewPagination : NSBox {
    InController *inControllerInstance;
}

@end
  

CustomViewPagination.m:

 #import "CustomViewPagination.h"
#import "InController.h"

@implementation CustomViewPagination

- (void) awakeFromNib {
    inControllerInstance = [[InController alloc] init];
}

- (void)beginPageInRect:(NSRect)aRect atPlacement:(NSPoint)location {
    int pageCounter = [[NSPrintOperation currentOperation] currentPage];
    if (pageCounter == 1) {
        // Don't respond to 1st page, do nothing.
    } else {
        [inControllerInstance inNextPage:self];
    }
    [super beginPageInRect:aRect atPlacement:location];
}

@end
  

Комментарии:

1. Где ваш метод инициализации burbController? (Обратите внимание, что имена классов всегда начинаются с верхнего регистра — BurbController. Также у вас есть ошибочная точка с запятой в конце вашего метода -beginPageInRect )

Ответ №1:

Вы используете 2 IBOutlets в InController ( inPreview amp; inSheet ), но InController создается программно в CustomViewPagination's awakeFromNib .

Как подключены выходы? (Не может быть из IB, поскольку вы создаете InController экземпляр программно). Это было бы объяснением, почему оба являются nil .

Комментарии:

1.Хорошо, этот путь исследования отличается от всего, что я читал / предлагал до сих пор. Я заинтригован. Я понимаю основы того, что вы говорите, но я немного сбит с толку. Я подключил CustomViewPagination inSheet к единственному объекту CVP в моем интерфейсе, который использует переопределенные методы подкласса. Причина этого в том, что позже я идентифицирую его по имени, когда буду описывать, что печатать в NSPrintOperation . Как бы мне избежать использования outlets для этого? Или же избегайте создания его программно в awakeFromNib и используйте только выходы (в основном, используйте один или другой).

2. inSheet — это выход InController. Чтобы подключить выход к объекту, вам необходимо создать экземпляр этого объекта в IB. Если вы сделали это и создаете еще один экземпляр InController в awakeFromNib: от CustomViewPagination, вы получите 2 разных экземпляра InController. Тот, который подключен внутри nib, и тот, который получает сообщения, которые вы отправляете из beginPageInRect : . Для меня это звучит так, что вы просто хотите иметь один контроллер рядом. Это правильно?

3.Правильно 🙂 Я в курсе того, что вы говорили в начале. Теперь я понимаю, что использую две привычки, которые не должны пересекаться. Я проявил некоторую инициативу и удалил инициализацию InController в CustomViewPagination awakeFromNib и вместо этого подключил розетку к InController в моей палитре Nib. Теперь я не уверен, как обращаться к тому же экземпляру InController, как вы предлагали, я хотел бы сделать (и я делаю).

4. Вы сделали inControllerInstance IBOutlet правильно? Таким образом, вы можете отправить inNextPage в inControllerInstance. Просто установите точку останова в beginPageInRect и проверьте, не равно ли значение inControllerInstance нулю. Я недостаточно знаю о вашем дизайне. Но вы могли бы рассмотреть возможность рефакторинга некоторых частей (возможно, с использованием NSViewController), чтобы избежать передачи экземпляров контроллера в классы просмотра.

5. У меня все чаще возникают проблемы с созданием IBOutlet для экземпляра inController . Я могу нормально перейти к классу в палитре nib, но, очевидно, я получаю предупреждения о том, что класс может не отвечать на вызовы моих методов, поскольку они не относятся к уровню класса. Каков наиболее простой способ использования IBOutlet для передачи экземпляра InController . Обычно на этом этапе я выделяю и инициализирую класс, но именно это создает отдельный экземпляр и вызывает у меня огорчение.