首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >问答首页 >NSTableView在macOS大Sur下交替行色的视觉小故障

NSTableView在macOS大Sur下交替行色的视觉小故障
EN

Stack Overflow用户
提问于 2021-02-03 00:08:19
回答 3查看 337关注 0票数 2

我使用的是NSTableViewusesAlternatingRowBackgroundColors设置为true

只要我

and

  • Set
  1. 添加许多列,例如,将单元格间距高度添加到大于0

的位置

该表显示了一个视觉故障,其中交替行的高度分布不均匀:

这只发生在macOS大苏尔。macOS Mojave和macOS Catalina工作得很好。我使用最新的Xcode 12.4尝试了几乎所有设置和样式的组合。

我的ViewController相当简单:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
class ViewController: NSViewController {

    @IBOutlet weak var tableView: NSTableView!

    override func viewDidLoad() {
        super.viewDidLoad()

        for columnIndex in 0..<15 {
            let tableColumn = NSTableColumn(identifier: NSUserInterfaceItemIdentifier(rawValue: "\(columnIndex)"))
            tableColumn.title = "CustomColumn \(columnIndex)"
            tableColumn.width = 150
            tableView.addTableColumn(tableColumn)
        }
    }
}

此外,Interface中的NSTableView配置也相当枯燥,除了调整后的单元间距高度:

如果有人能确认这一问题,并可能分享任何解决办法,那就太好了。

您可以在https://github.com/fheidenreich/table-test找到一个演示项目。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2021-08-13 02:14:29

在WWDC'21期间,我和一位苹果工程师谈过这个问题,他证实了这个问题,并提出了一个有趣的解决办法:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
override func drawBackground(inClipRect clipRect: NSRect)
{
   super.drawBackground(inClipRect: clipRect)
}

这将触发一个不同的代码路径,在AppKit中进行较少的优化,并防止问题出现。

我还用更多的例子更新了我对苹果的反馈,似乎这个问题最终通过macOS蒙特雷12.0Beta5 (21A5304g)解决了。

票数 1
EN

Stack Overflow用户

发布于 2021-02-16 15:02:09

我在MacOS 11.0和MacOS 11.2.1上测试了示例项目,但是无法重现故障。但这并不意外,因为代码本身看起来很好。

可能是中间MacOS版本或特定硬件软件组合的问题。如果问题仍然存在,可以尝试通过子类NSTableView来手工绘制背景。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
class TableViewEx: NSTableView {
    
    public override func drawBackground(inClipRect clipRect: NSRect) {
        
        guard usesAlternatingRowBackgroundColors else {
            super.drawBackground(inClipRect: clipRect)
            return
        }
        
        backgroundColor.setFill()
        clipRect.fill()
        let effectiveRowHeight = rowHeight + self.intercellSpacing.height
        
        // This color requires 10.14+. There is an older, deprecated property on NSColor to get this value if needed.
        let altColor = NSColor.alternatingContentBackgroundColors.last ?? backgroundColor
        altColor.setFill()
        
        let rowIndex = Int((clipRect.minY / effectiveRowHeight).rounded(.down))
        
        for i in rowIndex..<Int.max {
            if i % 2 == 0 { continue }
            let rect = NSRect(
                x: clipRect.minX,
                y: CGFloat(i) * effectiveRowHeight,
                width: clipRect.width,
                height: effectiveRowHeight
            )
            rect.fill()
            if rect.maxY >= clipRect.maxY { break }
        }
    }
}

但我不会感到惊讶,因为它仍然在那里,即使在压倒性平局。我不认为Cocoa代码与建议的代码有那么大的不同,所以它可能会在堆栈中将bug呈现得更低。

票数 2
EN

Stack Overflow用户

发布于 2021-05-26 19:58:32

对于那些选择在ClipRect中自己绘图的人来说,这是最好的方法。它有几个优点:

  1. 只在tableView的实际NSRowView实例不出现的那一部分绘制行,因此效率要高得多。

  1. 当你滚动“过去的边缘”的tableView (使边缘开始“橡皮筋”),现代NSTableView风格不画任何东西在“橡胶带区”。这一做法遵循了该公约。如果不这样做,实际的表行将停止绘制,因为您将从边缘拖动,但是我们正在绘制的假表行不会,这看起来会很奇怪。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
