Перераспределение NSCollectionView на прокрутке вызывает распад графики

StackOverflow https://stackoverflow.com/questions/1758597

Вопрос

У меня незначительное раздражение в NSCollectionView в которой NSCollectionViewItemРазбивается визуально, когда я прокручиваю окно.

Скорость разрыва зависит от скорости прокрутки. Например, если я медленно прокручиваю, разрыв происходит чаще. Быстрая прокрутка меньше. Похоже, что проблема в том, когда пользовательский NSView NSCollectionViewItem Я использую кресты границу просматривающейся рамки.

Мой nsview (пользовательский вид NSCollectionViewItem) имеет очень простой алгоритм рисования - ничего слишком сложного.

По сути, я создаю кадр в грязном образе метода натяжения и создаю несколько кадров внутри этого:

-(void)drawRect:(NSRect)dirtyRect
{   
    NSRect mOuterFrame = NSMakeRect(dirtyRect.origin.x, dirtyRect.origin.y, 104, 94);
    NSRect mSelectedFrame = NSInsetRect(mOuterFrame, 2, 2);
    NSRect mRedFrame = NSInsetRect(mSelectedFrame, 2, 2);
    NSRect mInnerFrame = NSInsetRect(mRedFrame, 2, 2);

    NSBezierPath * mOuterFramePath = [NSBezierPath bezierPathWithRect:mOuterFrame];
    NSBezierPath * mSelectedFramePath = [NSBezierPath bezierPathWithRect:mSelectedFrame];
    NSBezierPath * mRedFramePath = [NSBezierPath bezierPathWithRect:mRedFrame];
    NSBezierPath * mInnerFramePath = [NSBezierPath bezierPathWithRect:mInnerFrame];

    [mainBackgroundColor set];
    [mOuterFramePath fill];

    if (selected)
        [[NSColor yellowColor] set];
    else
        [mainBackgroundColor set];

    [mSelectedFramePath fill];

    if (isRedBorder)
        [[NSColor redColor] set];
    else
        [mainBackgroundColor set];

    [mRedFramePath fill];

    [[NSColor blackColor] set];
    [mInnerFramePath fill];
}

Я пытался заблокировать фокус и выпустить до и после кода, а также установить графический контекст и восстановить его - ни один из которых, кажется, не решает проблему.

Я использую Snow Leopard - не то, что я думаю, что это имеет значение.

Обновление решения

Для всех, кто заинтересован здесь, является решением проблемы, рекомендованной NSResponder. Я создавал начальный mOuterFrame на основе drawRect: методы dirtyRect что, как отмечалось, было неверным, что нужно сделать. Быстрое изменение от:

NSRect mOuterFrame = NSMakeRect(dirtyRect.origin.x, dirtyRect.origin.y, 104, 94);

В 0 -м точке происхождения:

NSRect mOuterFrame = NSMakeRect(0, 0, 104, 94);

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

-(void)drawRect:(NSRect)dirtyRect
{   
    NSRect mOuterFrame = NSMakeRect(0, 0, 104, 94);
    NSRect mSelectedFrame = NSInsetRect(mOuterFrame, 2, 2);
    NSRect mRedFrame = NSInsetRect(mSelectedFrame, 2, 2);
    NSRect mInnerFrame = NSInsetRect(mRedFrame, 2, 2);

    [NSBezierPath setDefaultLineWidth:2.0];

    [mainBackgroundColor set];
    [NSBezierPath strokeRect:mOuterFrame];

    if (selected)
        [[NSColor yellowColor] set];
    else
        [mainBackgroundColor set];

    [NSBezierPath strokeRect:mSelectedFrame];

    if (isRedBorder)
        [[NSColor redColor] set];
    else
        [mainBackgroundColor set];

    [NSBezierPath strokeRect:mRedFrame];

    [[NSColor blackColor] set];
    [NSBezierPath strokeRect:mInnerFrame];
}
Это было полезно?

Решение

Во -первых, я заметил, что ваш код выше довольно расточительна, поскольку вы создаете кучу путей, когда вы можете просто использовать nsframerect () и nsrectfill ().

Во -вторых, геометрия того, что вы рисуете, не должна зависеть от прямоугольника, передаваемого в -монте:. Этот прямоугольник просто рассказывает вам, какая область для обновления, поэтому вы можете быть более эффективным, решая, что нарисовать, если ваш взгляд является сложным.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top