Я пытаюсь дать пользователю возможность редактировать оттенок и яркость, используя пару ползунков, которые используют CIFilters для воздействия на изображение в UIImageView.
У меня это работает довольно хорошо, но с одной проблемой: если ползунки используются слишком часто, начинают появляться предупреждения о памяти, а затем, если пользователь продолжает попытки после этого, приложение закрывается, но журнала сбоев нет. (??? супер смущен этим).
Я все еще довольно новичок в программировании, особенно в управлении памятью, но, надеюсь, кто-то здесь может помочь.
Вот мой код:
В моем файле .h:
@property (weak, nonatomic) IBOutlet UISlider *hueSlider;
@property (weak, nonatomic) IBOutlet UISlider *brightnessSlider;
@property (weak, nonatomic) CIImage *outputImage;
@property (strong, nonatomic) CIFilter *hueFilter;
@property (strong, nonatomic) CIFilter *brightnessFilter;
@property (strong, nonatomic) CIContext *ccontext;
@property (strong, nonatomic) CIImage *inputImage;
- (IBAction)hueValueChangedAction:(id)sender;
- (IBAction)brightnessValueChangedAction:(id)sender;
И у меня также есть экземпляр BOOL, определенный под названием «imageFilterUpdating».
Вот соответствующие части .m:
- (IBAction)hueValueChangedAction:(id)sender {
if (!imageFilterUpdating) {
[self performSelectorInBackground:@selector(sliderValueChanged) withObject:nil];
}
}
- (IBAction)brightnessValueChangedAction:(id)sender {
if (!imageFilterUpdating) {
[self performSelectorInBackground:@selector(sliderValueChanged) withObject:nil];
}
}
- (void)sliderValueChanged {
imageFilterUpdating = YES;
if (inputImage == nil)
inputImage = [[CIImage alloc] initWithImage:self.imageWithoutOverlayView.image];
if (brightnessFilter == nil) {
brightnessFilter = [CIFilter filterWithName:@"CIExposureAdjust"];
[brightnessFilter setDefaults];
[brightnessFilter setValue: inputImage forKey: @"inputImage"];
}
[brightnessFilter setValue: [NSNumber numberWithFloat:self.brightnessSlider.value] forKey: @"inputEV"];
[self setOutputImage:[brightnessFilter valueForKey: @"outputImage"]];
if (ccontext == nil)
ccontext = [CIContext contextWithOptions:nil];
CIImage *editedInputImage = [[CIImage alloc] initWithCGImage:[ccontext
createCGImage:outputImage
fromRect:outputImage.extent]];
if (hueFilter == nil) {
hueFilter = [CIFilter filterWithName:@"CIHueAdjust"];
[hueFilter setDefaults];
}
[hueFilter setValue: editedInputImage forKey: @"inputImage"];
[hueFilter setValue: [NSNumber numberWithFloat:self.hueSlider.value] forKey: @"inputAngle"];
[self setOutputImage:[hueFilter valueForKey: @"outputImage"]];
UIImage *endImage = [[UIImage alloc] initWithCGImage:[ccontext
createCGImage:outputImage
fromRect:outputImage.extent]];
self.imageWithoutOverlayView.image = endImage;
[self setOutputImage:nil];
imageFilterUpdating = NO;
}
- (void)didReceiveMemoryWarning {
self.brightnessSlider.enabled = NO;
self.hueSlider.enabled = NO;
[super didReceiveMemoryWarning];
while (imageFilterUpdating); // this is because if you set the other parts nil in the middle of updating the image filter, the app crashes
[self setHueFilter:nil];
[self setBrightnessFilter:nil];
[self setCcontext:nil];
[self setOutputImage:nil];
self.brightnessSlider.enabled = YES;
self.hueSlider.enabled = YES;
}
Может ли кто-нибудь помочь мне более эффективно очистить память, чтобы пользователь мог бесконечно использовать ползунки? В противном случае этот код работает нормально.
Я пытался выделять/инициализировать вещи, где только мог, так как я читал во многих местах, что ARC справляется с этим намного лучше, чем с использованием таких вещей, как [UIImage imageNamed: @""], и кажется, Некоторым помогло, но приложение все равно вылетает после долгого редактирования. Я также начал повторно использовать переменные экземпляра, а не создавать новые переменные каждый раз при запуске метода, что также помогает, но не на 100%.
UISliders настроены на непрерывную работу, и я бы предпочел не менять это.
Спасибо