У меня анимация UIView прерывистая - как я могу оптимизировать следующий код? - PullRequest
2 голосов
/ 14 января 2012

На симуляторе мой метод анимации работает плавно.К сожалению, кажется, что на iPhone 4 он работает очень резко.

Я не на 100% уверен в том, что лучший и самый быстрый способ создания анимации - так что любые советы о том, как я могу оптимизировать или полностью изменить свой коддля ускорения этой анимации было бы очень полезно!

Примечания:

Это уже в главном потоке, поэтому делает вызов dispatch_async (dispatch_get_main_queue ()) 'не имеет значения или бесполезен?

Есть ли способ предварительно буферизовать эту анимацию?

Есть ли способ точно определить, какая часть кода выполняет большую часть замедления?

Существует только около 3 или 4 представлений в extensionView.subviews.

Я скомпилировал с -Os.

- (void)extendWithAnimation:(BOOL)animated; {

    isExtended = YES;
    extensionView.hidden = NO;
    topShadowView.hidden = NO;

    topShadowView.frame = CGRectMake(0, defaultHeight, topShadowView.frame.size.width, topShadowView.frame.size.height);
    topShadowView.layer.bounds = CGRectMake(0, 0, topShadowView.frame.size.width, 0);
    extensionView.frame = CGRectMake(0, defaultHeight - 8, DEVICE_WIDTH, extensionHeight + 8);
    extensionView.layer.bounds = CGRectMake(0, 0, DEVICE_WIDTH, 0);

    for (UIView *view in extensionView.subviews) {
        view.transform = CGAffineTransformMakeTranslation(0, -(extensionHeight+8));
    }

    dispatch_async(dispatch_get_main_queue(), ^{

        if (animated) {
            [UIView beginAnimations:nil context:nil];
            [UIView setAnimationDuration:0.3];
            [UIView setAnimationDelegate:self];
        }

        extensionView.layer.bounds = CGRectMake(0, 0, DEVICE_WIDTH, extensionHeight + 8);
        topShadowView.layer.bounds = CGRectMake(0, 0, topShadowView.frame.size.width, extensionHeight + 8);

        for (UIView *view in extensionView.subviews) {
            view.transform = CGAffineTransformIdentity;
        }

        if (animated) {
            [UIView commitAnimations];
        }
    });   
}

Решение:

Решено (спасибо Аарон!).

Рендеринг теней убивает анимацию большое время!Не используйте какие-либо основные свойства теней графики, если вы планируете анимировать - в моем случае всего несколько теней снизили частоту кадров в три раза.

Ответы [ 2 ]

8 голосов
/ 14 января 2012
  1. Что ж, если код уже находится в главной очереди, использование dispatch_async будет иметь дополнительные издержки.
  2. Я не знаю, поможет ли это (я в этом сомневаюсь), но вы можете попробовать использовать [UIView animateWithDuration:.3 animations:{ code... }];
  3. В моих прошлых попытках справиться с тенями у них был довольно большой удар по производительности. Вы можете оставить тени и слои в покое и вместо этого создать PNG с изменяемым размером тени, который вы можете использовать в UIImageView, расположенном за видом, который вы хотите затенять.
1 голос
/ 14 января 2012

Запустите ваш код через инструменты (начните с Time Profiler).Какие вызовы занимают больше всего времени во время анимации?

После того, как вы профилировали его, также запустите его через инструмент Core Animation и включите раскраску закадрового рендеринга и непрозрачного контента.Это поможет изолировать типичные проблемы с графикой.

Я также заметил, что вы упоминаете тени.Если вы используете теневые свойства CALayer, это может снизить производительность.Но нам нужно больше информации, чтобы действительно это зафиксировать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...