This commit is contained in:
zDEFz
2024-06-03 01:11:54 +02:00
commit 8bc055c7fb
81 changed files with 2182 additions and 0 deletions

1
CNAME Normal file
View File

@ -0,0 +1 @@
shenzhen-solitaire.tgratzer.com

21
LICENSE.txt Normal file
View File

@ -0,0 +1,21 @@
MIT License
Copyright (c) 2016 Taylor Gratzer
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

23
README.md Normal file
View File

@ -0,0 +1,23 @@
# SHENZHEN I/O Solitaire Game
![Preview image](http://i.imgur.com/pSFk7Jr.jpg)
Yes, this is in the browser! This is a replication of the addictive solitaire game from SHENZHEN I/O. It can use original graphics from the game for a near-identical experience, but without having to keep the game running. The graphics and audio are not included, however, and must be copied from your installation of the game.
_This project is not associated with Zachtronics or [SHENZHEN I/O](http://store.steampowered.com/app/504210/)._
## Play Online
<http://tgratzer.com/shenzhen-solitaire/>
If you own the game you can use the base game's graphics and music. See the next step:
## How to install
1. Download this project from Github as a .zip, and extract.
2. Locate the SHENZHEN I/O solitaire textures folder from your installation.
This will be something like `steamapps\common\SHENZHEN IO\Content\textures\solitaire`
3. Copy the contents of that folder into the `solitaire` folder in the project.
4. (Optional) Find and copy the music (`Content\music\Solitaire.ogg`) into the `solitaire` folder.
5. Open index.html in your browser.
6. (If you don't own SHENZHEN I/O, you can still play the game, but it's not nearly as pretty.)

BIN
assets/button_bottom.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 50 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 59 KiB

BIN
assets/cursor_normal.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

BIN
assets/cursor_point.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 KiB

BIN
assets/window.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 351 KiB

37
css/colorblind.css Normal file

File diff suppressed because one or more lines are too long

254
css/noimages.css Normal file
View File

@ -0,0 +1,254 @@
/* filter is used to correct game assets and is not needed in the no-assets fallback */
* {
filter: none !important;
}
.card {
background-color: lightgray;
border: 1px solid darkgray;
border-top: 2px solid white;
border-radius: 5px;
box-shadow: 0px 2px 2px rgba(0, 0, 0, 0.24), 0px 0px 2px rgba(0, 0, 0, 0.12);
}
.card-count-a {
top: 1px;
}
.card-count-b {
bottom: 1px;
}
.card-reverse {
border: 10px solid #66928a;
background-image: linear-gradient(45deg, #0d5d50 25%, transparent 25%, transparent 75%, #0d5d50 75%), linear-gradient(45deg, #0d5d50 25%, transparent 25%, transparent 75%, #0d5d50 75%);
background-size: 10px 10px;
background-position: 0 0, 5px 5px;
box-sizing: border-box;
}
/* ugly hack fix */
.card.card-highlight.card-reverse:not(.grand_dragon) {
background-color: #c6f2ea;
background-image: linear-gradient(45deg, #0d5d50 25%, transparent 25%, transparent 75%, #0d5d50 75%), linear-gradient(45deg, #0d5d50 25%, transparent 25%, transparent 75%, #0d5d50 75%);
}
.slot {
box-sizing: border-box;
border-radius: 10px;
}
.slot-spare {
border: 4px dotted rgba(255, 255, 255, 0.10);
}
.slot-flower, .slot-out {
border: 2px solid rgba(255, 255, 255, 0.10);
}
.slot-tray {
background-image: linear-gradient(45deg, rgba(255, 255, 255, 0.05) 25%, transparent 25%, transparent 75%, rgba(255, 255, 255, 0.05) 75%), linear-gradient(45deg, rgba(255, 255, 255, 0.05) 25%, transparent 25%, transparent 75%, rgba(255, 255, 255, 0.05) 75%);
background-size: 10px 10px;
background-position: 0 0, 5px 5px;
}
#board {
background-color: #012f1b;
}
.btn-dragon {
background-color: #b09d6f;
font-size: 40px;
box-sizing: border-box;
border-style: none;
font-weight: bold;
text-align: center;
vertical-align: middle;
line-height: 64px;
border-radius: 50%;
box-shadow: inset 0px 2px 12px rgba(0, 0, 0, 0.9), 0px 0px 2px rgba(0, 0, 0, 0.32);
border: 2px solid black;
}
.btn-dragon[style*="_active.png"] {
background-color: #e7d7b1;
}
.btn-dragon[style*="_down.png"] {
background-color: #86754a;
}
#btn_dragon_red {
color: #ae2810;
text-shadow: 1px 1px 0 #000;
}
#btn_dragon_red:after {
content: "\004E2D";
}
#btn_dragon_green {
color: #17714e;
text-shadow: 1px 1px 0 #000;
}
#btn_dragon_green:after {
content: "\024F35";
}
#btn_dragon_white {
color: black;
text-shadow:
-1px -1px 0 #FFF,
1px -1px 0 #FFF,
-1px 1px 0 #FFF,
1px 1px 0 #FFF;
}
#btn_dragon_white:after {
content: "\00767D";
}
.card-logo {
text-align: center;
vertical-align: middle;
}
.card-logo:after {
font-size: 70px;
line-height: 102px;
}
/* .card-logo[style*="solitaire/large_icons/dragon_white.png"] {
text-shadow: 0 0 16px rgba(0, 0, 0, 0.75);
}
.card-logo[style*="solitaire/large_icons/dragon_red.png"] {
text-shadow: 0 0 16px red;
}
.card-logo[style*="solitaire/large_icons/dragon_green.png"] {
text-shadow: 0 0 16px green;
} */
.card-logo[style*="solitaire/large_icons/flower.png"]:after {
content: "\01F337";
color: red;
}
.card-logo-a[style*="solitaire/small_icons/flower.png"]:after,
.card-logo-b[style*="solitaire/small_icons/flower.png"]:after {
font-weight: bold;
content: "\01F337";
font-size: 16px;
color: red;
}
.card-logo[style*="solitaire/large_icons/dragon_white.png"]:after {
content: "\00767D";
color: black;
}
.card-logo-a[style*="solitaire/small_icons/dragon_white.png"]:after,
.card-logo-b[style*="solitaire/small_icons/dragon_white.png"]:after {
font-weight: bold;
content: "\00767D";
font-size: 16px;
color: black;
}
.card-logo[style*="solitaire/large_icons/dragon_red.png"]:after {
content: "\004E2D";
color: #ae2810;
}
.card-logo-a[style*="solitaire/small_icons/dragon_red.png"]:after,
.card-logo-b[style*="solitaire/small_icons/dragon_red.png"]:after {
font-weight: bold;
content: "\004E2D";
font-size: 16px;
color: #ae2810;
}
.card-logo[style*="solitaire/large_icons/dragon_green.png"]:after {
content: "\024F35";
color: #17714e;
}
.card-logo-a[style*="solitaire/small_icons/dragon_green.png"]:after,
.card-logo-b[style*="solitaire/small_icons/dragon_green.png"]:after {
font-weight: bold;
content: "\024F35";
font-size: 16px;
color: #17714e;
}
.slot-flower {
text-align: center;
vertical-align: middle;
}
.slot-flower:after {
line-height: 237px;
content: "\01F337";
color: transparent;
text-shadow: 0 0 0 rgba(255, 255, 255, 0.1);
font-size: 70px;
}
/* numbers */
.card-logo[style*="solitaire/large_icons/bamboo_1.png"]:after,
.card-logo[style*="solitaire/large_icons/char_1.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_1.png"]:after {
content: "\4E00";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_2.png"]:after,
.card-logo[style*="solitaire/large_icons/char_2.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_2.png"]:after {
content: "\4E8C";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_3.png"]:after,
.card-logo[style*="solitaire/large_icons/char_3.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_3.png"]:after {
content: "\4E09";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_4.png"]:after,
.card-logo[style*="solitaire/large_icons/char_4.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_4.png"]:after {
content: "\56DB";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_5.png"]:after,
.card-logo[style*="solitaire/large_icons/char_5.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_5.png"]:after {
content: "\4E94";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_6.png"]:after,
.card-logo[style*="solitaire/large_icons/char_6.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_6.png"]:after {
content: "\516D";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_7.png"]:after,
.card-logo[style*="solitaire/large_icons/char_7.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_7.png"]:after {
content: "\4E03";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_8.png"]:after,
.card-logo[style*="solitaire/large_icons/char_8.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_8.png"]:after {
content: "\516B";
opacity: 0.5;
font-size: 36px;
}
.card-logo[style*="solitaire/large_icons/bamboo_9.png"]:after,
.card-logo[style*="solitaire/large_icons/char_9.png"]:after,
.card-logo[style*="solitaire/large_icons/coins_9.png"]:after {
content: "\4E5D";
opacity: 0.5;
font-size: 36px;
}

273
css/style.css Normal file
View File

@ -0,0 +1,273 @@
html {
cursor: url(../assets/cursor_normal.png) 38 38, default;
}
body {
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol";
margin: 0;
background-color: rgb(11, 82, 55);
color: #E8F5E9;
margin-left: auto;
margin-right: auto;
max-width: 1400px;
}
@media (min-width: 1279px) {
body {
background-image: url(../assets/window.png);
background-position: center -8px;
background-size: 1502px 889px;
background-repeat: no-repeat;
background-attachment: local;
}
}
/* the canary indicates whether we can load images */
#canary {
visibility: hidden;
}
a {
color: #B3E5FC;
}
#board {
margin-left: auto;
margin-right: auto;
margin-bottom: 4em;
background-image: url(../solitaire/table_large.png);
width: 1279px;
height: 805px;
position: relative;
}
#cards {
position: absolute;
width: 100%;
height: 100%;
top: 0px;
left: 0px;
overflow: hidden;
}
.card {
width: 122px;
height: 237px;
background-image: url(../solitaire/card_front.png);
position: absolute;
-webkit-touch-callout: none;
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
z-index: 1;
}
.card.card-highlight:not(.grand_dragon) {
background-image: linear-gradient( rgba(16, 125, 76, 0.5), rgba(255, 255, 255, 0)), url(../solitaire/card_front.png);
}
.card.card-highlight.grand_dragon {
filter: brightness(1.2) !important;
}
.card.card-hotspot {
border-radius: 8px;
background-image: radial-gradient(circle, rgba(255, 255, 255, 0) 50%, rgba(20, 50, 128, 0.5) 100%), url(../solitaire/card_front.png);
}
.card-reverse {
background-image: url(../solitaire/card_back.png)
}
.card-reverse.grand_dragon {
background-image: url(../assets/card_back_upgrade.png);
background-size: cover;
background-position: center;
border: none;
background-color: transparent;
}
.card-reverse.grand_dragon.grand_dragon_2 {
background-image: url(../assets/card_back_upgrade_200.png)
}
.card-reverse .card-logo, .card-reverse .card-logo-a, .card-reverse .card-logo-b {
display: none;
}
.slot {
width: 122px;
height: 237px;
position: absolute;
/*background-color: #FF00FF;*/
}
.card-logo {
position: absolute;
width: 73px;
height: 102px;
left: 25px;
top: 67px;
}
.card-count-a, .card-count-b {
position: absolute;
font-family: sans-serif;
font-size: 24px;
font-weight: bold;
}
.card-count-a {
left: 10px;
top: 5px;
}
.card-count-b {
right: 10px;
bottom: 5px;
}
.card-count-b, .card-mini-logo.b {
-webkit-transform: rotate(180deg);
-moz-transform: rotate(180deg);
-ms-transform: rotate(180deg);
-o-transform: rotate(180deg);
filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=2);
}
.card-mini-logo-a, .card-mini-logo-b {
position: absolute;
width: 15px;
height: 15px;
}
.card-mini-logo-a {
left: 10px;
top: 40px;
}
.card-mini-logo-b {
right: 10px;
bottom: 40px;
}
.card-logo-a, .card-logo-b {
position: absolute;
width: 22px;
height: 24px;
}
.card-logo-a {
left: 6px;
top: 6px;
}
.card-logo-b {
right: 6px;
bottom: 6px;
}
.btn-dragon {
position: absolute;
left: 497px;
width: 72px;
height: 71px;
background: none;
border: none;
}
#btn_dragon_red {
top: 18px;
background-image: url('solitaire/button_red_up.png');
}
#btn_dragon_green {
top: 102px;
}
#btn_dragon_white {
top: 184px;
}
/*.ui-draggable-dragging {
visibility: hidden;
}*/
a, button, .btn-dragon, .bottom-button, .bottom-button * {
cursor: url(../assets/cursor_point.png) 38 38, pointer;
-webkit-user-select: none;
-moz-user-select: none;
user-select: none;
}
#buttons {
position: absolute;
top: 808px;
right: 0px;
left: 0px;
height: 46px;
vertical-align: middle;
line-height: 46px;
}
.bottom-button {
background-image: url(../assets/button_bottom.png);
background-color: transparent;
border: 0px;
color: white;
width: 141px;
height: 46px;
font-size: 20px;
font-family: sans-serif;
float: right;
text-align: center;
}
.bottom-button.music {
display: none;
}
.bottom-button:hover {
background-image: url(../assets/button_bottom_hover.png);
}
.info-text {
padding: 2em;
}
#image_load_error {
color: orange;
font-size: 1.5em;
}
.card-logo-display, .card-text-display {
position: relative;
display: inline-block;
width: 34px;
height: 48px;
background-color: #fafafa;
border-radius: 6px;
text-align: center;
vertical-align: middle;
}
.card-logo-display .card-logo-a {
left: 6px;
top: 12px;
}
.card-text-display {
color: black;
line-height: 48px;
font-size: 18px;
font-weight: bold;
}
.card-text-display--red {
color: #ae2810;
}
.card-text-display--green {
color: #17714e;
}
.card-text-display--white {
color: black;
}

