Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 40 additions & 0 deletions src/components/Bar.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import { useDimensions, useGameState, useTheme } from "../providers";
import { Checker } from "./Checker";
import { PipCounter } from "./PipCounter";

export const Bar = () => {
const dimensions = useDimensions();
const colours = useTheme();
const gameState = useGameState();

const { barWidth, panelWidth, borderWidth, boardHeight } = dimensions;
const barPositions = (gameState?.positions ?? []).filter(
(p) => p.position === "bar",
);

return (
<>
<rect
key="bar"
x={panelWidth + borderWidth}
y={borderWidth}
width={barWidth}
height={boardHeight - borderWidth * 2}
fill={colours.borderColor}
/>
{barPositions.map(({ playerType, numberOfCheckers = 1 }) =>
[...new Array(numberOfCheckers)].map((_, i) => (
<Checker
key={`bar-${playerType}-${i}`}
playerType={playerType}
x="bar"
y={i + 1}
totalOnPoint={numberOfCheckers}
/>
)),
)}
<PipCounter key="opponent-pip-counter" playerType="opponent" />
<PipCounter key="player-pip-counter" playerType="player" />
</>
);
};
17 changes: 4 additions & 13 deletions src/components/Board.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,8 @@ import { useDimensions, useGameState, useTheme } from "../providers";
import { Checker } from "./Checker";
import { Point } from "./Point";
import { Sidebar } from "./Sidebar";
import { PipCounter } from "./PipCounter";
import { Dice } from "./Dice";
import { Bar } from "./Bar";

