简体   繁体   English

NSTableRowView / NSTableCellView如何将自定义颜色设置为选定的行?

[英]NSTableRowView/NSTableCellView how to set custom color to selected row?

I am trying to implement custom row color when table row is selected. 我正在尝试在选择表行时实现自定义行颜色。

-(void)tableViewSelectionDidChange:(NSNotification *)notification{


    NSInteger selectedRow = [_mainTable selectedRow];

    NSTableCellView *cell = [_mainTable rowViewAtRow:selectedRow makeIfNecessary:NO];

    cell.layer.backgroundColor = [NSColor redColor].CGColor;

    NSLog(@"selected");
}

But this is not working. 但这不起作用。 I find that Apple documentation very confusing (maybe I am wrong). 我发现Apple文档很混乱(也许我错了)。 I am not experienced with Mac programming. 我对Mac编程没有经验。

Can someone suggest any solution? 有人建议任何解决方案? Basically I need that selection Color to be transparent. 基本上我需要选择颜色是透明的。

Solution

This should be done by subclassing NSTableRowView and then returning your subclass in with the NSTableView delegate method 这应该通过NSTableRowView然后使用NSTableView委托方法返回子类来完成
-(NSTableRowView*)tableView:(NSTableView *)tableView rowViewForRow:(NSInteger)row

Subclassing NSTableRowView provides much more flexibility when modifying your row view. 在修改行视图时,子类化NSTableRowView提供了更大的灵活性。 Returning your subclass in the NSTableView delegate method above will also automatically remove the background selection color when clicking from one row to the next (which is an open issue in the other answer provided). 在上面的NSTableView委托方法中返回您的子NSTableView也会在从一行到另一行的单击时自动删除背景选择颜色(这是在提供的另一个答案中的一个未解决的问题)。


Steps 脚步

First, subclass NSTableRowView and override drawSelectionInRect to change its background color when selected: 首先,子类NSTableRowView并覆盖drawSelectionInRect以在选择时更改其背景颜色:

@implementation MyTableRowView

- (void)drawSelectionInRect:(NSRect)dirtyRect
{
    [super drawSelectionInRect:dirtyRect];
    [[NSColor yellowColor] setFill];
    NSRectFill(dirtyRect);
}

Next, return your subclassed row view using the rowViewForRow NSTableView delegate method: 接下来,使用rowViewForRow NSTableView委托方法返回子类行视图:

- (NSTableRowView*)tableView:(NSTableView *)tableView rowViewForRow:(NSInteger)row
{
    static NSString* const kRowIdentifier = @"MyTableRow";
    MyTableRowView* myRowView = [tableView makeViewWithIdentifier:kRowIdentifier owner:self];
    if (!myRowView) {
        myRowView = [[MyTableRowView alloc] initWithFrame:NSZeroRect];
        myRowView.identifier = kRowIdentifier;
    }
    return rowView;
}

Using this approach, you can also easily override other elements like the separator color. 使用此方法,您还可以轻松覆盖其他元素,如分隔符颜色。 To do this, override the drawSeparatorInRect method in your NSTableRowView subclass like so: 为此,请覆盖NSTableRowView子类中的drawSeparatorInRect方法,如下所示:

- (void)drawSeparatorInRect:(NSRect)dirtyRect
{
    // Change the separator color if the row is selected
    if (self.isSelected) [[NSColor orangeColor] setFill];
    else [[NSColor grayColor] setFill];
    // Fill the seperator
    dirtyRect.origin.y = dirtyRect.size.height - 1.0;
    dirtyRect.size.height = 1.0;
    NSRectFill(dirtyRect);
}

Resources 资源

Overriding NSTableRowView display settings https://developer.apple.com/reference/appkit/nstablerowview 覆盖NSTableRowView显示设置https://developer.apple.com/reference/appkit/nstablerowview

NSTableview rowViewForRow delegate method https://developer.apple.com/reference/appkit/nstableviewdelegate/1532417-tableview NSTableview rowViewForRow委托方法https://developer.apple.com/reference/appkit/nstableviewdelegate/1532417-tableview

first set tableview selection highlight style to 首先设置tableview选择高亮样式

 NSTableViewSelectionHighlightStyleNone

then in your tablView delegate implement 然后在你的tablView委托工具中

