Skip to content

Commit 9a86029

Browse files
Implement TMX support for maps (#14)
1 parent cfb3366 commit 9a86029

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

67 files changed

+8663
-736
lines changed

README.md

+73-62
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ The Open-Source IO Shooter is an open-source multiplayer game in the browser (de
66

77
**Desktop version**
88

9-
![banner](images/banner.jpg "In-game screenshot of desktop")
9+
![banner](images/banner.png "In-game screenshot of desktop")
1010

1111
**Mobile version**
1212

@@ -100,66 +100,75 @@ This project is a monorepo (with the help of Yarn workspaces). It contains the f
100100

101101
### Maps
102102

103-
Anyone can create their own map pretty easily in TOSIOS.
104-
105-
Maps are composed of `arrays` of `arrays` where each number greater than `0` represents a `wall` to which entities will collide.
106-
107-
When creating a map each number represents a specific wall sprite that will be drawn:
108-
* `1` for a wall on the left
109-
* `2` for a wall on the top
110-
* `3` for a wall on the right
111-
* `4` for a wall on the bottom
112-
* `5` for a wall on the bottom-left (concave angle)
113-
* `6` for a wall on the bottom-right (concave angle)
114-
* `7` for a wall on the top-left (convexe angle)
115-
* `8` for a wall on the bottom-right (convexe angle)
116-
* `9` for a left door
117-
* `10` for a right door
118-
* `11` for a torch
119-
* `12` for a ladder (player spawner)
120-
121-
Example:
122-
123-
```js
124-
[
125-
[1, 2, 9, 10, 2, 3],
126-
[1, 11, 0, 0, 11, 3],
127-
[1, 0, 0, 0, 0, 3],
128-
[1, 0, 7, 8, 0, 3],
129-
[1, 0, 4, 4, 0, 3],
130-
[1, 0, 0, 0, 0, 3],
131-
[5, 4, 4, 4, 4, 6],
132-
]
133-
```
134-
135-
will render into
136-
137-
<img src="images/map.jpg" alt="drawing" width="200"/>
138-
139-
**Creating your own map**
140-
141-
If you want to add your own map to the game:
142-
143-
1. Add a new file in `package/common/maps` containing your map template as shown in the example (e.g. `package/common/maps/gigantic.ts`).
144-
2. Open `package/common/maps/index.ts`, and add the following statements:
145-
```typescript
146-
///...
147-
import gigantic from './gigantic';
148-
//...
149-
const MAPS = {
150-
//...
151-
gigantic,
152-
};
153-
//...
154-
export const List: Types.IListItem[] = [
155-
//...
156-
{ value: 'gigantic', title: 'Gigantic' }, // Used for the dropdown on the client
157-
];
158-
```
159-
3. Open `package/common/types.ts`, and add your map `value` key to `MapNameType`:
160-
```typescript
161-
export type MapNameType = 'small' | 'long' | 'big' | 'gigantic';
162-
```
103+
Anyone can create their own map to use in TOSIOS.
104+
105+
#### How to create my map?
106+
107+
The maps available in TOSIOS have all been created thanks to [Tiled Map Editor](https://www.mapeditor.org/) (TME). You must first download this software in order to start creating your own map. I also invite you to read some tutorial for an easier beginning.
108+
109+
The most important concepts to create a functional map are `layers` and `tilesets` (I invite you to open one of the existing map in TME to familiarize yourself with how maps are structured. It will make things 10x easier if you have a living example under your eyes).
110+
111+
**Layers**
112+
113+
A `layer` is where your tiles are placed to form a map. You can combine multiple `layers` on top of each other so that you can get a crate over a ground tile, or a spider web over a wall for example.
114+
115+
There are two reserved layers that should be present at all time (although not rendered):
116+
117+
* `collisions`: for the client and server to know where the player can move or not (ex: walls or pits), or shoot through (ex: pits or small rocks).
118+
* `spawners`: for the server to determine the starting position of a player.
119+
120+
Other than that, you can add as many `layers` as you want and they will be rendered by `PIXI.js` in a WYSIWYG manner (order is maintained).
121+
122+
Although in the `dungeon.png` spritesheet I use colored tiles to represent `collisions` (light red and light blue) and spawners (deep red), you can use any tile you want as it won't be rendered anyway.
123+
124+
<img src="images/tme-layers.png" alt="drawing"/>
125+
126+
**Tilesets**
127+
128+
The `tilesets` is where lie the splitted spritesheet and its collision, animated and spawner tiles.
129+
130+
When defining which tile will be used for collisions it is very important to set its `type` field to either:
131+
132+
* `half`: a `player` CAN'T go through, but a `bullet` CAN go through.
133+
* `full`: a `player` CAN'T go through, and a `bullet` CAN'T go through.
134+
135+
This can be done by selecting a tile in the tilesets editor, and entering its `type` on the left pane.
136+
137+
<img src="images/tme-tilesets.png" alt="The collision tile (red) is selected"/>
138+
139+
#### How to add my map to the game?
140+
141+
If you want to add your map to the game:
142+
143+
1. If you have a custom spritesheet image, add it in `/packages/client/src/images/maps/custom.png`
144+
2. Open `/packages/client/src/images/maps/index.ts`, and add the following statements:
145+
```typescript
146+
import gigantic from './gigantic.png';
147+
import custom from './custom.png'; // <- Add this line
148+
149+
export const SpriteSheets: { [key: string]: string } = {
150+
'dungeon.png': dungeon,
151+
'custom.png': custom, // <- Add this line
152+
};
153+
```
154+
3. Add your map file (TMX as JSON) in `/packages/common/maps/custom.json`.
155+
4. Open `/packages/common/maps/index.ts`:
156+
```typescript
157+
// ...
158+
import gigantic from './gigantic.json';
159+
import custom from './custom.json'; // <- Add this line
160+
161+
export const List: { [key: string]: TMX.IMap } = {
162+
gigantic,
163+
custom, // <- Add this line
164+
};
165+
```
166+
5. Open `/packages/common/constants.ts`:
167+
```typescript
168+
// ...
169+
export const MAPS_NAMES = ['gigantic', 'custom']; // <- Add this entry
170+
// ...
171+
```
163172

164173
## Roadmap for 1.0.0 (Q4 2019)
165174

@@ -173,10 +182,10 @@ This is not an exhaustive, nor final, features list but it will give you a good
173182
* ~Add smoother bullets.~ DONE
174183
* ~Implement a R-Tree for performances.~ DONE
175184
* ~Add players spawner object instead of randomized points.~ DONE
185+
* ~Add support for JSON TMX format (Tiled).~ DONE
176186
* Add a Team Death Match mode.
177187
* Add a force shield to deflect bullets.
178188
* Add some monsters that attack players.
179-
* Add support for JSON TMX format (Tiled).
180189

181190
## Special thanks
182191

@@ -186,6 +195,8 @@ Thanks to the [PIXI.js](https://github.com/pixijs/pixi.js) team for their incred
186195

187196
Thanks to [@pixel_poem](https://twitter.com/pixel_poem) for the art package he published on Itch.io which made this game looks cool instantly.
188197

198+
Thanks to [@thorbjorn81](https://twitter.com/thorbjorn81) for the many years of work on the [Tiled](https://github.com/bjorn/tiled) map editor.
199+
189200
## Licenses
190201

191202
This project is under the [MIT](https://github.com/halftheopposite/tosios/blob/master/LICENSE) license.

images/banner.jpg

-78.1 KB
Binary file not shown.

images/banner.png

332 KB
Loading

images/map.jpg

-34.8 KB
Binary file not shown.

images/tme-layers.png

356 KB
Loading

images/tme-tilesets.png

131 KB
Loading

packages/client/src/components/Select.tsx

+7-3
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import { Types } from '@tosios/common';
21
import React, { CSSProperties, SyntheticEvent } from 'react';
32

43
const SELECT: CSSProperties = {
@@ -13,9 +12,14 @@ const SELECT: CSSProperties = {
1312
maxWidth: '100%',
1413
};
1514

16-
export default function (props: {
15+
export interface IListItem {
16+
value: string | number;
17+
title: string;
18+
}
19+
20+
export function Select(props: {
1721
value?: any;
18-
values: Types.IListItem[];
22+
values: IListItem[];
1923
style?: CSSProperties;
2024
onChange?: (event: SyntheticEvent) => void;
2125
}): React.ReactElement {

packages/client/src/components/index.ts

+1-2
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,10 @@ import GitHub from './GitHub';
44
import Inline from './Inline';
55
import Input from './Input';
66
import Room from './Room';
7-
import Select from './Select';
87
import Separator from './Separator';
98
import Space from './Space';
109
import View from './View';
10+
export * from './Select';
1111

1212
export {
1313
Box,
@@ -16,7 +16,6 @@ export {
1616
Inline,
1717
Input,
1818
Room,
19-
Select,
2019
Separator,
2120
Space,
2221
View,

packages/client/src/entities/Ground.ts

-35
This file was deleted.

packages/client/src/entities/Wall.ts

-74
This file was deleted.

packages/client/src/entities/index.ts

-4
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,9 @@
11
import Bullet from './Bullet';
2-
import Ground from './Ground';
32
import Player from './Player';
43
import Prop from './Prop';
5-
import Wall from './Wall';
64

75
export {
86
Bullet,
9-
Ground,
107
Player,
118
Prop,
12-
Wall,
139
};
5.47 KB
Loading
+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
import dungeon from './dungeon.png';
2+
3+
// This is where you want to reference images needed by your maps
4+
export const SpriteSheets: { [key: string]: string } = {
5+
'dungeon.png': dungeon,
6+
};
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.

packages/client/src/images/textures/ground/index.ts

-18
This file was deleted.
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,15 @@
1-
import * as Grounds from './ground';
21
import * as GUI from './gui';
32
import * as Inputs from './inputs';
43
import * as Particles from './particle';
54
import * as Players from './player';
65
import * as Props from './prop';
7-
import * as Walls from './wall';
86
import * as Weapons from './weapon';
97

108
export {
11-
Grounds as GroundTextures,
129
GUI as GUITextures,
1310
Inputs as InputsTextures,
1411
Particles as ParticleTextures,
1512
Players as PlayerTextures,
1613
Props as PropTextures,
17-
Walls as WallTextures,
1814
Weapons as WeaponTextures,
1915
};
-432 Bytes
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.

0 commit comments

Comments
 (0)