Изменить цвет подсветки в NSTableView в Какао? - PullRequest
15 голосов
/ 12 августа 2011

Я разрабатываю приложение Какао и столкнулся с проблемой выделения.Стандартный цвет подсветки в приложениях MAC OS X - синий, но он не подходит моему приложению, так как из-за концепций дизайна мне нужен зеленый цвет для подсветки.

Я попытался создать подкласс NSTableview и переопределить метод

- (void)highlightSelectionInClipRect:(NSRect)clipRect

но это не помогло.

Как решить эту проблему?

Ответы [ 3 ]

19 голосов
/ 12 августа 2011

Я использую это, и пока отлично работает:

- (void)highlightSelectionInClipRect:(NSRect)theClipRect
{

        // this method is asking us to draw the hightlights for 
        // all of the selected rows that are visible inside theClipRect

        // 1. get the range of row indexes that are currently visible
        // 2. get a list of selected rows
        // 3. iterate over the visible rows and if their index is selected
        // 4. draw our custom highlight in the rect of that row.

    NSRange         aVisibleRowIndexes = [self rowsInRect:theClipRect];
    NSIndexSet *    aSelectedRowIndexes = [self selectedRowIndexes];
    int             aRow = aVisibleRowIndexes.location;
    int             anEndRow = aRow + aVisibleRowIndexes.length;
    NSGradient *    gradient;
    NSColor *       pathColor;

        // if the view is focused, use highlight color, otherwise use the out-of-focus highlight color
    if (self == [[self window] firstResponder] && [[self window] isMainWindow] && [[self window] isKeyWindow])
    {
        gradient = [[[NSGradient alloc] initWithColorsAndLocations:
                     [NSColor colorWithDeviceRed:(float)62/255 green:(float)133/255 blue:(float)197/255 alpha:1.0], 0.0, 
                     [NSColor colorWithDeviceRed:(float)48/255 green:(float)95/255 blue:(float)152/255 alpha:1.0], 1.0, nil] retain]; //160 80

        pathColor = [[NSColor colorWithDeviceRed:(float)48/255 green:(float)95/255 blue:(float)152/255 alpha:1.0] retain];
    }
    else
    {
        gradient = [[[NSGradient alloc] initWithColorsAndLocations:
                     [NSColor colorWithDeviceRed:(float)190/255 green:(float)190/255 blue:(float)190/255 alpha:1.0], 0.0, 
                     [NSColor colorWithDeviceRed:(float)150/255 green:(float)150/255 blue:(float)150/255 alpha:1.0], 1.0, nil] retain];

        pathColor = [[NSColor colorWithDeviceRed:(float)150/255 green:(float)150/255 blue:(float)150/255 alpha:1.0] retain];
    }

        // draw highlight for the visible, selected rows
    for (aRow; aRow < anEndRow; aRow++)
    {
        if([aSelectedRowIndexes containsIndex:aRow])
        {
            NSRect aRowRect = NSInsetRect([self rectOfRow:aRow], 1, 4); //first is horizontal, second is vertical
            NSBezierPath * path = [NSBezierPath bezierPathWithRoundedRect:aRowRect xRadius:4.0 yRadius:4.0]; //6.0
                [path setLineWidth: 2];
                [pathColor set];
                [path stroke];

            [gradient drawInBezierPath:path angle:90];
        }
    }
}
10 голосов
/ 24 ноября 2013

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

1) Установите для NSTableView selectionHighLightStyle значение None

Это необходимо для того, чтобы OSX не просто применял свои собственные блики наднаверху, оставляя вас с синей подсветкой.

Вы можете сделать это либо через IB, либо с помощью кода.

2) Подкласс NSTableView и переопределить drawRow.

Этоустановит цвет фона для выбранных вами строк на основной (активное окно) и вторичный (неактивный).

- (void)drawRow:(NSInteger)row clipRect:(NSRect)clipRect
{
    NSColor* bgColor = Nil;

    if (self == [[self window] firstResponder] && [[self window] isMainWindow] && [[self window] isKeyWindow])
    {
        bgColor = [NSColor colorWithCalibratedWhite:0.300 alpha:1.000];
    }
    else
    {
        bgColor = [NSColor colorWithCalibratedWhite:0.800 alpha:1.000];
    }

    NSIndexSet* selectedRowIndexes = [self selectedRowIndexes];
    if ([selectedRowIndexes containsIndex:row])
    {
        [bgColor setFill];
        NSRectFill([self rectOfRow:row]);
    }
    [super drawRow:row clipRect:clipRect];
}

3) Реализуйте NSTableViewDelegate, присоедините его к вашему NSTableView и внедрите willDisplayCell.

Это позволит вам изменить textColor строк при выделении / отмене выделения, если цвета выделения затрудняют чтение текста.

- (void)tableView:(NSTableView *)aTableView willDisplayCell:(id)aCell forTableColumn:(NSTableColumn *)aTableColumn row:(NSInteger)rowIndex
{
    // check if it is a textfield cell
    if ([aCell isKindOfClass:[NSTextFieldCell class]])
    {
        NSTextFieldCell* tCell = (NSTextFieldCell*)aCell;
        // check if it is selected
        if ([[aTableView selectedRowIndexes] containsIndex:rowIndex])
        {
            tCell.textColor = [NSColor whiteColor];
        }
        else
        {
            tCell.textColor = [NSColor blackColor];
        }
    }
}

И все готово.

2 голосов
/ 21 февраля 2012
- (void)drawInteriorWithFrame:(NSRect)frame inView:(NSView *)controlView
{

    if ([self isHighlighted])
    {
        NSRect bgFrame = frame;
        [[NSColor redColor] set];  
        NSRectFill(bgFrame);

    }
}

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

...