123
index.html Normal file
View File

@ -0,0 +1,123 @@
<!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">
<meta name="Description" content="Play Shenzhen IO Solitaire online. This unique twist on standard solitaire rules offers a fresh challenge!">
<title>SHENZHEN I/O Solitaire Online</title>
<link rel="stylesheet" type="text/css" href="lib/jquery-ui.min.css">
<link rel="stylesheet" type="text/css" href="lib/jquery-ui.structure.min.css">
<link rel="stylesheet" type="text/css" href="css/style.css">
<link rel="preload" as="style" href="css/noimages.css">
<!-- Google tag (gtag.js) -->
<script async src="https://www.googletagmanager.com/gtag/js?id=G-5SR0DS0PV2"></script>
<script>
window.dataLayer = window.dataLayer || [];
function gtag(){dataLayer.push(arguments);}
gtag('js', new Date());
gtag('config', 'G-5SR0DS0PV2');
</script>
</head>
<body>
<div id="board">
<div id="cards"></div>
<div id="buttons">
<button class="bottom-button" id="newGame">New Game</button>
<button class="bottom-button" id="retryGame">Retry Game</button>
<button class="bottom-button music" id="playMusicButton">Play Music</button>
<button class="bottom-button music" id="pauseMusicButton">Pause Music</button>
<label id="toggleColorblindContainer" class="bottom-button" for="toggleColorblind">
<input type="checkbox" id="toggleColorblind" name="toggleColorblind" /> Colorblind
</label>
<span class="info-left-text">
<span id="win_count">?</span> wins
</span>
</div>
<button aria-label="Move Red Dragons" class="btn-dragon" id="btn_dragon_red"></button>
<button aria-label="Move Green Dragons" class="btn-dragon" id="btn_dragon_green"></button>
<button aria-label="Move White Dragons" class="btn-dragon" id="btn_dragon_white"></button>
</div>
<div class="info-text">
<main>
<h1>Shenzhen Solitare</h1>
<h2>How to Play</h2>
<p>
The goal of the game is to move all cards off the center.
</p>
<ul>
<li>Move numbered cards to the upper-right.</li>
<li>Move the 'Dragon' cards (with logos) to the upper-left.</li>
</ul>
<h3>Numbered Cards</h3>
<div class="card-text-display card-text-display--green">
3
</div>
<div class="card-text-display card-text-display--red">
9
</div>
<div class="card-text-display card-text-display--white">
1
</div>
<p>
Numbered cards can stack, with smaller numbers stacked on larger numbers.
</p>
<p>
Cards can't be stacked on Dragons, or on cards of the same suit.
</p>
<p>
Multiple number cards can be moved around if they're stacked correctly (in descending order with alternating suits).
</p>
<h3>Dragon Cards</h3>
<div class="card-logo-display">
<div class="card-logo-a"
style="background-image: url(&quot;solitaire/small_icons/dragon_green.png&quot;); filter: sepia(100%) saturate(10000%) hue-rotate(63deg) brightness(0.35);">
</div>
</div>
<div class="card-logo-display">
<div class="card-logo-a" style="background-image: url(&quot;solitaire/small_icons/dragon_red.png&quot;);"></div>
</div>
<div class="card-logo-display">
<div class="card-logo-a" style="background-image: url(&quot;solitaire/small_icons/dragon_white.png&quot;);">
</div>
</div>
<p>
Dragon cards can't be stacked.
</p>
<p>
If all four dragons of a suit are uncovered and a slot is available, clicking the Dragon button moves
that suit to a free slot in the upper-left.
</p>
<h3>About</h3>
<p>
Adaptation created by Taylor Gratzer. Original gameplay concept by Zachtronics, from the game
<a href="http://store.steampowered.com/app/504210/">SHENZHEN I/O</a>.
<a href="https://zachtronics.bandcamp.com/track/patience">Music</a> by Matthew S Burns.
<a href="https://github.com/Nickardson/shenzhen-solitaire">GitHub Repo</a>
</p>
<p>Ideas? Comments? <a href="http://tgratzer.com/contact">Send me a message!</a></p>
<div id="image_load_error"></div>
</main>
</div>
<script src="lib/jquery-3.7.1.min.js"></script>
<script src="lib/jquery-ui.min.js"></script>
<script src="lib/jquery.ui.touch-punch.js"></script>
<script src="lib/seedrandom.min.js"></script>
<script src="js/main.js"></script>
<img id="canary" alt="" />
</body>
</html>

