Matrix 是少数派的写作社区,我们主张分享真实的产品体验,有实用价值的经验与思考。我们会不定期挑选 Matrix 最优质的文章,展示来自用户的最真实的体验和观点。
文章代表作者个人观点,少数派仅对标题和排版略作修改。
不久前和老同学的聚会中他问我:「都说 iOS 很好用,那它到底好在哪里?」我想了一下说了一句:「软件生态。」正好最近我的文章阅读流程所有代码都写完了,那么不如就通过这篇文章来看看我是如何使用 iOS 的软件生态来阅读文章。
通过这一年时间的磨合调整最后构建出来的阅读流程如图所示:
微信公众号是我的主要信息来源,每天早上起床会先刷一眼微信公众号的文章推送。对于有价值的文章我会将它们保存到我的笔记软件中。我将这个过程分为三步对应着图左的三个框框。依次为:内容摘抄、添加标签和任务、开始阅读。
为什么要分成三个过程?因为我的碎片化时间比较多,在多数情况下不能一次性完成这三个步骤,但是如果把它们切割开,我就可以利用碎片化时间的优势,有一点时间我就做一个或者两个的步骤。
如何很方便地将文章内容复制粘贴到 Drafts 中进行处理?从尾部选中文本一直拉到头部吗?不对,我们可以使用 Bookmarklet 来实现这个功能。这个做法是受一个朋友的启发,他之前在群里说年纪大了,现在看文章都懒得看图片了,都是直接复制纯文本出来看的。而我所阅读的 95% 的文章都是不配图也可以看的,所以只要将文章的文字稿复制粘贴给 Drafts 这第一步「内容摘抄」就算是完成了。
原理:通过 document.body.innerText 获取文章内容,使用 copyToClipboard 函数将文章内容拷贝到剪切板,最后使用 window.open 打开 Drafts 的 URL Scheme 激活 paste action,用剪切板的内容创建新草稿。
技术要点:Bookmarklet 和 URL Scheme。
相关阅读:
具体实现:任意收藏一个网页,然后编辑网页地址改成下面这段 JavaScript 代码。这段代码不仅仅是将文章内容复制粘贴到 Drafts,而且还会在文章最后一行添加本文的 Markdown 链接,方便以后直接找到原文。对于微信公众号的文章会删除底部的推荐阅读和阅读原文等匹配内容。最后对 Markdown 链接的标题也会做一定的处理,删除 - | 之后的文字。
javascript: (function() {
function copyToClipboard(text) {
if (window.clipboardData && window.clipboardData.setData) {
return clipboardData.setData("Text", text);
} else if (document.queryCommandSupported && document.queryCommandSupported("copy")) {
var textarea = document.createElement("textarea");
textarea.textContent = text;
textarea.style.position = "fixed";
document.body.appendChild(textarea);
textarea.select();
try {
return document.execCommand("copy");
} catch(ex) {
console.warn("Copy to clipboar failed.", ex);
return false;
} finally {
document.body.removeChild(textarea);
}
}
}
copyToClipboard(document.body.innerText.replace(/(推荐阅读|喜欢此内容的人还喜欢)(.*\n)+/g, "").replace(/.*阅读原文.*/g,'').replace(/[\r\n]{3,}/g, "\n\n") + "\n" + '[' + document.title.replace(/ \/ Twitter/, '').replace(/^【.*】/, '').replace(/(|.*$|\|.*$)/, '').replace(/^\(.*\)/, '').replace(/-.*$/, '').replace(/(!|?|\?|\!)/g, '').replace(/_.*$/, '').trim() + '](' + window.location.href + ')');
url = 'drafts4://x-callback-url/runAction?action=paste';
window.open(url,'_self');
})();
打开 Drafts 新建一个 action,命名为 paste,添加 URL Action Step:
drafts4://x-callback-url/create?text=[[clipboard]]
为什么不直接用 Bear 的共享操作收藏而是先把文章摘抄到 Drafts 中?原因如下:
技术要点:JavaScript 和 URL Scheme
相关阅读:从 OmniFocus 认识 Drafts 的 Prompt 用法
实现方法:创建一个名为「笔记添加标签」的 action,选择 Prompt,Key 保持默认的 prompt 不变,Title 改为:「选择标签」,Buttons 填入你的 Bear 标签,使用半角的 | 间隔开。
我的 Buttons 参考如下:
600 清单|400 兴趣/405 绘图设计|400 兴趣/410 单车骑行|400 兴趣/450 财务知识|400 兴趣/470 投资机会|400 兴趣/480 生财有术| 500 课余/001 政治体制|500 课余/004 课外知识|010 日记/020 恋爱日记|010 日记/011 生活日记|010 日记/013 社会时事|800 语录摘抄|900 演讲稿
添加 Script Action Step 粘贴如下代码:
// 默认内容来自文稿 否则从剪切板读取
if (draft.content){
text = draft.content;
}else{
text = getClipboard();
}
// 微信公众号文章处理
temp = text.split("\n");
if(temp[temp.length-1].match(/mp.weixin.qq.com/g)){
head = temp;
// 删除发布日期
head = head.slice(0,1);
temp = temp.slice(3);
if (temp[0].length == 0)
temp = temp.slice(1);
// 删除收录分类
if (temp[0].match(/收录/))
temp = temp.slice(3);
if (temp[0].length == 0)
temp = temp.slice(1);
temp = head.concat(temp);
}
head = temp[0];content = temp.slice(1).join("\n");
// 删除行首行末空格
head = head.trim();content = content.trim();
// 替换中文引号 删除井号空格
content = content.replace(/#/g,'');
content = content.replace(/“/g,'「');
content = content.replace(/”/g,'」');
content = content.replace(/[\u00A0]/g,'');
// 当有两个以上换行合并为两个
content = content.replace(/\n{2,}/g, '\n\n');
draft.defineTag("head", head);
draft.defineTag("content", content);
添加 URL Action Step 粘贴如下 URL:
bear://x-callback-url/create?title=[[head]]&text=[[content]]&tags=[[prompt_button]]&x-success=drafts4://
将这个「笔记添加标签」的动作添加到键盘上方的快捷工具栏中,可以像我一样命名为「🏷️」,这样不仅一眼就能看出这个快捷键的用途而且还能节省空间,在屏幕限定的宽度里放下更多的动作。
运行这个快捷动作,选择「400 兴趣 / 480 生财有术」就会对文章进行文字处理之后跳转到 Bear 新建这样一篇笔记并给它添加 #400 兴趣 / 480 生财有术# 的标签。
至于从剪切板读取内容,这个是为了保存 Telegram Solidot 频道或者类似的时事内容设计的。例如从 Solidot 频道复制消息内容,回到 Drafts 点击工具栏上的「🏷️」选择「010 日记 / 社会时事」即可直接跳转到 Bear 创建笔记。
添加任务这个操作是以前看《用 GTD 的方法结束稍后读》这篇文章学习到的,我使用了这些年下来对这个方法非常满意,再也不会担心遗忘阅读摘抄的文章了。但是如果你先把文章内容放在 Drafts 不动,等自己有空闲时间的时候先给 Drafts 里的文章打上标签发送给 Bear。macOS 上的 Bear 经过几秒之后同步过来就可以直接开始阅读,跳过添加任务的这个步骤。
原理:笔记添加到 Bear 之后会分配到每篇文章独有的一个 ID,而 Bear 也有提供捷径的 API 接口,可以通过剪切板传入 ID 获取文章内容,拆分文本取出第一行的标题,构造 URL Scheme 添加 OmniFocus 阅读任务。
相关阅读:OmniFocus 的 URL Schemes 用法
捷径下载:Bear to OmniFocus
使用方法:先长按笔记点击「复制标记的标志符」,再次长按选择共享,选择「Bear to OmniFocus」捷径即可,所以总共需要长按笔记两次。
在 macOS 上使用 WebDavNav 搭建本地 WebDAV 环境,具体方法可参考 使用 WebDavNav 同步 OmniFocus 数据库。然后在 iOS 和 macOS 两端的 OmniFocus 客户端都在局域网内同步,这是最快的同步方案,没有之一。
现在阅读任务已经同步到了 OmniFocus 上,点击左下角的小图标或者使用快捷键 option+command+" 查看任务备注,点击即可通过 URL Scheme 跳转到对应的笔记。
接下来就是一边阅读一遍使用 PopClip 处理文段的事情了。我制作了一系列的 PopClip 扩展用于处理文本,可以在Apple-Automation/PopClip下载。
为了能更高效地处理文章段落内容,我使用 PopClip 制作了 一些插件 来完成这些重复性的枯燥的工作,所有插件都是调用地表最强的纯文本处理工具 sed 命令处理,如果你也是需要经常重复性地处理一些文本,非常建议学习一下 sed 命令的用法。
我在 learn-linux-command/gsed.md 也整理了很多的基础用法和具体实例可供参考学习。但是注意需要先在电脑上安装 GNU sed,安装命令如下:
brew install gnu-sed
➜ echo '这是一段**测试**文本\n这是**一**段**测试**文本\n这是**一段****测试**文本\n这是一段**测试****文本**\n**这是一段测试文本**\n这是一段测试文本\n- 这是一段测试文本'
这是一段**测试**文本
这是**一**段**测试**文本
这是**一段****测试**文本
这是一段**测试****文本**
**这是一段测试文本**
这是一段测试文本
- 这是一段测试文本
➜ echo '这是一段**测试**文本\n这是**一**段**测试**文本\n这是**一段****测试**文本\n这是一段**测试****文本**\n**这是一段测试文本**\n这是一段测试文本\n- 这是一段测试文本'|gsed 's/\*\*/::/g ; /^- / s//- ::/ ; /^- ::/ s/$/::/ ; /::/! s/^/::/ ; /^::/ s/$/::/ ;s/\(::\)\(.*\)\(::::\)\(.*\)\(::\)/::\2\4::/ ; s/::::$/::/g'
这是一段::测试::文本
这是::一::段::测试::文本
这是::一段测试::文本
这是一段::测试文本::
::这是一段测试文本::
::这是一段测试文本::
- ::这是一段测试文本::
首行开头添加 Markdown 四级标题标记,其余行合并为一行,去掉首行加粗标记,内容加粗转为高亮
2021年,投资什么行业?
我的建议是,大家可以重点关注消费、医疗、科技这三个行业。
可能有的人会说,这三个行业在2020年已经涨得很高了,还适合投资吗?决定要不要投,不仅要看行业的短期涨幅,还要看它们长期增长的逻辑。
从长期来看,这3个行业,还是有很大机会的。接下来我分开说:
先说说消费行业。
随着中国人均收入的增长,消费升级必然带动消费行业的增长。
#### 2021年,投资什么行业?
我的建议是,大家可以重点关注消费、医疗、科技这三个行业。可能有的人会说,这三个行业在2020年已经涨得很高了,还适合投资吗?决定要不要投,不仅要看行业的短期涨幅,还要看它们长期增长的逻辑。从长期来看,这3个行业,还是有很大机会的。接下来我分开说:先说说消费行业。随着中国人均收入的增长,消费升级必然带动消费行业的增长。
➜ echo '1 列表\n1.列表\n1、列表\n01 列表\n一、列表\n(1)列表'
1 列表
1.列表
1、列表
01 列表
一、列表
(1)列表
➜ echo '1 列表\n1.列表\n1、列表\n01 列表\n一、列表\n(1)列表'|gsed 's/^(.)/- / ; s/^.\( \|\.\|\、\|[0-9]\)/- /; s/- /- /'
- 列表
- 列表
- 列表
- 列表
- 列表
- 列表
选中行去掉所有换行符号合并为一行
我无论做任何事情,如果自己不熟悉,我都会从这句话开始入口:一切智慧都在历史当中。
然后,找做过这件事,并且做成的人,看他的书、读他的文章,基本能解决了解到90% 的信息。
一件事情,当你知道了 90% 的信息,其实就可以放心上路了,路上遇到问题,再去搜索、研究,解决掉。
这个方法,适用于任何人、任何行业、任何事情。
我无论做任何事情,如果自己不熟悉,我都会从这句话开始入口:一切智慧都在历史当中。然后,找做过这件事,并且做成的人,看他的书、读他的文章,基本能解决了解到90% 的信息。一件事情,当你知道了 90% 的信息,其实就可以放心上路了,路上遇到问题,再去搜索、研究,解决掉。这个方法,适用于任何人、任何行业、任何事情。
好了,我总结一下,如何抓住2021年的投资机会:
1、买小帮的的基金组合优于买指数基金,买指数基金优于炒股。
2、如果你一定要炒股,首先要学习投资股票的基础知识。如果暂时还没完全学懂,宁愿先投资基金。记住,不懂不投。
3、如果你想通过基金来投资,那么通过“小帮组合”买主动管理型基金,要好过买指数基金。
4、长期关注消费、医疗和科技这3个行业的投资机会,适当时机,可以买入持有。
最后,祝大家2021年投资顺利,多多赚钱,让自己的学习和思考,转化成口袋里的真金白银。
好了,我总结一下,如何抓住2021年的投资机会:
1. 买小帮的的基金组合优于买指数基金,买指数基金优于炒股。
2. 如果你一定要炒股,首先要学习投资股票的基础知识。如果暂时还没完全学懂,宁愿先投资基金。记住,不懂不投。
3. 如果你想通过基金来投资,那么通过“小帮组合”买主动管理型基金,要好过买指数基金。
4. 长期关注消费、医疗和科技这3个行业的投资机会,适当时机,可以买入持有。
最后,祝大家2021年投资顺利,多多赚钱,让自己的学习和思考,转化成口袋里的真金白银。
对于中文文本将半角符号变成全角符号,但是不会误伤 :// 链接中的冒号。
我说:“这是一段测试文本!你试试看效果怎么样?”
[少数派](https://sspai.com)
我说:「这是一段测试文本!你试试看效果怎么样?」
[少数派](https://sspai.com)
cats 插件实际上是指 cat -s 命令的效果而不是好多猫 😂,它会去掉所有空行。
15 年,我开始全职做淘宝,亏了一整年。
16 年实现几万盈利,17 年赚了四五十万,18 年实现 98 万的净利润。
19 年,除了淘宝主业以外,也开始做知识付费。这一年,淘宝实现净利润 220 多万,知识付费盈利 80 多万。
20 年,公司 4 月份第一次实现月利润突破百万。在刚刚过去的6月份,公司历史上第二次实现月利润破百万,全年上半年净利润突破 400 万。
15 年,我开始全职做淘宝,亏了一整年。
16 年实现几万盈利,17 年赚了四五十万,18 年实现 98 万的净利润。
19 年,除了淘宝主业以外,也开始做知识付费。这一年,淘宝实现净利润 220 多万,知识付费盈利 80 多万。
20 年,公司 4 月份第一次实现月利润突破百万。在刚刚过去的6月份,公司历史上第二次实现月利润破百万,全年上半年净利润突破 400 万。
用以上这些插件对「让能力变现,才是硬道理」这篇文章处理之后的效果如图所示。删除很多不必要的换行,有启发有价值的语句用高亮符号标记,删除尾部的广告。
这些笔记多数都是值得再次一读的,所以在 Bear 里我有个专门的复盘日记用于存储每天阅读文章的内链,但是 Bear 自带的复制笔记链接快捷键太难记了,我们可以先去偏好设置的键盘里设置一下新的快捷键。
我给「复制笔记的链接」设置了 control+c(copy link) 的快捷键,为什么不是更相近的 option+c 快捷键?因为被系统占用了。如法炮制也可以给「日期与时间」添加一个 command+d(date) 的快捷键来替换来原来的三个快捷键。
快捷键设置好了之后回到刚才阅读的文章,control+c 复制笔记内链,打开第一个标签第一条「复盘清单」笔记,标题回车,command+d 添加日期,command+l 转为列表,回车,command+v 粘贴内链,一篇文章的阅读历程到此结束。如果这篇文章值得以后再多看几眼,也可以使用 PopClip 的 Highlight 插件把这个内链高亮。
为什么我要额外花时间对文章段落格式化?最重要的原因就是如果这篇文章很有价值的话,我会把它打印出来就放在手边的书立栏里,能让我闲了的时候可以再翻翻看看。我使用带有 AirPrint 功能的 EPSON L4168 打印机来实现无线自动双面打印,打开 Bear 选择笔记导出 PDF 即可开始打印。
一般阅读的文章,可能是技术方面的参考文章也可能是整篇文章都在讲一个道理,技术文章阅读完了之后如果有价值会转为 Markdown 链接作为引用参考资料,道理类文章阅读完之后消化理解这个道理就足够了。
对于这类不需要保存到 Bear 中的文章只要把标题和链接添加到 OmniFocus 作为一个任务就够了,这里我使用捷径实现这个功能。为了方便调用,可以在设置 → 辅助功能 → 触控 → 轻点背面 → 轻点两下设置触发微信文章这个捷径。很多人说轻点两下有时候太灵敏有时候又没反应,我用了这么久总体来说属于一个还行的水平,希望以后能够改进做的更好吧。
捷径下载:微信文章
前面提到技术类的文章如果有参考意义,我会将其转换为 Markdown 链接作为引用写到文章里。那么具体是怎么实现呢?OmniFocus 中的任务都是可以导出 TaskPaper 格式的,我们只要处理一下这个 TaskPaper 转换成 Markdown 的形式就可以了。
但是 OmniFocus 中把任务拷贝为 TaskPaper 格式是没有快捷键的,我们需要先为它设置一个快捷键,我还是设置了和 拷贝 Bear 内链一样的 option+c 快捷键,因为如果选择 command+c 的话以后就不能复制任务里的文本了。
选中要转换的任务,按下 option+c 复制 TaskPaper 格式文本。
打开终端拖入下面这条命令,然后执行命令即可。第一条命令看看转换效果的,第二条命令才是我们实际要用的命令,从剪切板读取 TaskPaper 格式的任务,通过 sed 处理之后再替换回剪切板。
➜ pbpaste|sed '/^$/d ; s/^- /[/ ; s/ @.*)/](/ ; N ; s/\n// ; s/\x09// ; s/$/)/'
[建议收藏,彻底搞懂字符编码问题,从此告别中文乱码](https://mp.weixin.qq.com/s/Dxj8b9LX56ZUF5lUCtKp2A)
[万字长文讲解编码知识,看这文就够了!| 原力计划](https://mp.weixin.qq.com/s/8QEYD8U6Bx2rqO56cuU2KQ)
➜ pbpaste|sed '/^$/d ; s/^- /[/ ; s/ @.*)/](/ ; N ; s/\n// ; s/\x09// ; s/$/)/'|pbcopy
此时终端不会有任何输出显示,但是实际上剪切板的内容已经变成了:
[建议收藏,彻底搞懂字符编码问题,从此告别中文乱码](https://mp.weixin.qq.com/s/Dxj8b9LX56ZUF5lUCtKp2A)
[万字长文讲解编码知识,看这文就够了!| 原力计划](https://mp.weixin.qq.com/s/8QEYD8U6Bx2rqO56cuU2K
另外还有一种情况是直接在 Safari 上搜索到的网页要直接转为 Markdown 格式,同样可以用 Bookmarklet 实现。不仅仅是将链接拷贝为 Markdown 格式,而且如果网页中有选择文字的话,文字也会被一同复制到剪切板,Markdown 链接在最后一行,实现代码如下:
javascript: (function() {
function copyToClipboard(text) {
if (window.clipboardData && window.clipboardData.setData) {
return clipboardData.setData("Text", text);
} else if (document.queryCommandSupported && document.queryCommandSupported("copy")) {
var textarea = document.createElement("textarea");
textarea.textContent = text;
textarea.style.position = "fixed";
document.body.appendChild(textarea);
textarea.select();
try {
return document.execCommand("copy");
} catch(ex) {
console.warn("Copy to clipboar failed.", ex);
return false;
} finally {
document.body.removeChild(textarea);
}
}
}
copyToClipboard(document.body.innerText.replace(/(推荐阅读|喜欢此内容的人还喜欢)(.*\n)+/g, "").replace(/.*阅读原文.*/g,'').replace(/[\r\n]{3,}/g, "\n\n") + "\n" + '[' + document.title.replace(/ \/ Twitter/, '').replace(/^【.*】/, '').replace(/(|.*$|\|.*$)/, '').replace(/^\(.*\)/, '').replace(/-.*$/, '').replace(/(!|?|\?|\!)/g, '').replace(/_.*$/, '').trim() + '](' + window.location.href + ')');
})();
这套阅读流程看下来似乎非常复杂,主要原因是本文所写的都是如何搭建这套工作流,实际上搭建好了之后使用起来我个人评价还是比较简单的。本文所涉及的技术点包括 html、Bookmarklet,URL Scheme、JavaScript。使用了微信、Safari、Drafts、Bear、WebDAVNav、OmniFocus、PopClip、sed 八个软件,三个步骤再次概览:
除了前两步的微信和调用 Bookmarklet 可以不限制系统,其余后面的步骤都算是在 iOS/macOS 软件生态的加持在才得以实现的。例如 Drafts、Bear、Shortcuts、URL Scheme、PopClip、AirPrint 都是 iOS/macOS 软件生态下独有的软件。
另外你可能会疑惑为什么我把 URL Scheme 称之为 iOS/macOS 软件生态下独有的。因为在安卓系统下 URL Scheme 更多的是面向开发者,他们会提供「必要」的 URL Scheme 以供不同软件之间「必要」的跳转而不是考虑到用户的需求提供尽可能完善的 URL Scheme。但是得益于 iOS 开发者之间不成文的规定,想做出一个优秀的有口碑的效率类软件面向普通用户 URL Scheme 的支持也是必不可少的。
这个观点在 Hum 的《URL Schemes 使用详解》这篇文章中也有体现:
注:文中会提到使用 Launch Center Pro、Drafts 等应用的例子,它们都是同类应用中的最好选择,而支持 URL Schemes 是促成它们如此地位的不可忽视的原因。
而 Drafts 的作者直接不满 URL Schemes 只能跳出不能跳回的问题,和 Marco Arment、Justin Williams 等人开发了 x-callback-URL 来做到跳出,并跳回这样的动作。可以说这两款 App Launch Center Pro 和 Drafts 对 URL Schemes 的推广和使用构思上的贡献是最突出的,现在 URL Schemes 越来越被 iOS 用户和开发者所重视,在我眼里,一款 App 是否完整系统地支持 URL Schemes 已经是判断它是否优秀的标志之一。
包括原来的 Workflow 被苹果收购之后更名为 Shortcuts,有苹果官方站台之后效率类软件的开发者也会有更高的积极性给 Shortcuts 提供软件的 API。
到这篇文章写完之前,我用寒假的时间完成了这套流程的所有代码编写,但是实际上我做这些东西已经做了一年多了,因为很多需求并不是一开始就想得到的,都是在逐渐使用过程中发现还有哪些不足,就去完善代码,不断迭代了一年之后才有了现在的这套流程。通过这套流程我摆脱了微信公众号的封闭环境实现了阅读内容的良性闭环,希望我的这套流程对你有帮助或者启发。
本文中的所有代码都可以在 JamesHopbourn/Apple-Automation 中找到,如果方便希望能帮我 star 一下。如果有任何需求或者 bug 也可以通过 issue 报给我。本文很多思路以及想法都是这一年在我的频道上发表过的,本文也是对过去一年一些自动化思路的合集,如果有兴趣也可以关注我的频道 James Notes。
> 下载少数派 客户端 、关注 少数派公众号 ,了解更妙的数字生活 🍃
> 想申请成为少数派作者?冲!