tableView:shouldSelectRow:

and write this code inside it: 并在其中编写此代码:

NSTableViewRow *row= [_mainTable rowViewAtRow:selectedRow makeIfNecessary:NO];
row.backgroundColor = [your color];
return YES;

read these also https://developer.apple.com/library/mac/documentation/Cocoa/Reference/NSTableViewDelegate_Protocol/index.html#//apple_ref/occ/intfm/NSTableViewDelegate/tableView:rowViewForRow : 阅读这些也https://developer.apple.com/library/mac/documentation/Cocoa/Reference/NSTableViewDelegate_Protocol/index.html#//apple_ref/occ/intfm/NSTableViewDelegate/tableView:rowViewForRow

for selection style https://developer.apple.com/library/mac/documentation/Cocoa/Reference/ApplicationKit/Classes/NSTableView_Class/index.html#//apple_ref/occ/instp/NSTableView/selectionHighlightStyle 选择样式https://developer.apple.com/library/mac/documentation/Cocoa/Reference/ApplicationKit/Classes/NSTableView_Class/index.html#//apple_ref/occ/instp/NSTableView/selectionHighlightStyle

This is to set the custom color to the selected row and also the highlighted text color. 这是将自定义颜色设置为选定的行以及突出显示的文本颜色。 The output should look something like this, 输出应该看起来像这样,

在此输入图像描述

In the above screenshot, we are doing 在上面的截图中,我们正在做

  • Setting the background selected color to white 将背景选定颜色设置为白色

  • Adding the corner radius 添加角半径

  • Changing the text color to blue 将文本颜色更改为蓝色

  • Adding the blue stroke color 添加蓝色笔触颜色

You can do a lot more customization but this answer covers above-mentioned points. 你可以做更多的定制,但这个答案涵盖了上述几点。

1. Start with subclassing NSTableRowView 1.从子类化NSTableRowView开始

class CategoryTableRowView: NSTableRowView {

override func drawSelection(in dirtyRect: NSRect) {
    if selectionHighlightStyle != .none {
        let selectionRect = bounds.insetBy(dx: 2.5, dy: 2.5)
        NSColor(calibratedRed: 61.0/255.0, green: 159.0/255.0, blue: 219.0/255.0, alpha: 1.0).setStroke()
        NSColor(calibratedWhite: 1.0, alpha: 1.0).setFill()
        let selectionPath = NSBezierPath(roundedRect: selectionRect, xRadius: 25, yRadius: 25)
        selectionPath.fill()
        selectionPath.stroke()
    }
  }
}

2. Return custom CategoryTableRowView() in the NSTableViewDelegate method 2.在NSTableViewDelegate方法中返回自定义CategoryTableRowView()

func tableView(_ tableView: NSTableView, rowViewForRow row: Int) -> NSTableRowView? {
      return CategoryTableRowView()
}

3. Make sure you have selectionHighlightStyle to regular in your ViewController class 3.确保在ViewController类中定期使用selectionHighlightStyle

override func viewDidLoad() {
     super.viewDidLoad()
     self.tableView.selectionHighlightStyle = .regular
}

4. To set the textColor, create a subclass of NSTableCellView 4.要设置textColor,请创建NSTableCellView的子类

class CategoryCellView: NSTableCellView {

@IBOutlet weak var categoryTextField: NSTextField!

override var backgroundStyle: NSView.BackgroundStyle {
    willSet{
        if newValue == .dark {
            categoryTextField.textColor = NSColor(calibratedRed: 61.0/255.0, green: 159.0/255.0, blue: 219.0/255.0, alpha: 1.0)
        } else {
            categoryTextField.textColor = NSColor.black
        }
    }
  }
}

override the backgroundStyle property and set the desired color for the text. 覆盖backgroundStyle属性并为文本设置所需的颜色。

Note: In my case, I have a custom cell which has a categoryTextField outlet.So to set the text color I use: categoryTextField.textColor = NSColor.black 注意:在我的情况下,我有一个自定义单元格,它有一个categoryTextField outlet.So来设置我使用的文本颜色: categoryTextField.textColor = NSColor.black

5. Set custom class inside storyboard 5.在故事板中设置自定义类 在此输入图像描述

I hope this helps. 我希望这有帮助。 Thanks. 谢谢。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM