小游戏 | 耐心极限大挑战,整蛊小游戏之「禁止向上走」

1,545 阅读12分钟

故事是这样开始的

很久很久以前,我关注的一个游戏博主,发了一个游戏视频。然后我就见识到了什么叫,「游戏叫你一步噶,你绝对走不到第二步」。

这个带那么点整蛊的性质的脑洞游戏,瞬间引起了我浓厚的兴趣。需要玩家克服大脑常规套路的惯性,那岂不是游戏处处是惊喜。

不过,游戏的本质还是在于趣味性,玩家掌握了规律之后,还是可以通关的。

等等,有没有无法通关的游戏?

这不就来了么,被「愚弄」智商的愉乐游戏, 不设计一个怪浪费的。

通关看心情

所以通关条件是什么?看作者心情吧。

试玩一下

我玩之前,先把脑子里的设计的规则都删除之后,才开始游戏。不然,玩着没那么有趣。

「愉」乐还是「愚」乐

「禁止向上走」小游戏,一起来设计其中的千层套路。

突然发现,这部分不仅是设计,还是解密。

正向思维,作者在复原游戏设计。

逆向思维,作者在拆解游戏攻略。

打不开的开始按钮

心急玩不了这游戏

情景再现

玩家想玩一下游戏,于是点击**「开始游戏」按钮,结果却发现按钮偏离了当前位置,跑到了别的地方,于是就上演了一场「你追我赶」**的戏码。

当按钮「逃跑」3次之后,回到原处,按钮文字变成「点击5次开始」。

实际玩家点击了3次,便进入了游戏关卡1。

惊不惊喜?意不意外?开不开心?

两重设计

开始按钮是有两重设计的:

第一重:前3次点击,按钮会发生**「跑动」**的现象,到第3次点击,按钮归位,文字改变,并进入第二重。

第二重:按钮名字为**「点击5次开始」**,实际点击3次便能进入关卡页。

能帮你到这

「开始」按钮的两重设计,实现起来也是比较简单的。

1、首先定义一个数组 movePosition,存放按钮在页面上移动的不同位置。

2、然后定义两个变量

moveNum:移动次数,记录当前按钮移动的具体次数。每次点击数值增加1,当次它的数值到临界值的时候,触发第二重设计。

conClickNum: 连续点击次数。每次点击数值增加1,当它的数值达到临界值时,触发进入关卡页。

3、将上述提到的变量都存放在一个对象 beginObj 中,方便管理。

/** @name 开始按钮具体数据对象  */
var beginObj = {
  text: ['开始游戏', '点击5次开始'], // 按钮展示文字
  moveNum: 0, // 移动次数
  conClickNum: 0, // 连续点击次数
  movePosition: [
    { x: '40%', y: '-200%' },
    { x: '0', y: '-350%' },
    { x: '-40%', y: '-110%' },
  ],
};

4、监听按钮点击事件,进行逻辑处理

var homeBeginE = document.getElementById('homeBeginE');
// 开始按钮-点击事件
homeBeginE.onclick = function () {
  // 如果已经打开过,不重复搞怪
  if (jjxxzgameUserInfo.beginTime) {
    getGateBoxShow();
  } else {
    if (beginObj.moveNum > 4) {
    	// 按钮归位,进入连续点击的设计
      setBeginClickData();
    } else {
    	// 设置按钮移动位置
      setBeginmovePosition();
    }
  }
};

过不去的下一关

论好玩,还得是无限流

情景再现

当玩家想趁热打铁的进入下一关的时候,但是惊奇的发现,这一关和上一关的展示名是一样的。

是时空倒流了,还是我穿越回去了?

真实的当前关卡

如果想知晓真实的当前关卡,需要点击一下关卡名,这个时候就会更换成真实的关卡名。

还能帮你到这

看似无限流,其实是通过获取随机数实现的效果。

1、随机值的范围,最大值是当前关卡最高数字。得到的结果向上取整,就能得到想要的随机值。

/**
 * 关卡-获取随机展示关卡值
 */
function getGateRandomValue() {
  let randomNum = Math.random() * gateObj.total;
  return Math.ceil(randomNum);
}

2、虽然展示的是随机关卡名,但是实际进入的确是真实的下一关,所以内容回显还是下一关的。

/**
 * 关卡-设置关卡名 每次进入下一步的时候
 */
function setGateTitleData(gateCurrVal) {
  const gateVal = getGateRandomValue();
  gateNumE.innerHTML = `关卡 ${gateVal}`;
  const gateCurrIndex = gateCurrVal - 1;
  gateTitleE.innerHTML = gateObj.list[gateCurrIndex].title;
}