1244
js/main.js Normal file

File diff suppressed because it is too large Load Diff

2
lib/jquery-3.7.1.min.js vendored Normal file

File diff suppressed because one or more lines are too long

6
lib/jquery-ui.min.css vendored Normal file
View File

@ -0,0 +1,6 @@
/*! jQuery UI - v1.13.2 - 2024-02-10
* http://jqueryui.com
* Includes: draggable.css
* Copyright jQuery Foundation and other contributors; Licensed MIT */
.ui-draggable-handle{-ms-touch-action:none;touch-action:none}

6
lib/jquery-ui.min.js vendored Normal file

File diff suppressed because one or more lines are too long

5
lib/jquery-ui.structure.min.css vendored Normal file
View File

@ -0,0 +1,5 @@
/*! jQuery UI - v1.13.2 - 2024-02-10
* http://jqueryui.com
* Copyright jQuery Foundation and other contributors; Licensed MIT */
.ui-draggable-handle{-ms-touch-action:none;touch-action:none}

182
lib/jquery.ui.touch-punch.js vendored Normal file
View File

@ -0,0 +1,182 @@
"use strict";
/*!
* jQuery UI Touch Punch 0.2.3
*
* Copyright 20112014, Dave Furfero
* Dual licensed under the MIT or GPL Version 2 licenses.
*
* Depends:
* jquery.ui.widget.js
* jquery.ui.mouse.js
*/
(function ($) {
// Detect touch support
$.support.touch = 'ontouchend' in document;
// Ignore browsers without touch support
if (!$.support.touch) {
return;
}
var mouseProto = $.ui.mouse.prototype,
_mouseInit = mouseProto._mouseInit,
_mouseDestroy = mouseProto._mouseDestroy,
touchHandled;
/**
* Simulate a mouse event based on a corresponding touch event
* @param {Object} event A touch event
* @param {String} simulatedType The corresponding mouse event
*/
function simulateMouseEvent (event, simulatedType) {
// Ignore multi-touch events
if (event.originalEvent.touches.length > 1) {
return;
}
event.preventDefault();
var touch = event.originalEvent.changedTouches[0],
simulatedEvent = document.createEvent('MouseEvents');
// Initialize the simulated mouse event using the touch event's coordinates
simulatedEvent.initMouseEvent(
simulatedType, // type
true, // bubbles
true, // cancelable
window, // view
1, // detail
touch.screenX, // screenX
touch.screenY, // screenY
touch.clientX, // clientX
touch.clientY, // clientY
false, // ctrlKey
false, // altKey
false, // shiftKey
false, // metaKey
0, // button
null // relatedTarget
);
// Dispatch the simulated event to the target element
event.target.dispatchEvent(simulatedEvent);
}
/**
* Handle the jQuery UI widget's touchstart events
* @param {Object} event The widget element's touchstart event
*/
mouseProto._touchStart = function (event) {
var self = this;
// Ignore the event if another widget is already being handled
if (touchHandled || !self._mouseCapture(event.originalEvent.changedTouches[0])) {
return;
}
// Set the flag to prevent other widgets from inheriting the touch event
touchHandled = true;
// Track movement to determine if interaction was a click
self._touchMoved = false;
// Simulate the mouseover event
simulateMouseEvent(event, 'mouseover');
// Simulate the mousemove event
simulateMouseEvent(event, 'mousemove');
// Simulate the mousedown event
simulateMouseEvent(event, 'mousedown');
};
/**
* Handle the jQuery UI widget's touchmove events
* @param {Object} event The document's touchmove event
*/
mouseProto._touchMove = function (event) {
// Ignore event if not handled
if (!touchHandled) {
return;
}
// Interaction was not a click
this._touchMoved = true;
// Simulate the mousemove event
simulateMouseEvent(event, 'mousemove');
};
/**
* Handle the jQuery UI widget's touchend events
* @param {Object} event The document's touchend event
*/
mouseProto._touchEnd = function (event) {
// Ignore event if not handled
if (!touchHandled) {
return;
}
// Simulate the mouseup event
simulateMouseEvent(event, 'mouseup');
// Simulate the mouseout event
simulateMouseEvent(event, 'mouseout');
// If the touch interaction did not move, it should trigger a click
if (!this._touchMoved) {
// Simulate the click event
simulateMouseEvent(event, 'click');
}
// Unset the flag to allow other widgets to inherit the touch event
touchHandled = false;
};
/**
* A duck punch of the $.ui.mouse _mouseInit method to support touch events.
* This method extends the widget with bound touch event handlers that
* translate touch events to mouse events and pass them to the widget's
* original mouse event handling methods.
*/
mouseProto._mouseInit = function () {
var self = this;
// Delegate the touch handlers to the widget's element
self.element.bind({
touchstart: $.proxy(self, '_touchStart'),
touchmove: $.proxy(self, '_touchMove'),
touchend: $.proxy(self, '_touchEnd')
});
// Call the original $.ui.mouse init method
_mouseInit.call(self);
};
/**
* Remove the touch event handlers
*/
mouseProto._mouseDestroy = function () {
var self = this;
// Delegate the touch handlers to the widget's element
self.element.unbind({
touchstart: $.proxy(self, '_touchStart'),
touchmove: $.proxy(self, '_touchMove'),
touchend: $.proxy(self, '_touchEnd')
});
// Call the original $.ui.mouse destroy method
_mouseDestroy.call(self);
};
})(jQuery);

