C++调用matlab函数实现微信自动跳一跳

时间:2022-09-26 23:25:56

突发奇想,动手去做。

截图1920*1080。

HSV,一种颜色模型,类似于常见的红绿蓝RGB

H:色调

S:饱满度

V:明度

在Matlab中将手机截图分解成这三个层次。如下图。

C++调用matlab函数实现微信自动跳一跳

      图1    原图

C++调用matlab函数实现微信自动跳一跳

                              图2     HSV三个层次

从图上可以观察到:

  1. 人物处在图像中间。
  2. 目标跳台总是在人物上面。
  3. 图像上下一定区域对识别无用。
  4. S层背景,有从上到下存在渐变。

去掉上下部分。如下图3。

C++调用matlab函数实现微信自动跳一跳

                                                                    图3  去掉上下

首先确定人物坐标C++调用matlab函数实现微信自动跳一跳,红点。

三个图中的人物明显区别周围区域,利用Matlab对人物区域数据进行统计分析。或者简单粗暴如下图4。

C++调用matlab函数实现微信自动跳一跳

                                                    图4  H层人物区域部分数据

H层,人物主要落在范围A:0.6458—0.7222。

S层,人物主要落在范围B:0.3000—0.4500。(S层井盖落在0-0.1500)红色区域受到动物眼睛的干扰。

V层,人物主要落在范围C:0.2200—0.3400。红色区域受到动物眼睛的干扰。

由此,我们在三个图层加限制条件。

在H层找到值落在A的像素点,这些像素点都固定为0.7222。再找值不是0.7222的像素点全固定为0。

同理在S层,V层重复上一句话的操作。S层固定为1,V层固定为0.36。总体效果如下图5。

C++调用matlab函数实现微信自动跳一跳    C++调用matlab函数实现微信自动跳一跳    C++调用matlab函数实现微信自动跳一跳

                                       图6  取出人物

H层:C++调用matlab函数实现微信自动跳一跳

S层:C++调用matlab函数实现微信自动跳一跳

V层:C++调用matlab函数实现微信自动跳一跳C++调用matlab函数实现微信自动跳一跳

红色区域为笑脸眼睛的干扰。发现H层并没有受到干扰。如果将H、S、V层点对点元素相乘,那么最后得到的矩阵Image_HSV在上图红色矩形框定的区域即为0了。因为H层红色矩形框定的区域框定的区域对应的像素值为0。0乘任何都为0。

Image_HSV = H .* S.* V;

Image_HSV,如下图6。

C++调用matlab函数实现微信自动跳一跳

图6  HSV三层再合成

可见,人物只有可怜的一点。C++调用matlab函数实现微信自动跳一跳

利用形态学的膨胀。

结构元素对象用15*15的正方形C++调用matlab函数实现微信自动跳一跳

两次膨胀后的效果。C++调用matlab函数实现微信自动跳一跳

四次膨胀后的效果,并二值化。C++调用matlab函数实现微信自动跳一跳

接下来找到人物坐标(x,y)C++调用matlab函数实现微信自动跳一跳

从上往下,从左到右扫描,最后一个白点取y。

从左到右,从上到下扫描,最后一个白点取x。


特别地,当遇到井盖时,要对S层再附加一层约束条件,去除井盖。

H层井盖:C++调用matlab函数实现微信自动跳一跳

V层井盖:C++调用matlab函数实现微信自动跳一跳

S层加约束条件井盖:C++调用matlab函数实现微信自动跳一跳

可见,H,V层所出现的井盖,在S层加约束条件后消失。但S层出现点状带,而H,V层却没有。三层相乘,干扰消失。如下图。 C++调用matlab函数实现微信自动跳一跳


接下来确定跳台坐标。

我们采用HSV的S层来作为母板,进行处理。如下图7

C++调用matlab函数实现微信自动跳一跳

      图7  跳台母板


下一个跳台的随机性,会有时向左跳,有时向右跳。

             

故将图像转置。我们就不用判断左右了。如下图8。

转置:原来(x,y),转置后变成(y,x)。

C++调用matlab函数实现微信自动跳一跳

                       图8   跳台母板转置

可以看到背景色是渐变的。如下图9。

C++调用matlab函数实现微信自动跳一跳

                                                  图9  渐变的背景色

把背景色统一为一种颜色。只看第一行,统一的背景色规定为从左边黑色部分到第一次出现背景色的值。

用unique函数找到第一行中所有出现的背景色的值。则下图中统一的背景色的值为0.3412。

C++调用matlab函数实现微信自动跳一跳

则遍历所有像素点,只要像素点的值不与统一背景色相同,则置为统一背景色。效果如下图10。

C++调用matlab函数实现微信自动跳一跳

                               图10  统一背景色

我们只要如下图11,从左到右,从上到下找到第一个不与背景色相同的点(蓝点),则为跳台最左边的顶点。最左边的点里包含跳台的行坐标x3。接下来要确定列坐标y4。

C++调用matlab函数实现微信自动跳一跳

              图11   含背景区域

要确定列坐标y4还需要进一步处理图片。

固定在蓝点所在的行x3,从左往右,每次往右一个像素点(y3+m)。则点(x3,y3+m)垂直往上找最后一个不与背景色相同的点,则这个点的坐标应为(x3-n,y3+m)。如下图12。统计m个数据中,找到使n最大的点(红线最长的点)。第一个出现n最大的点(第一个红线最长的点)则为黄点。所以可以确定跳台的坐标(x3,y4)。测试得m取200合适所有情况,n取最大上限100合适。

C++调用matlab函数实现微信自动跳一跳

                                         图12

因为图片先前转置,所以得到的跳台坐标实际应为(y4,x3),记得加上开始删除分数那部分的坐标。此方法同样适用于圆形。

特别地,当人物目前所在跳台和下一个跳台之间过近,会出现人物头比跳台还靠左的现象。根据算法,则会找到人头顶的点。这是不正确的。

C++调用matlab函数实现微信自动跳一跳

解决办法:将人物全部置为统一背景色,则不会对上述找跳台坐标产生影响。

因为之前在确定人物坐标的时候,经过四次膨胀C++调用matlab函数实现微信自动跳一跳。可见人物下部总比上部宽,则以下部宽为宽,人物长为长,用矩形选中人物。C++调用matlab函数实现微信自动跳一跳蓝色矩形区域全部置为统一背景色。效果如下图13。

C++调用matlab函数实现微信自动跳一跳

              图13  人物清除


综上,人物坐标(x,y),跳台坐标(y4,x3)。

根据勾股定理,距离dis,C++调用matlab函数实现微信自动跳一跳

以上方法,经测试不能100%准确测量距离,当遇到诡异花纹时,将出现小范围跳动,恰好不能100%落入图像中间,也规避了作弊机制,但值得一提的是,连续跳入中点的概率越往后越高。

经过测试可得按压时间time(单位:毫秒)与距离dis的关系大致为:

time = k × dis,其中k取1.3~1.5。

例子1:

C++调用matlab函数实现微信自动跳一跳

跳台和人物的距离:406.6018


例子2:

C++调用matlab函数实现微信自动跳一跳

跳台和人物的距离:384.8428


例子3:

C++调用matlab函数实现微信自动跳一跳

魔方将会跳到顺着蓝线最远的那一格。

跳台和人物的距离:692.6074


例子4:

C++调用matlab函数实现微信自动跳一跳

看看圆形的表现。

C++调用matlab函数实现微信自动跳一跳

跳台和人物的距离: 302.7689

经过测试,跳到1000分没问题,超过1000分基本不会上榜。

vs2017 如何控制手机,调用 matlab函数部分,待更。