帮不上的帮助按钮

灵魂拷问,事不过三

情景再现

初玩游戏的玩家,多少会有感到困惑的地方。于是,玩家就会找游戏规则,这个时候看到页面上的帮助按钮,下意识就会点击它。

「大聪明」游戏GM不会很爽快的一次就打开帮助页,会一直给提示,等到第三次时,此时的玩家耐心到了临界点,也会导致两种结果

  • 直接点击取消,却发现进入了帮助页。
  • 又耐着性子点了一遍确定,终于进入了帮助页。

「愚」乐要有度

虽然号称耐心挑战,但是也不能让玩家完成失去耐心,这样会导致玩家的流失

一个人回答多少次相似的问题会产生厌倦呢?

我观察过我自己和身边人,一般大家的极限是三次。三次之后可能就直接放弃回答了。

所以帮助按钮上,我设计了看似无限循环的相似问题,但是「愚」乐次数极限是三次,第三次之后会正式打开帮助页面。

瞧瞧谁的眼神这么有智慧,原来是我自己。

只能帮你到这

弹层呢,还是哪个弹层,每次的内容就各不相同了。

1、先来设置一个数组,存储每次展示的内容的具体文字。

2、再来设置点击次数的变量,记录当前按钮点击的具体次数。每次点击数值增加1,当次它的数值到临界值的时候,触发进入帮助页。

3、将上述提到的变量都存放在一个对象 helpObj 中,方便管理。

/** @name 开始信息对象  */
var helpObj = {
  text: ['聪明的玩家,您真的需要小助手的帮助吗?', '聪明的玩家,您真的需要小助手的帮助吗?', '智慧的玩家,无论您做出何种选择,小助手都祝您游戏愉快,确定打开帮助吗?'], // 提示文字
  clickNum: 0, // 点击次数
};

4、监听帮助按钮点击事件,进行逻辑处理:

  • 当已经经历过三次提问进入了帮助页,则再次点击不重复,直接进入帮助页。
  • 当是第一次进行点击帮助操作,记录点击次数,并打开提问弹层。
var homeHelpE = document.getElementById('homeHelp');

// 帮助按钮-点击事件
homeHelpE.onclick = function () {
  // 如果已经打开过,不重复搞怪
  if (jjxxzgameUserInfo.helpTime) {
    gethelpShow();
  } else {
    modalE.style.display = 'block';
    modalTextE.innerHTML = helpObj.text[helpObj.clickNum];
    helpObj.clickNum += 1;
  }
};

5、三次提问弹层,两种处理设计:

  • 前两次无论是确定按钮还是取消按钮都会直接关闭弹层。
  • 第三次打开后,无论是确定还是取消,都会进入帮助页。
// 帮助弹层-确定
modalBtnConfirmE.onclick = function () {
  closeModal();
  // 帮助的第三个弹窗 点击确定会进去帮助页
  if (helpObj.clickNum >= 3) {
    gethelpShow();
  }
};
// 帮助弹层-取消
modalBtnCancelE.onclick = function () {
  closeModal();
  // 帮助的第三个弹窗 点击取消也会进去帮助页
  if (helpObj.clickNum >= 3) {
    gethelpShow();
  }
};

设计「小心思」

棋盘背景

之所以设置类似「棋盘」的背景样式,是因为玩这个小游戏,就像是下棋,走对了可以将游戏一军,走岔了会被游戏将一军。

类似的样式我之前还实现过马赛克心形,都是借助 box-shadow 绘制而成,诀窍在于X和Y的偏移,只要设置合理,就能得到想要的展示效果。

#root::before {
  content: '';
  width: 70px;
  height: 75px;
  box-shadow: 70px 0px #254f88, 145px 0px #514b9a, 220px 0px #254f88, 295px 0px #514b9a, 370px 0px #254f88, 445px 0px #514b9a, 70px 80px #514b9a, 145px 80px #254f88, 220px 80px #514b9a, 295px 80px #254f88, 370px 80px #514b9a, 445px 80px #254f88, /*第一组*/ 70px 160px #254f88, 145px 160px #514b9a, 220px 160px #254f88, 295px 160px #514b9a, 370px 160px #254f88, 445px 160px #514b9a, 70px 240px #514b9a, 145px 240px #254f88, 220px 240px #514b9a, 295px 240px #254f88, 370px 240px #514b9a, 445px 240px #254f88, /*第二组*/ 70px 320px #254f88, 145px 320px #514b9a, 220px 320px #254f88, 295px 320px #514b9a, 370px 320px #254f88, 445px 320px #514b9a, 70px 400px #514b9a, 145px 400px #254f88, 220px 400px #514b9a, 295px 400px #254f88, 370px 400px #514b9a, 445px 400px #254f88, /*第三组*/ 70px 480px #254f88, 145px 480px #514b9a, 220px 480px #254f88, 295px 480px #514b9a, 370px 480px #254f88, 445px 480px #514b9a, 70px 560px #514b9a, 145px 560px #254f88, 220px 560px #514b9a, 295px 560px #254f88,
    370px 560px #514b9a, 445px 560px #254f88, /*第四组*/ 70px 640px #254f88, 145px 640px #514b9a, 220px 640px #254f88, 295px 640px #514b9a, 370px 640px #254f88, 445px 640px #514b9a, 70px 720px #514b9a, 145px 720px #254f88, 220px 720px #514b9a, 295px 720px #254f88, 370px 720px #514b9a, 445px 720px #254f88; /*第五组*/
  position: absolute;
  left: -95px;
}