export const Board: React.FC = () => {
const dimensions = useDimensions();
Expand All @@ -15,7 +15,6 @@ export const Board: React.FC = () => {
const {
boardWidth,
barWidth,
panelWidth,
borderWidth,
pointWidth,
boardHeight,
Expand Down Expand Up @@ -154,7 +153,8 @@ export const Board: React.FC = () => {
{positions &&
positions.map(({ position, numberOfCheckers = 1, playerType }) => {
const checkers = [...new Array(numberOfCheckers)].map((_, i) => {
if (position === 0 || position === 25) return null;
if (position === 0 || position === 25 || position === "bar")
return null;
return (
<Checker
key={`${playerType}-${position}-${i}`}
Expand All @@ -172,16 +172,7 @@ export const Board: React.FC = () => {
);
})}
{/* Middle bar */}
<rect
key="bar"
x={panelWidth + borderWidth}
y={borderWidth}
width={barWidth}
height={boardHeight - borderWidth * 2}
fill={colours.borderColor}
/>
<PipCounter key="opponent-pip-counter" playerType="opponent" />
<PipCounter key="player-pip-counter" playerType="player" />
<Bar />
</svg>
<Sidebar key="sidebar" />
</svg>
Expand Down
34 changes: 32 additions & 2 deletions src/components/Checker.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,33 @@ import { useDimensions, usePosition, useTheme } from "../providers";
import { PlayerType } from "../types";

type CheckerProps = {
x: number;
x:
| 0
| 1
| 2
| 3
| 4
| 5
| 6
| 7
| 8
| 9
| 10
| 11
| 12
| 13
| 14
| 15
| 16
| 17
| 18
| 19
| 20
| 21
| 22
| 23
| 24
| "bar";
y: number;
playerType: PlayerType;
totalOnPoint: number;
Expand All @@ -28,10 +54,14 @@ export const Checker: React.FC<CheckerProps> = ({
: opponentCheckerBorderColor;
const pos = usePosition();
const { checkerWidth, checkerStroke } = useDimensions();
const bottomModifier = x > 12 ? 1 : -1;
const bottomModifier =
x === "bar" ? (playerType === "opponent" ? 1 : -1) : x > 12 ? 1 : -1;
const baseYOffset = checkerWidth * bottomModifier;

const barInitialOffset =
x === "bar" ? (checkerWidth / 1.8) * bottomModifier : 0;
const yOffset =
barInitialOffset +
(y - 1) * baseYOffset * (totalOnPoint > 5 ? 4 / (totalOnPoint - 1) : 1);
return (
<circle
Expand Down
1 change: 0 additions & 1 deletion src/components/Die.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,6 @@ export const Die: React.FC<DieProps> = ({ value = 2, colorSchema }) => {
);
break;
}
console.log(value);
return (
<g
transform={`translate(${panelWidth + barWidth + panelWidth / 2 - dieWidth / 2}, ${boardHeight / 2 - dieWidth / 2})`}
Expand Down
8 changes: 5 additions & 3 deletions src/components/PipCounter.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,11 @@ export const PipCounter: React.FC<PipCountProps> = ({ playerType }) => {
const pip = positions?.reduce((acc, current) => {
const isPlayer = current.playerType === playerType;
const normalisedPosition =
current.playerType === "player"
? current.position
: 25 - current.position;
current.position === "bar"
? 25
: current.playerType === "player"
? current.position
: 25 - current.position;
return isPlayer ? acc + current.numberOfCheckers * normalisedPosition : acc;
}, 0);

Expand Down
4 changes: 2 additions & 2 deletions src/components/Point.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ export const Point: React.FC<PointProps> = ({
}) => {
const { pointWidth, pointHeight, borderWidth } = useDimensions();

const { pointNumberColor, pointColor } = useTheme();
const { pointNumberColor, pointColor, altPointColor } = useTheme();

const transform = bottom ? `scale(1 -1) translate(0, ${borderWidth})` : "";

Expand All @@ -38,7 +38,7 @@ export const Point: React.FC<PointProps> = ({
</text>
<polygon
points={`${x},${y} ${x + width},${y} ${x + width / 2},${y + height}`}
fill={pointColor}
fill={odd ? pointColor : altPointColor}
fillOpacity={odd ? "1" : "0.4"}
/>
;
Expand Down
5 changes: 5 additions & 0 deletions src/helpers/calculate-base-points.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,13 @@ export const calculateBasePoints = (
checkerWidth,
boardHeight,
checkerStroke,
boardWidth,
} = dimensions;
return {
bar: {
x: boardWidth / 2,
y: boardHeight / 2,
},
24: {
x: borderWidth + pointWidth / 2,
y: borderWidth + checkerWidth / 2 + checkerStroke,
Expand Down
2 changes: 1 addition & 1 deletion src/helpers/presets.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ export const presets = {
borderColor: "#ff7f50",
pointColor: "#008080",
pointNumberColor: "#000",
altPointColor: "#ffd700",
altPointColor: "#00d4d4",
playerCheckerColor: "#fff",
playerCheckerBorderColor: "#000",
opponentCheckerColor: "#000",
Expand Down
6 changes: 3 additions & 3 deletions src/providers/PositionProvider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ import React, { createContext, useContext } from "react";
import { calculateBasePoints } from "../helpers/calculate-base-points";
import { useDimensions } from "./DimensionProvider";

const PositionContext = createContext<Record<number, { x: number; y: number }>>(
{},
);
const PositionContext = createContext<
Record<number | "bar", { x: number; y: number }>
>({ bar: { x: 0, y: 0 } });

export const usePosition = () => useContext(PositionContext);

Expand Down
3 changes: 2 additions & 1 deletion src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,8 @@ type Position = {
| 22
| 23
| 24
| 25;
| 25
| "bar";
numberOfCheckers:
| 1
| 2
Expand Down
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 2 additions & 0 deletions test-harness/tests/presets.ts
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,8 @@ export const positionsPresets: Record<string, BoardStateState["positions"]> = {
{ position: 23, playerType: "opponent", numberOfCheckers: 15 },
{ position: 24, playerType: "opponent", numberOfCheckers: 15 },
{ position: 25, playerType: "opponent", numberOfCheckers: 15 },
{ position: "bar", playerType: "opponent", numberOfCheckers: 15 },
{ position: "bar", playerType: "player", numberOfCheckers: 15 },
],
random: randomPositions(),
};
Expand Down
Loading