1
lib/seedrandom.min.js vendored Normal file
View File

@ -0,0 +1 @@
!function(a,b,c,d,e,f,g,h,i){function j(a){var b,c=a.length,e=this,f=0,g=e.i=e.j=0,h=e.S=[];for(c||(a=[c++]);d>f;)h[f]=f++;for(f=0;d>f;f++)h[f]=h[g=s&g+a[f%c]+(b=h[f])],h[g]=b;(e.g=function(a){for(var b,c=0,f=e.i,g=e.j,h=e.S;a--;)b=h[f=s&f+1],c=c*d+h[s&(h[f]=h[g=s&g+b])+(h[g]=b)];return e.i=f,e.j=g,c})(d)}function k(a,b){var c,d=[],e=typeof a;if(b&&"object"==e)for(c in a)try{d.push(k(a[c],b-1))}catch(f){}return d.length?d:"string"==e?a:a+"\0"}function l(a,b){for(var c,d=a+"",e=0;e<d.length;)b[s&e]=s&(c^=19*b[s&e])+d.charCodeAt(e++);return n(b)}function m(c){try{return o?n(o.randomBytes(d)):(a.crypto.getRandomValues(c=new Uint8Array(d)),n(c))}catch(e){return[+new Date,a,(c=a.navigator)&&c.plugins,a.screen,n(b)]}}function n(a){return String.fromCharCode.apply(0,a)}var o,p=c.pow(d,e),q=c.pow(2,f),r=2*q,s=d-1,t=c["seed"+i]=function(a,f,g){var h=[];f=1==f?{entropy:!0}:f||{};var o=l(k(f.entropy?[a,n(b)]:null==a?m():a,3),h),s=new j(h);return l(n(s.S),b),(f.pass||g||function(a,b,d){return d?(c[i]=a,b):a})(function(){for(var a=s.g(e),b=p,c=0;q>a;)a=(a+c)*d,b*=d,c=s.g(1);for(;a>=r;)a/=2,b/=2,c>>>=1;return(a+c)/b},o,"global"in f?f.global:this==c)};if(l(c[i](),b),g&&g.exports){g.exports=t;try{o=require("crypto")}catch(u){}}else h&&h.amd&&h(function(){return t})}(this,[],Math,256,6,52,"object"==typeof module&&module,"function"==typeof define&&define,"random");

