对于 iOS 开发者来说,面对 app 盗版,最大的问题不是技术破解,反而是越来越多的 Apple ID 共享盗版,有的人可能会说这样的盗版就相当于是“试用”了,喜欢的人自然会去入正……但实际上,由于一分钱共享账号盗版的存在,导致无数独立开发者最终走向了投简历。
总之,去年,Surge 的作者[……]
苹果新出的用于代替OC的高级编程语言!
对于 iOS 开发者来说,面对 app 盗版,最大的问题不是技术破解,反而是越来越多的 Apple ID 共享盗版,有的人可能会说这样的盗版就相当于是“试用”了,喜欢的人自然会去入正……但实际上,由于一分钱共享账号盗版的存在,导致无数独立开发者最终走向了投简历。
总之,去年,Surge 的作者[……]
在 iOS 上,如果我们要一个 View 显示阴影,那么基本上是这么做的:
|
1 2 3 4 5 |
self.view.layer?.shadowColor = NSColor.black.cgColor self.view.layer?.shadowOpacity = 0.1 self.view.layer?.shadowOffset = CGSize(width: 0, height: 0) self.view.layer?.shadowRadius = 3 self.view.layer?.masksToBounds = false |
不过,到了 macOS 上,这样就不灵了——没有任何效果。
答案在于 macOS 上如果你想要给一个 View 使用 [crayon-6900e19[……]
一般情况下,你不需要了解这些内容。
在极少数情况下,你的app可能需要去获取用户按下的按键信息,比如盗号木马 开发一款输入法。只有这样你才能给用户提供候选。
怎么在 macOS 下创建一个输入法,我在Swift 使用 InputMethodKit 写输入法这篇文章中有详细的说明,这里略过[……]
在开发落格输入法 macOS 版本的时候,我遇到了这么一个难题,那就是窗口优先级的问题。在之前 如何让 NSWindow 显示在不同的 Space 或者 Screen 中 这篇文章中我提到了自己实现了落格输入法的候选栏,其实是用一个 NSWindow
在开发落格输入法的时候,我遇到了这么一件事情,就是作为候选栏的窗口会在屏幕边缘的时候超出屏幕去!所以,在显示窗口的时候我根据坐标做了额外的检查:
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
if visiableCandidateCells.isEmpty { if let screenframe = NSScreen.main?.visibleFrame { if screenframe.width < location.x + size.width { location.x -= location.x + size.width - screenframe.width } } } else { if let screenframe = NSScreen.main?.visibleFrame { if screenframe.width < location.x + self.window!.frame.size.width { location.x -= location.x + self.window!.frame.size.width - screenframe.width } } } if location.y < 50 { location.y += 35 + 35 } |
总之,就是说如果坐标算上自己的宽度超过了屏幕的宽度,就把它挪回来。
但是,这样[……]
在写落格输入法 Mac 版的过程当中,我遇到了这么一个问题,系统的候选条 API 年久失修,很多功能 API 存在但根本无效,比如:
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
/*! @method @abstract Sets the "style" attributes for the candidates window. The keys for the attributes dictionary and the values are: NSFontAttributeName (value = NSFont) Setting the font attribute sets the font that is used to draw Candidates. It does not effect the selection keys which are always drawn in the same font. Note that to set the font size you should use this key/value pair. IMKCandidatesOpacityAttributeName (value = NSNumber with a float value between 0 and 1). Sets the opacity level to transparent (0.0) to completely opaque (1.0). The default opacity is 1.0. This constant is declared above. NSForegroundColorAttributeName (value = NSColor) Sets the text color used for the candidate text. By default it is black. NSBackgroundColorDocumentAttribute (value = NSColor). Set the background color that is drawn behind the candidate text. IMKCandidatesSendServerKeyEventFirst (value = NSNumber). NO (default) gives the candidate window first chance at key events. YES causes events to first be routed to the current IMKInputController. In that case, if the event is not handled, it will then be sent to the candidate window. */ open func setAttributes(_ attributes: [AnyHashable : Any]!) |
这个方法是用来设置候选条风格的,里边除了默认的[crayon-6900e19fb43051343[……]
在 Swift 中,大家经常会用 URL 来初始化一个路径,比如网页的链接。比如这样:
|
1 2 3 4 5 6 |
…… @IBAction func goToWeb(_ sender: NSButton) { let url = URL(string: "https://v2mm.tech/category/80/logcg-input-method") NSWorkspace.shared.open(url!) } …… |
当用户点击按钮(比如说这个帮助按钮),那么一下子就帮用户打开默认的浏览器,并打开指定的页面(这里是个论坛)。
那么,如果你的链接是这样的[……]
众所周知,落格输入法不需要获取“完全访问权限”,所以根据苹果的权限,自然就无法播放按键音了。
不过,最近的落格输入法更新中加入了这一功能——在后续的版本中甚至可以加入按键震动了。然而我还是无需获取“完全访问权限”。
那么,我是怎么做到的呢?
iOS 里的声音和震动
其实是同一回事[……]
通常 UILabel 是用来在应用界面显示简单提示文字的,不过,我们也可以用它来显示一些大段的不需要用户参与编辑的内容——比如阅读的 tweet
这些内容有一个特点就是需要支持富文本。 [crayon-6900e19fb4b4a26989[……]
UITableViewController 是iOS开发中相当常用的一个空间了,它的 cell 很早就可以支持自适应高度,或者说是 动态高度。在开发中,如果cell里布局了复杂的内容——比如连图带字的一条微博。那么这个时候动态的自动的高度就显得很有用了——总不用你自己去计算[……]
做开发者肯定有过这样的烦恼:版本号提交错了!
编译和测试的版本多了,难免提交的时候才发现版本号搞错了。要不就是后台版本号正确,前台的版本号忘记更改。其实,可以让前台自动获取后台的版本号数据,比如这样:
|
1 2 |
let info = Bundle.main.infoDictionary! version.text = "Version \(info["CFBundleShortVersionString"]!) (build \(info["CFBundleVersion"]!))" |
后台的版本号[……]
一年前,我在 git 上发布了一个用 Swift 实现的栈,一共有两个版本。因为 Swift 自身并没有实现这个东西——尽管官方的教程中泛型的部分就是用这个栈举的例子。
也许是人家觉得这个太简单了吧
总之,这次我又来玩这个东西了,因为 HMM 的 Viterbi 算法需要做修剪,不然路径太多无谓[……]
众所周知,在 iOS 平台上自从 8.0 版本开始,可以为 iOS 开发第三方的输入法键盘了,而这些键盘可以被放在 AppStore 销售了,不过,同时也有着十分严格的权限规则。
对此,苹果为第三方的键盘设计了两种权限,一种是最小的,只有最基本的键盘功能的权限、另一种则相对较多,键盘获取了“完[……]
今天遇到一个奇怪的问题,程序运行一点问题都没有但终端报错如下
|
1 |
Could not load the "" image referenced from a nib in the bundle with identifier "com.xxx.xxx" |
其实就是题目上的错误,这个问题看上去挺简单——不就是引用的图片丢失了么……
其实不然,由于名字是 ""
最近给落格输入法加入了一个叫做“对数云”的东西,其实不难,比使用 iCloud Document 要简单,不过网上的资料不太多,你通过那些上手教程来现充应该不是问题,但想要提升用户体验,就不是那么容易了。这里我们就一起来看看,怎么样才能让 CloudKit 运行得更畅快。
cmph 的全称是 C Minimal Perfect Hashing Library ,是一个很著名的用 C 写成的最小完美哈希库,什么是完美哈希?
这里我们不讲原理,你只需要知道传统的哈希有冲突,我们需要靠各种算法来处理冲突就可以了,对于哈希,总是需要一个表,这个表里预留了很多位置[……]
很多时候,我们需要在字符串中执行查找,以判断过滤指定的内容出来。比如过在落格输入法当中,就需要用辅码过滤出需要的候选词。
一般来说,查找和对比肯定是数字来的最快,不过在词库上总不能把所有的词汇都转换为数字(虽然理论上可行……)在字符串的搜索上,我们有很多种办法来实现,这里我就说一下我自己的思路[……]