├── .gitattributes
├── .gitignore
├── README.md
├── index.html
├── init.js
├── load.js
├── log.js
├── mouse.js
├── render.js
└── resize.js
/.gitattributes:
--------------------------------------------------------------------------------
1 | # Auto detect text files and perform LF normalization
2 | * text=auto
3 |
4 | # Custom for Visual Studio
5 | *.cs diff=csharp
6 |
7 | # Standard to msysgit
8 | *.doc diff=astextplain
9 | *.DOC diff=astextplain
10 | *.docx diff=astextplain
11 | *.DOCX diff=astextplain
12 | *.dot diff=astextplain
13 | *.DOT diff=astextplain
14 | *.pdf diff=astextplain
15 | *.PDF diff=astextplain
16 | *.rtf diff=astextplain
17 | *.RTF diff=astextplain
18 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Windows image file caches
2 | Thumbs.db
3 | ehthumbs.db
4 |
5 | # Folder config file
6 | Desktop.ini
7 |
8 | # Recycle Bin used on file shares
9 | $RECYCLE.BIN/
10 |
11 | # Windows Installer files
12 | *.cab
13 | *.msi
14 | *.msm
15 | *.msp
16 |
17 | # Windows shortcuts
18 | *.lnk
19 |
20 | # =========================
21 | # Operating System Files
22 | # =========================
23 |
24 | # OSX
25 | # =========================
26 |
27 | .DS_Store
28 | .AppleDouble
29 | .LSOverride
30 |
31 | # Thumbnails
32 | ._*
33 |
34 | # Files that might appear in the root of a volume
35 | .DocumentRevisions-V100
36 | .fseventsd
37 | .Spotlight-V100
38 | .TemporaryItems
39 | .Trashes
40 | .VolumeIcon.icns
41 |
42 | # Directories potentially created on remote AFP share
43 | .AppleDB
44 | .AppleDesktop
45 | Network Trash Folder
46 | Temporary Items
47 | .apdisk
48 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | ## responsiveTouchGameFramework v2
2 |
3 | A tiny boilerplate for HTML5 games featuring a responsive, centered, fixed-ratio canvas, and unified pointer events (mouse + touch).
4 |
5 | **Demo:**
6 |
7 | http://xem.github.io/responsiveTouchGameFramework
8 |
9 | **How to use:**
10 |
11 | - Clone this repo
12 | - Edit the page title and global CSS (index.html)
13 | - Set your canvas size (ex: 480 x 270) and game variables in init.js
14 | - Write your game's code in the render loop (render.js) - the demo draws a square movable with the mouse/finger.
15 | - At any moment you have access to the variables ````click_x````, ````click_y````, ````down_x````, ````down_y````, ````move_x````, ````move_y````, ````up_x```` and ````up_y```` (adapted to your canvas dimensions), and ````pointer_down```` (to tell if the mouse/finger is currently down)
16 | - Log stuff on screen using the ````log()```` function
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
TITLE
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/init.js:
--------------------------------------------------------------------------------
1 | /* Customizable canvas size */
2 | canvas_width = 480;
3 | canvas_height = 270;
4 |
5 |
6 | /* Game variables */
7 | x = 100;
8 | y = 100;
9 | grab = false;
10 | grab_x = 0;
11 | grab_y = 0;
--------------------------------------------------------------------------------
/load.js:
--------------------------------------------------------------------------------
1 | /* Load */
2 | onload = e => {
3 | logz.value = "";
4 | a.width = canvas_width;
5 | a.height = canvas_height;
6 | c = a.getContext("2d");
7 | canvas_ratio = canvas_width / canvas_height;
8 | onresize();
9 | setInterval(render, 16);
10 | }
--------------------------------------------------------------------------------
/log.js:
--------------------------------------------------------------------------------
1 | log = e => {
2 | logz.value += e + "\n";
3 | logz.scrollTop = log.scrollHeight;
4 | }
--------------------------------------------------------------------------------
/mouse.js:
--------------------------------------------------------------------------------
1 | /* Compute mouse / touch coordinates on the canvas */
2 |
3 | pointer_down = false;
4 |
5 | update_mouse = e => {
6 |
7 | pointer = {};
8 | if(e.changedTouches){
9 | pointer = e.changedTouches[0];
10 | }
11 | else {
12 | pointer = e;
13 | }
14 |
15 | return [
16 | ~~(((pointer.pageX) - canvas_left) * canvas_width / canvas_real_width),
17 | ~~(((pointer.pageY) - canvas_top) * canvas_height / canvas_real_height)
18 | ];
19 | }
20 |
21 | /* Click */
22 | onclick = e => {
23 | e.preventDefault();
24 | [click_x, click_y] = update_mouse(e);
25 |
26 | };
27 |
28 | /* Mousedown / touchstart */
29 | onmousedown = ontouchstart = e => {
30 | e.preventDefault();
31 | pointer_down = true;
32 | [down_x, down_y] = update_mouse(e);
33 | };
34 |
35 | /* Mousemove / touchmove */
36 | onmousemove = ontouchmove = e => {
37 | e.preventDefault();
38 | [move_x, move_y] = update_mouse(e);
39 | };
40 |
41 | /* Mouseup / touchend */
42 | onmouseup = ontouchend = e => {
43 | e.preventDefault();
44 | pointer_down = false;
45 | [up_x, up_y] = update_mouse(e);
46 |
47 | /* Add click on mobile */
48 | if(e.changedTouches){
49 | onclick();
50 | }
51 | };
52 |
53 | /* Right click */
54 | oncontextmenu = e => {
55 | e.preventDefault();
56 | };
--------------------------------------------------------------------------------
/render.js:
--------------------------------------------------------------------------------
1 | /* Render */
2 | render = e => {
3 |
4 | // Reset
5 | a.width = a.width;
6 |
7 | // Drax square
8 | c.rect(x,y,30,30)
9 | c.fill();
10 |
11 | // Grab
12 | if(!grab && pointer_down && c.isPointInPath(down_x, down_y)){
13 | grab = true;
14 | grab_x = down_x - x;
15 | grab_y = down_y - y;
16 | log("grab");
17 | }
18 |
19 | // Let go
20 | if(grab && !pointer_down){
21 | grab = false;
22 | log("let go");
23 | }
24 |
25 | // Follow mouse / finger
26 | if(grab){
27 | x = move_x - grab_x;
28 | y = move_y - grab_y;
29 | }
30 | }
--------------------------------------------------------------------------------
/resize.js:
--------------------------------------------------------------------------------
1 | /* Canvas offsets (changed onresize) */
2 | canvas_left = 0;
3 | canvas_top = 0;
4 |
5 | /* Canvas "real" size (changed onresize) */
6 | canvas_real_width = 0;
7 | canvas_real_height = 0;
8 |
9 | /* Resize */
10 | onresize = onrotate = b => {
11 |
12 |
13 | screen_ratio = innerWidth / innerHeight;
14 |
15 | /* Full width */
16 | if(canvas_ratio > screen_ratio){
17 | canvas_real_width = innerWidth;
18 | canvas_real_height = innerWidth / canvas_ratio;
19 | canvas_left = 0;
20 | canvas_top = (innerHeight - canvas_real_height) / 2;
21 | logz.style.width = "200px";
22 | logz.style.height = (canvas_top - 20) + "px";
23 | }
24 |
25 | /* Full height */
26 | else {
27 | canvas_real_width = innerHeight * canvas_ratio;
28 | canvas_real_height = innerHeight;
29 | canvas_left = (innerWidth - canvas_real_width) / 2;
30 | canvas_top = 0;
31 | logz.style.width = (canvas_left - 20) + "px";
32 | logz.style.height = "100px";
33 | }
34 | a.style.width = canvas_real_width + "px";
35 | a.style.height = canvas_real_height + "px";
36 |
37 | logz.style.height = (canvas_top - 20) + "px";
38 |
39 | };
40 |
--------------------------------------------------------------------------------