View File

@ -0,0 +1,4 @@
Copy the contents of the "textures\solitaire" folder into this folder.
You can find the folder at:
steamapps\common\SHENZHEN IO\Content\textures\solitaire

BIN
solitaire/Solitaire.ogg Executable file

Binary file not shown.

BIN
solitaire/button_green_active.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

BIN
solitaire/button_green_down.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.8 KiB

BIN
solitaire/button_green_up.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.8 KiB

BIN
solitaire/button_red_active.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

BIN
solitaire/button_red_down.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.1 KiB

BIN
solitaire/button_red_up.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.8 KiB

BIN
solitaire/button_white_active.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

BIN
solitaire/button_white_down.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.2 KiB

BIN
solitaire/button_white_up.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.2 KiB

BIN
solitaire/card_back.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

BIN
solitaire/card_back_upgrade.psd Executable file

Binary file not shown.

BIN
solitaire/card_front.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.0 KiB

BIN
solitaire/card_shadow.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

BIN
solitaire/card_texture.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.0 KiB

BIN
solitaire/large_icons/char_1.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.9 KiB

BIN
solitaire/large_icons/char_2.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

BIN
solitaire/large_icons/char_3.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

BIN
solitaire/large_icons/char_4.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

BIN
solitaire/large_icons/char_5.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

