konvajs+AlloyFinger实现h5找一找简易版游戏
文章目录
基本介绍
小游戏找一找熊猫demo使用konva-js+AlloyFinger实现图形插入展示及手势操作监听
使用jquery+animate-css操作dom节点实现窗口动画交互
游戏完成结算通过html2canvas+微信jdk构建生成海报保存图片分享
一、构建资源
1.引入插件库
代码如下(示例):(vconsole即手机端调式工具)
<link rel="stylesheet" href="style/animate.css">
<script src="js/jquery-3.6.0.min.js"></script>
<script src="js/konva.js"></script>
<script src="js/alloy_finger.js"></script>
<script src="https://cdn.bootcdn.net/ajax/libs/vConsole/3.9.0/vconsole.min.js"></script>
2.地图及动物图片资源
地图
真假熊猫
规则弹窗
这里就不一一展示了
二、代码部分
1.DOM部分
<!-- 游戏规则弹窗 -->
<div class="game_rule_mask" style="display: none;">
<div class="game_rule_info animate__animated animate__zoomIn" style="display: none; --animate-duration: 1.3s;">
<img src="images/map/rule_dialog.png" alt="">
<div class="game_rule_button"></div>
</div>
</div>
<!-- main -->
<div class="container_box">
<!-- canvas -->
<div id="container"></div>
</div>
2.JS部分
2.1 创建地图容器
// 初始化地图
var imageObj = new Image();
// 建立地图图片
var map = new Konva.Image({
x: 0,
y: 0,
image: imageObj,
width: imageObj.width * 0.5,
height: imageObj.height * 0.5,
preventDefault: false,
});
// 把地图加入到组中
group.add(map);
// 地图图片路径
imageObj.src = 'images/map/map.png';
2.2 创建真假动物
// 创建动物我并加入
function loadImages(sources, animals, callback) {
var assetDir = '';
var images = {};
var loadedImages = 0;
var numImages = 0;
for (var src in sources) {
numImages++;
}
for (var src in sources) {
images[src] = new Image();
images[src].onload = function () {
if (++loadedImages >= numImages) {
callback(images);
}
};
images[src].src = assetDir + sources[src];
}
}
// 创建动物 (位置-名称-大小)
function create_panda(anim, key) {
var animal = new Konva.Image({
image: images[key],
x: anim.x,
y: anim.y,
width: anim.w,
height: (images[key].height / images[key].width) * anim.w,
draggable: false,
});
// 触摸事件
animal.on('touchstart', function () { });
// 把动物载入进
group.add(animal);
}
2.3 真假动物图片路径及位置摆放
// 动物图片路径
var sources = {
// 真熊猫
panda_true_1: 'images/map/map_panda_true_1.png',
};
// 动物位置
var animals = {
// 真熊猫
panda_true_1: {
x: 300,
y: 570,
w: 50,
},
};
loadImages(sources, animals, initStage);
2.4 游戏规则及触发逻辑动画
三、全部代码
<!--
* @Author: hyzx
* @Date: 2021-11-26 15:55:55
* @Description:
-->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0">
<base href="assets/" target="assets" />
<title>保利</title>
<script src="https://unpkg.com/vconsole/dist/vconsole.min.js"></script>
<link rel="stylesheet" href="layui/css/layui.css">
<link rel="stylesheet" href="style/common.css">
<link rel="stylesheet" href="plugins/swiper/animate.min.css" />
<link rel="stylesheet" href="style/animate.css">
<link rel="stylesheet" href="style/panda.css">
<script src="js/common.js"></script>
</head>
<body>
<!--加载动画 Start-->
<!-- <div class="usun-load-box" id="usun-loading">
<div class="load-img"><img src="images/common/loadding.gif" alt="" /></div>
<div class="copyright"> 优上创意</div>
</div> -->
<!--加载动画 End-->
<!--背景音乐 Start-->
<div class="usun-audio">
<audio autoplay="autoplay" loop="loop" id="usun-music">
<source src="video/bg.mp3" type="audio/mpeg" />
</audio>
</div>
<!--背景音乐 End-->
<!-- 游戏规则 Start-->
<div class="rule_float">
<img src="/assets/images/map/rule_icon.png" alt="">
</div>
<!-- 游戏规则 End-->
<!-- 状态信息 -->
<div class="game_left_right">
<div class="game_left_right_panda">6/6</div>
<div class="game_left_right_life">10</div>
</div>
<!-- 玩法介绍 -->
<div class="play_info_mask " style="display: none;">
<div class="play_info animate__animated animate__zoomIn" style="display: none; --animate-duration: 1.3s;">
<img src="images/map/dialog.png" alt="">
<div class="play_info_button"></div>
</div>
</div>
<!-- 开局提示 -->
<div id="game_start_box_mask" style="display: none;">
<div class="game_start_box">
<!-- 水平手势提示 -->
<span class="game_start_box_reminder_level">
<span class="game_start_box_finger_level"></span>
</span>
</div>
</div>
<!-- 游戏规则弹窗 -->
<div class="game_rule_mask" style="display: none;">
<div class="game_rule_info animate__animated animate__zoomIn" style="display: none; --animate-duration: 1.3s;">
<img src="images/map/rule_dialog.png" alt="">
<div class="game_rule_button"></div>
</div>
</div>
<!-- 成功找出所有熊猫 -->
<div class="results_info_mask" id="results_info_mask" style="display: none;">
<div class="results_info animate__animated animate__zoomIn" style="--animate-duration: 1s;">
<b>6</b>
</div>
<span class="dont_feed_dialog_main_overGame_button" style="top:7rem">结束游戏</span>
</div>
<!-- 没有竹子可喂食对话框 -->
<div class="dont_feed_dialog_mask" style="display: none;">
<div class="dont_feed_dialog_box animate__animated animate__zoomIn" style="--animate-duration: 0.6s;">
<div class="dont_feed_dialog_main">
<span class="dont_feed_dialog_main_overGame_button">结束游戏</span>
</div>
</div>
</div>
<!-- 成功找出熊猫 -->
<div class="find_success_dialog_mask " style="display: none;">
<div class="find_success_dialog_avatar_box animate__animated animate__zoomIn" style="--animate-duration: 1s;">
<div class="find_success_dialog_avatar">
<img class="find_success_dialog_avatar_panda" src="images/map/map_panda_true_1.png" alt="">
</div>
<img class="find_success_dialog_avatar_light" src="images/map/find_success_dialog_bg_light.png" alt="">
<img class="find_success_dialog_message" src="images/map/find_success_dialog_bg.png" alt="">
</div>
</div>
<!-- 找出错误熊猫 -->
<div class="find_error_dialog" style="display: none;">
<img class="find_error_dialog_img animate__animated animate__zoomIn" style="--animate-duration: 0.6s;"
src="images/map/find_error_dialog.png" alt="">
</div>
<!-- main -->
<div class="container_box">
<!-- canvas -->
<div id="container"></div>
</div>
<script src="js/konva.js"></script>
<script src="js/jquery-3.6.0.min.js"></script>
<script src="layui/layui.js"></script>
<script src="js/base.js"></script>
<script src="js/jweixin-1.6.0.js"></script>
<script src="plugins/swiper/swiper.animate1.0.3.min.js"></script>
<script src="js/alloy_finger.js"></script>
<script src="https://cdn.bootcdn.net/ajax/libs/vConsole/3.9.0/vconsole.min.js"></script>
<script>
var vConsole = new VConsole();
$(function () {
// 定义画布宽高及画框尺寸
var border_px = 11;
var info_box = 0;
var myCanvas_width = window.innerWidth - (border_px * 2);
var myCanvas_height = window.innerHeight - (border_px * 2) - info_box;
var panda_number = 0;//当前找到熊猫数量
var panda_count = 6;//熊猫总数
var food_number = 10;//当前竹子(生命)
var is_feed_panda_arr = [];//已经投喂过的熊猫
var nowScaleBy = 0.5;//当前倍数
var stage = new Konva.Stage({
container: 'container',
width: myCanvas_width,
height: myCanvas_height,
});
var stageDom = document.getElementById('container')
new AlloyFinger(stageDom, {
pinch: function (evt) {
console.log(evt)
},
});
var map_layer = new Konva.Layer();
var group = new Konva.Group({
x: -1100,
y: -300,
draggable: true,
dragBoundFunc: function (pos) {
// 获取当前镜头倍数
var current_ScaleBy = nowScaleBy != null ? nowScaleBy : panda_map_scale;
// 获取可移动最大高度
var max_move_height = (imageObj.height * current_ScaleBy) - myCanvas_height;
// 获取可移动最大宽度
var max_move_width = (imageObj.width * current_ScaleBy) - myCanvas_width;
var mapY = Math.abs(pos.y)
var mapX = Math.abs(pos.x)
var now_map_Y = pos.y > 0 ? 0 : (mapY > max_move_height ? max_move_height : mapY)
var now_map_X = pos.x > 0 ? 0 : (mapX > max_move_width ? max_move_width : mapX)
return {
x: -(now_map_X),
y: -(now_map_Y)
};
},
});
// 初始化地图
var imageObj = new Image();
imageObj.onload = function () {
// 建立地图图片
var map = new Konva.Image({
x: 0,
y: 0,
image: imageObj,
width: imageObj.width * 0.5,
height: imageObj.height * 0.5,
preventDefault: false,
});
// 把地图加入到组中
group.add(map);
// 创建动物我并加入
function loadImages(sources, animals, callback) {
var assetDir = '';
var images = {};
var loadedImages = 0;
var numImages = 0;
for (var src in sources) {
numImages++;
}
for (var src in sources) {
images[src] = new Image();
images[src].onload = function () {
if (++loadedImages >= numImages) {
callback(images);
}
};
images[src].src = assetDir + sources[src];
}
}
// 初始化动物配置项信息
function initStage(images) {
// 创建动物 (位置-名称-大小)
function create_panda(anim, key) {
var animal = new Konva.Image({
image: images[key],
x: anim.x,
y: anim.y,
width: anim.w,
height: (images[key].height / images[key].width) * anim.w,
draggable: false,
});
// 触摸事件
animal.on('touchstart', function () {
// 判断该熊猫是否投喂过
if (is_feed_panda_arr.includes(String(key))) {
$('.find_success_dialog_avatar_panda').attr('src', 'images/map/map_panda_true_' + key.split('_')[2] + '.png')
$('.find_success_dialog_mask').show()
setTimeout(() => {
$('.find_success_dialog_avatar_box').removeClass('animate__zoomIn')
$('.find_success_dialog_avatar_box').addClass('animate__zoomOut')
clear_animate_zoom_state('find_success_dialog_mask', 'find_success_dialog_avatar_box');
clearTimeout()
}, 1800);
return false
}
// 没有竹子可喂食
if (Number(food_number) === Number(0)) {
$('.dont_feed_dialog_mask').show()
return false
}
// 确保所有弹出已关闭
if (
String($('.find_success_dialog_mask').css('display')) === 'none'
&&
String($('.find_error_dialog').css('display')) === 'none'
) {
feed_panda(key)
}
});
group.add(animal);
}
// 循环熊猫配置项
for (var key in animals) {
(function () {
var anim = animals[key];
switch (key) {
// 真熊猫
case 'panda_true_1':
create_panda(anim, key)
break;
case 'panda_true_2':
create_panda(anim, key)
break;
case 'panda_true_3':
create_panda(anim, key)
break;
case 'panda_true_4':
create_panda(anim, key)
break;
case 'panda_true_5':
create_panda(anim, key)
break;
case 'panda_true_6':
create_panda(anim, key)
break;
// 假熊猫
case 'panda_false_1':
create_panda(anim, key)
break;
case 'panda_false_2':
create_panda(anim, key)
break;
case 'panda_false_3':
create_panda(anim, key)
break;
case 'panda_false_4':
create_panda(anim, key)
break;
case 'panda_false_5':
create_panda(anim, key)
break;
case 'panda_false_6':
create_panda(anim, key)
break;
}
})();
}
// 将组加入到 地图层中
map_layer.add(group);
stage.add(map_layer);
}
// 动物图片路径
var sources = {
// 真熊猫
panda_true_1: 'images/map/map_panda_true_1.png',
panda_true_2: 'images/map/map_panda_true_2.png',
panda_true_3: 'images/map/map_panda_true_3.png',
panda_true_4: 'images/map/map_panda_true_4.png',
panda_true_5: 'images/map/map_panda_true_5.png',
panda_true_6: 'images/map/map_panda_true_6.png',
// 假熊猫
panda_false_1: 'images/map/map_panda_false_1.png',
panda_false_2: 'images/map/map_panda_false_2.png',
panda_false_3: 'images/map/map_panda_false_3.png',
panda_false_4: 'images/map/map_panda_false_4.png',
panda_false_5: 'images/map/map_panda_false_5.png',
panda_false_6: 'images/map/map_panda_false_6.png',
};
// 动物位置
var animals = {
// 真熊猫
panda_true_1: {
x: 300,
y: 570,
w: 50,
},
panda_true_2: {
x: 228,
y: 820,
w: 50,
},
panda_true_3: {
x: 1300,
y: 1100,
w: 50,
},
panda_true_4: {
x: 180,
y: 1100,
w: 50,
},
panda_true_5: {
x: 1980,
y: 750,
w: 50,
},
panda_true_6: {
x: 1811,
y: 532,
w: 15,
},
// 假熊猫
panda_false_1: {
x: 930,
y: 380,
w: 50,
},
panda_false_2: {
x: 530,
y: 438,
w: 50,
},
panda_false_3: {
x: 1010,
y: 850,
w: 90,
},
panda_false_4: {
x: 1445,
y: 590,
w: 50,
},
panda_false_5: {
x: 2310,
y: 657,
w: 50,
},
panda_false_6: {
x: 1400,
y: 90,
w: 320,
},
};
loadImages(sources, animals, initStage);
};
// 地图图片路径
imageObj.src = 'images/map/map.png';
// 初始化竹子&熊猫
function init_panda_food(pandaNumber, foodNumber) {
$('.game_left_right_panda').text(pandaNumber + '/' + panda_count)
$('.game_left_right_life').text(foodNumber)
}
init_panda_food(panda_number, food_number)
// 玩法介绍显示
$('.play_info_mask').show()
$('.play_info').show()
// 游戏规则显示
$('.rule_float').click(function () {
$('.game_rule_mask').show()
$('.game_rule_info').show()
})
// 游戏规则隐藏
$('.game_rule_button').click(function () {
$('.game_rule_mask').hide()
$('.game_rule_info').hide()
})
// 玩法介绍隐藏
$('.play_info_button').click(function () {
$('.play_info_mask').hide()
$('.play_info').hide()
$('#game_start_box_mask').show()
})
// 水平垂直滑动手势提示
var gameStartBoxMask = document.getElementById('game_start_box_mask')
new AlloyFinger(gameStartBoxMask, {
swipe: function () {
$('#game_start_box_mask').hide()
}
});
// 喂食熊猫
function feed_panda(current_panda) {
// 判断真假熊猫
if (current_panda !== null && current_panda.split('_')[1] === 'true') {
$('.find_success_dialog_avatar_panda').attr('src', 'images/map/map_panda_true_' + current_panda.split('_')[2] + '.png')
panda_number++;//熊猫计数加一
is_feed_panda_arr.push(String(current_panda));//最加到已投喂熊猫数组
$('.find_success_dialog_mask').show()
// 成功找到熊猫动画
setTimeout(() => {
$('.find_success_dialog_avatar_box').removeClass('animate__zoomIn')
$('.find_success_dialog_avatar_box').addClass('animate__zoomOut')
clear_animate_zoom_state('find_success_dialog_mask', 'find_success_dialog_avatar_box');
clearTimeout()
}, 2200);
} else {
$('.find_error_dialog').show()
// 失败找到熊猫动画
setTimeout(() => {
$('.find_error_dialog_img').removeClass('animate__zoomIn')
$('.find_error_dialog_img').addClass('animate__zoomOut')
clear_animate_zoom_state('find_error_dialog', 'find_error_dialog_img');
clearTimeout()
}, 1800);
}
food_number--;
init_panda_food(panda_number, food_number)
}
// 清除找熊猫动画效果恢复延迟隐藏
function clear_animate_zoom_state(dialog_dom, animate_dom) {
setTimeout(() => {
$('.' + animate_dom).removeClass('animate__zoomOut')
$('.' + animate_dom).addClass('animate__zoomIn')
$('.' + dialog_dom).hide()
// 判断是否找全所有熊猫
if (panda_number === panda_count) success_findAll_panda()
clearTimeout()
}, 1000);
}
// 成功找到所有熊猫
function success_findAll_panda() {
$('.results_info_mask').show()
}
// 确认结束游戏
$('.dont_feed_dialog_main_overGame_button').click(function () {
$('.dont_feed_dialog_mask').hide()
window.location.href = `/hierarchical?life=${food_number}`
})
})
</script>
<script>
//隐藏加载动画
setTimeout(function () {
$('#usun-loading').hide();
}, 1800)
window.onload = function () {
}
document.addEventListener('DOMContentLoaded', function () {
function audioAutoPlay() {
var bgmusic = document.getElementById('usun-music');
bgmusic.play();
//侦听微信ready事件。
document.addEventListener("WeixinJSBridgeReady", function () {
bgmusic.play();
}, false);
}
audioAutoPlay();
})
</script>
</body>
</html>
最后
这里就是找一找动物小游戏的全部内容,想要全部源码案例点在这里可以下载查看
https://gitee.com/Yuanmw/panda