override func drawBackground(inClipRect clipRect: NSRect)
{
    backgroundColor.setFill()
    clipRect.fill()
        
    let effectiveRowHeight: CGFloat = rowHeight + self.intercellSpacing.height
        
    let altColor: NSColor = NSColor.alternatingContentBackgroundColors.last ?? backgroundColor
    altColor.setFill()
    
    // Don't draw rows that the tableView already has
    let rowIndex = max(Int((clipRect.minY / effectiveRowHeight).rounded(.down)), numberOfRows)
        
    // How many rows do we need to draw?
    // Don't draw rows in the "rubber banding" zone if the user scrolls down past the end of the table, or horizontally off the side.
    // That matches how modern NSTableView draws NSRowView instances, so the table will look uniform during "rubber-banding"
    let maxRows = Int((self.bounds.size.height/effectiveRowHeight).rounded(.up))
    let tableOrigin: CGFloat = bounds.origin.x
    let tableWidth: CGFloat = bounds.size.width
        
    guard rowIndex < maxRows else {
        return
    }
        
    for i in rowIndex ..< maxRows
    {
        if i % 2 != 0
        {
            let rect = NSRect(x: tableOrigin, y: (CGFloat(i) * effectiveRowHeight), width: tableWidth, height: effectiveRowHeight)
            rect.fill()
        }
    }
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/66023486

复制
相关文章
如何智能地在每个数字中间加一个逗号?
问题链接: https://www.zhihu.com/question/412135686
Qt君
2023/03/17
9010
如何智能地在每个数字中间加一个逗号?
在windows下详解:大端对齐和小端对齐
计算机的内存最小单位是什么?是BYTE,是字节。 一个大于BYTE的数据类型在内存中存放的时候要有先后顺序。
黑泽君
2018/10/11
3.6K0
如何只用 30 行代码在 JavaScript 中创建一个神经网络
在这篇文章,我将会展示给你如何使用 Synaptic.js 创建并训练一个神经网络,它允许你在 Node.js 和浏览器中进行深度学习。
疯狂的技术宅
2019/03/27
1.1K0
如何只用 30 行代码在 JavaScript 中创建一个神经网络
在 Golang 中实现一个简单的Http中间件
本文主要针对Golang的内置库 net/http 做了简单的扩展,通过添加中间件的形式实现了管道(Pipeline)模式,这样的好处是各模块之间是低耦合的,符合单一职责原则,可以很灵活的通过中间件的形式添加一些功能到管道中,一次请求和响应在管道中的执行过程如下
全球技术精选
2021/08/20
5530
如何真正成为一个在路上的Linuxer
Linux是工具,更像一个信仰。 写在前面 本文目的不是教你如何成为一个真正的Linuxer,也没有能力教你成为一个真正的linuxer,而是通过笔者的一些想法试图指引你真正踏上学习linux之路,成为一个真正意义的在路上的linuxer。 这有什么区别?是的,一个成熟的Linuxer能够游走于表面的命令提示符与内部代码细节实现之间,他们甚至也是linux内核源码的贡献者。这样 的能力是人人都期望的,但是事实是绝大部分在学习linux的人都还没能达到那样高深莫测的水准。而那绝大部分人当中又有很大一部分人
FB客服
2018/02/06
2.1K0
如何真正成为一个在路上的Linuxer
如何检测一个元素是否在 vector 中
可以使用头文件 <algorithm> 里的方法 std::find, #include <algorithm> #include <vector> vector<int> vec; if (std::find(vec.begin(), vec.end(), item) != vec.end()) do_this(); else do_that();
ClearSeve
2022/02/10
1.9K0
android 在一个应用中启动另一个应用android 在一个应用中启动另一个应用
在程序开发过程当中,常遇到需要启动另一个应用程序的情况,比如在点击软件的一个按钮可以打开地图软件。
一个会写诗的程序员
2018/08/20
5200
​2021-03-09:在一个数组中,一个数左边比它小的数的总和,叫数的小和,所有数的
2021-03-09:在一个数组中,一个数左边比它小的数的总和,叫数的小和,所有数的小和累加起来,叫数组小和。求数组小和。例子: 1,3,4,2,5,1左边比1小的数:没有,3左边比3小的数:1,4左边比4小的数:1、3,2左边比2小的数:1,5左边比5小的数:1、3、4、 2,所以数组的小和为1+1+3+1+1+3+4+2=16 。
福大大架构师每日一题
2021/03/09
5770
​2021-03-09:在一个数组中,一个数左边比它小的数的总和,叫数的小和,所有数的
如何优雅地实现判断一个值是否在一个集合中?
如何判断某变量是否在某个集合中?注意,这里的集合可能并不是指确定的常量,也可能是变量。
编程珠玑
2021/01/05
1.8K0
在 docker 中搭建一个 sonarqube
如果你本地的9000端口,已经被portainer之类的占用了,可以将映射出来的端口改一个端口号,例如9001。
前Thoughtworks-杨焱
2021/12/07
4630
在 docker 中搭建一个 sonarqube
在 Python 中如何快速创建一个只读字典?
不少人喜欢在 Python 项目中,使用字典来存放各种数据。虽然这不是一个好习惯,但是对于少量数据来说,用字典无疑是最简单方便的做法。但前提是,不要一不小心把字典里面的值给覆盖了。
青南
2020/09/14
3.4K0
在 Python 中如何快速创建一个只读字典?
在RenderTransform上叠加一个ScaleAt
代码很简单,就是在缩放时,获取鼠标对元素的相对坐标,调用ScaleAt,然后添加到它现有的RenderTransform中
黄腾霄
2020/06/10
5470
在iOS上面写一个Blockchain
区块链是什么,到底可以解决什么问题? 简单来说区块链就是一个不需要第三方认证的加密账本交易系统。 举个例子:老王租了老李一个房子,他找中介签房屋合同。 老王拉来了中介小张作为第三方见证人,签署了一个简单合同: 来自 老王 给 老李 房屋出租 时间:某年某月 老王签名 :老王 老李签名:老李 小张签名: 小张 一式三份,人手一张,基于这份合同: 1,此时老王,老李,都无法否认该合同的存在。因为第三方小张这里有一份存根可以证明
rectinajh
2018/05/17
6750
中国有两个“造字”故事,一个在远古传说,一个在虚拟现实
回顾2021,虚拟与现实的次元壁被不断打破。你或许想象不到,就连输入法,也“闯入”了虚拟世界。
用户2908108
2022/01/05
3691
中国有两个“造字”故事,一个在远古传说,一个在虚拟现实
如何使用机器学习在一个非常小的数据集上做出预测
朴素贝叶斯是一系列简单的概率分类器,它基于应用贝叶斯定理,在特征之间具有强或朴素的独立假设。它们是最简单的贝叶斯模型之一,但通过核密度估计,它们可以达到更高的精度水平。
deephub
2021/07/23
1.3K0
如何使用机器学习在一个非常小的数据集上做出预测
关于hashmap在多线程环境下的一个小实验
我们都知道hashmap是非线程安全的,平时我们经常是在单线程环境下使用这个类的,现在我们模拟一个多线程环境,并发操作访问一个hashmap实例,看看会出现什么匪夷所思的问题。 运行如下程序: import java.util.HashMap; public class TestMap { private HashMap map = new HashMap(2, 0.5f); public TestMap() { Thread t1 = new Thread() { public void r
java达人
2018/01/31
1.2K0
关于hashmap在多线程环境下的一个小实验
在eclipse当中如何做一个jsp的helloWorld?
做jsp的实验步骤非常简单。在eclipse当中,右键点击代表你WebModule的根目录的WebContent。new/jsp 即可。
马克java社区
2021/07/09
6090
Android 在一个APP里打开另一个APP
不知道你们有没有注意过,每次打开一些软件的时候都会有广告引导页,有时候手滑点到了,会有进入手机上的另一个APP,这有没有引起你的注意呢?
晨曦_LLW
2020/09/25
2.7K0
在JavaScript中,如何创建一个数组或对象?
1:使用数组字面量(Array Literal)语法,使用方括号 [] 包裹元素,并用逗号分隔:
王小婷
2023/10/23
4220
在JavaScript中,如何创建一个数组或对象?
idea在一个窗口打开多个项目
使用场景:Spring-cloud框架下的项目一般都有多个子项目,就像我们项目由6个子项目,每个子项目单独更新很麻烦,还有相互之间的依赖,所以就把所有的子项目都放到一个文件夹下,只要更新所有的子项目都会更新,依赖也会更新。这样就很方便管理。
赵哥窟
2022/05/13
4.7K0
idea在一个窗口打开多个项目

相似问题

我如何在一行中对齐这三个div,一个在左边,一个在中间,一个在右边?

20

在同一行中垂直对齐3个元素,一个在左边,一个在中间,一个在右边。

50

颤振:如何在左边添加一个小部件,在一行中间添加另一个小部件。

417

如何管理小部件行(抖动)--一个在左边,另一个在右边

12

一行对齐两个小部件,一个在中间,另一个在右边。

32
添加站长 进交流群

领取专属 10元无门槛券

AI混元助手 在线答疑

扫码加入开发者社群
关注 腾讯云开发者公众号

洞察 腾讯核心技术

剖析业界实践案例

扫码关注腾讯云开发者公众号
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
查看详情【社区公告】 技术创作特训营有奖征文