你走过哪条街,那条街就变成你的颜色。
这是「像素征途」的核心玩法。不是步数统计,不是卡路里,就是纯粹的领地占领。
为什么做这个
我走路上班,每天同一条路,走了三年。健康 App 告诉我消耗了多少卡路里——那个数字对我来说就是 0,从来没认真看过一次。
有一天在想:如果把「走过的路」变成地图上可视的领地,是不是完全不同?就像战略游戏里战争迷雾被揭开的满足感。做了个原型,在自己手机上跑了一周,发现每天上班开始主动绕路——就为了多点亮几格。上瘾了。
地图层用的 MapLibre(离线瓦片渲染),Tile 坐标计算和领地状态全部本地跑,不依赖服务端实时计算。这个选择是为了在没网络时也能正常探索,但带来了一些同步麻烦,后面说。
后悔决定一:连击门槛设太远了
连击系统的逻辑是:连续活跃天数越多,得分倍率越高,3-4 天 1.5x,5 天以上 2x,中断一天有缓冲期不立刻清零。
static func multiplier(for consecutiveDays: Int) -> Double {
switch max(0, consecutiveDays) {
case 5...:
return 2.0
case 3...4:
return 1.5
default:
return 1.0
}
}
最早设计的是连续 7 天才能拿到 2x。结果发现用户到第 5 天就开始大量流失——从内测数据看,第 5 天留存大概只有 30% 出头,门槛太远,放弃比坚持轻松。往前调到 5 天之后,同期第 5 天留存爬到了接近 55%。
激励设计里「目标距离感」挺关键的。太近没挑战,太远就不玩了。这是我调参调得最久的一个地方,前后试了三版数值。
后悔决定二:历史照片导入砍得太狠
App 支持导入相册的 GPS 位置记录来「找回」历史足迹。上线前我加了一个 3 年时间限制——担心一次性导入太多历史数据会卡顿,直接在读取时过滤掉 3 年前的数据。
上线后第一条五星评论写的就是:「前些年旅游的照片位置无法导入了。」
用一个「能用」换掉了「好用」。说实话有点难受,这种为了省事加的硬限制,影响的偏偏是最有历史足迹、最有黏性的那类用户。
下个版本准备改成分批异步导入,去掉年份限制。但这个决定在上线阶段就留下了差评种子,挺可惜的。
后悔决定三:热力衰减上线太激进
走过的格子不是永久亮着,而是有衰减——最近走的最亮,久没去的慢慢变暗,30 天后只剩淡淡痕迹(opacity 0.12)。
enum MapHeatRules {
static let routeGlowSoftDecayDay = 4
static let routeGlowDecayDay = 7
static let zoneEmphasisDecayDay = 14
static let tileResidualDecayDay = 30
static let tileResidualOpacity = 0.12
}
设计意图是让用户有「复刻领地」的动力。但我没想到的是:新用户第一次看到地图,走了几天,某天打开发现上周的足迹变淡了——不是「哦我得回去走走」,而是「这 App 有 bug 吗」。
衰减本身没问题,但新手引导没做到位,用户不理解这是机制而不是故障。现在评论区偶尔会问「为什么以前走的路变淡了」,每次解释都要费一番功夫。这个本来应该在第一次出现衰减时主动告知用户的,没做。
区域「征服」的判定细节
顺带说一个设计决定这次没后悔的。地图按 8×8 的 Zone 划分,走满 58 格算「征服」,走满 64 格算「完美征服」。
阈值定 58 而不是 64 是因为实际地图里总有格子是河流、封闭建筑内部,根本走不到。如果要求 100% 才算征服,大部分区域永远无法达成。留 6 格容错,让「完美征服」变得有挑战但不是不可能完成的任务。
这个数字到现在没改过,感觉比较合适。
现在的状态
上线 7 天,iOS 端下载 0 次——对,就是 0。没有任何推广预算,纯靠自然搜索,等于没有流量。
这类「需要你真的出门走路才能玩」的 App 冷启动比纯内容 App 难多了:用户得先理解玩法,还得愿意出门,链条多一环就多一次流失机会。
我试了两个方向:联系了两个本地跑步打卡社群,发了介绍帖,没有回音;在 Twitter/X 发了地图截图,几个点赞,没有转化。说实话还没找到打开口子的方式。
技术方向上接下来想做社区排行榜——「你占了这个城市的 X%」这个数字天然有攀比属性,单机状态下这个数据没有参照物,加了榜单之后应该能提高一些分享动力。
如果你做过「行为激励类」或者「需要用户真实行动」的 App,冷启动是怎么找到第一批真实用户的?尤其是在没有预算的情况下。