BIN
solitaire/large_icons/char_6.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

BIN
solitaire/large_icons/char_7.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

BIN
solitaire/large_icons/char_8.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

BIN
solitaire/large_icons/char_9.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

BIN
solitaire/large_icons/coins_1.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.2 KiB

BIN
solitaire/large_icons/coins_2.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

BIN
solitaire/large_icons/coins_3.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

BIN
solitaire/large_icons/coins_4.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

BIN
solitaire/large_icons/coins_5.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.0 KiB

BIN
solitaire/large_icons/coins_6.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.5 KiB

BIN
solitaire/large_icons/coins_7.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.1 KiB

BIN
solitaire/large_icons/coins_8.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

BIN
solitaire/large_icons/coins_9.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

BIN
solitaire/large_icons/flower.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.4 KiB

BIN
solitaire/small_icons/bamboo.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 KiB

BIN
solitaire/small_icons/coins.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 KiB

BIN
solitaire/small_icons/flower.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.7 KiB

BIN
solitaire/stack_side.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

BIN
solitaire/table_large.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 MiB

BIN
solitaire/table_small.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 MiB

BIN
solitaire/tutorial_large.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 MiB

BIN
solitaire/tutorial_small.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.0 MiB

BIN
solitaire/win_count.png Executable file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.7 KiB