变色龙按钮

我本来想仿照掘金的 Bug Fix 的按钮,做一个上下移动的动态按钮。但是那个立体感,我设计的不够好看。

后来想到蜡笔小新一个喝饮料变色的表情包很好玩,由此引发了灵感。

按钮变色用到的是 ****filter 滤镜,filter 拥有多种滤镜效果,其中有一种叫做色相旋转。

hue-rotate(-90deg):色相旋转可以设置顺时针角度,也可以设置逆时针角度。它的作用是按照标准色轮旋转元素的整体色相。

如下是一个标准色轮:

颜色不停变化的动效,则是因为配合加入了动画:

.home-btn {
  width: 200px;
  height: 60px;
  position: absolute;
  left: 50%;
  top: 300px;
  margin-left: -100px;
  box-shadow: 0 10px 25px #fc4d56, 0px -10px 25px #ffde2e, inset 0 -5px 10px #fc4d56, inset 0 5px 10px #ffde2e;
}
.home-btn-begin {
  animation: homeBtnBegin 2s linear infinite;
}

@keyframes homeBtnBegin {
  100% {
    filter: hue-rotate(360deg);
  }
}

关卡1:绿灯才能行

第一个关卡,我们先来看都有哪些元素。提示写的「不要向上走」,确实,我们的游戏也叫这个。那往下走呢?

我们来尝试往下走,结果噶了。向上也是这个结果。

等等,上面的圈可以移动,我们来试一下,果然,将上面的黄圈移动到下面的红圈上,出现了一个绿圈,这个时候,再移动到绿圈,就通关了。

所以关卡1的通关秘诀在于:

先将上面的黄圈移动到下面的红圈上,合成一个绿圈。

然后再将角色移动到绿圈,就可以通关了。

关卡2:选大(随时注意游戏名字哦~)

关卡2,每一组有两个数字,这关的通关诀窍在于:

1、当两个数字不同时,选择其中数值大的。

2、当两个数字相同时,选择下面的数字。

例如,当数字是3和2的时候,

选择3

总结

这算是我第一个真正意义上的通关游戏。之前的小游戏,有趣味性,缺少些完整性。

这次,无论是配色、交互、关卡设置、通关提示、帮助信息,都花费了我许多心思。尽管它只有两个关卡,但是整个开发的过程,从无到有,还挺耗心神的,不过实现过程充满了乐趣。

大致总结一下这个小游戏的几个巧妙的设计:

1、嵌套反套路,有趣但是有度。游戏的最终目的还是留住玩家,所以即便是脑洞游戏,也要时刻保持这个观念,不能一味的设计多层反转。玩,才是游戏的奥义。

2、关卡设计虽然不是完全的原创,但是加入了自己的脑洞。 比如第一关,我称之为红绿灯关卡,红灯停,绿灯行,遇到黄灯等一等。而第二个关,我特意设置了相同的数字,而通过条件就在游戏名字里,「禁止向上走」,所以选择下方的就成功了。

3、细节到位。标题处的向下箭头,随时提醒玩家,大部分时候选择向下是正确的。以及当玩家第一次体验了按钮的玄机之后,再次操作的时候,跳过按钮套路,让玩家不会产生抗拒心理。

以上就是本次分享的内容。如果觉得有帮助,欢迎留言讨论、点赞 、收藏,持续产出技术分享。


我是 叶一一,非职业「传道授业解惑」的技术博主。「趣学前端」、「CSS畅想」系列作者。

华夏美食、国漫、古风重度爱好者,刑侦、无限流小说初级玩家。

欢迎技术或非技术问题的讨论。

本文正在参加「金石计划」