Skip to content

Commit

Permalink
overlays
Browse files Browse the repository at this point in the history
  • Loading branch information
gtanczyk committed Oct 25, 2024
1 parent 9ab7f7d commit 77f1d6f
Show file tree
Hide file tree
Showing 4 changed files with 105 additions and 14 deletions.
2 changes: 1 addition & 1 deletion games/masterplan/src/screens/battle/battle-styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,7 @@ export const BattleStyles = createGlobalStyle`
font-size: 15px;
bottom: 5px;
left: 5px;
width: 100%;
}
#battle-result span {
Expand All @@ -127,7 +128,6 @@ export const BattleStyles = createGlobalStyle`
font-size: 14px;
color: white;
text-shadow: 0 2px 4px rgba(0, 0, 0, 0.2);
min-width: 100px;
}
#battle-time:before {
Expand Down
10 changes: 8 additions & 2 deletions games/masterplan/src/screens/designer/canvas-grid.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -206,9 +206,15 @@ CanvasGrid.displayName = 'CanvasGrid';

const CanvasContainer = styled.canvas`
position: absolute;
transform: translate(-50%, -50%);
&[data-is-player-area='false'] {
transform: translateX(-50%);
bottom: 0;
}
&[data-is-player-area='true'] {
transform: translateX(-50%);
top: 0;
}
left: 50%;
top: 50%;
max-width: 90vw;
max-height: 50vh;
`;
59 changes: 55 additions & 4 deletions games/masterplan/src/screens/designer/designer-screen.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,15 @@ export const DesignerScreen: React.FC<DesignerScreenProps> = ({ onStartBattle, i
const [oppositionUnits, setOppositionUnits] = useState<Unit[]>([]);
const [showInfoPanel, setShowInfoPanel] = useState(false);
const [infoPanelPosition, setInfoPanelPosition] = useState({ x: 0, y: 0 });
const [hasInteracted, setHasInteracted] = useState(false);
const terrainData = useMemo<TerrainData>(() => {
return generateTerrain(SOLDIER_WIDTH);
}, []);
const containerRef = useRef<HTMLDivElement>(null);

const { selectedUnit, handleUnitSelect, setSelectedUnit } = useUnitSelection(playerUnits);
const { handleDragStart, handleDragMove, handleDragEnd, isDragging } = useUnitDrag(playerUnits, setPlayerUnits);

const { generateOppositionPlan, updateOppositionPlan } = useOppositionAI();

useEffect(() => {
Expand All @@ -50,11 +52,20 @@ export const DesignerScreen: React.FC<DesignerScreenProps> = ({ onStartBattle, i

const handleCellClick = useCallback(
(col: number, row: number) => {
setHasInteracted(true);
handleUnitSelect(col, row);
},
[handleUnitSelect],
);

const handlePlayerDragStart = useCallback(
(e: React.MouseEvent<HTMLCanvasElement> | React.TouchEvent<HTMLCanvasElement>) => {
setHasInteracted(true);
handleDragStart(e);
},
[handleDragStart],
);

useEffect(() => {
if (isDragging) {
setShowInfoPanel(false);
Expand Down Expand Up @@ -84,7 +95,7 @@ export const DesignerScreen: React.FC<DesignerScreenProps> = ({ onStartBattle, i

return (
<DesignerContainer ref={containerRef}>
<OppositionPlan units={oppositionUnits} terrainData={terrainData} />
<OppositionPlan units={oppositionUnits} terrainData={terrainData} hasInteracted={hasInteracted} />
<PlayerPlanContainer>
<CanvasGrid
isPlayerArea={true}
Expand All @@ -95,15 +106,20 @@ export const DesignerScreen: React.FC<DesignerScreenProps> = ({ onStartBattle, i
units={playerUnits}
selectedUnitId={selectedUnit?.id || null}
onCellClick={handleCellClick}
onMouseDown={handleDragStart}
onMouseDown={handlePlayerDragStart}
onMouseMove={handleDragMove}
onMouseUp={handleDragEnd}
onTouchStart={handleDragStart}
onTouchStart={handlePlayerDragStart}
onTouchMove={handleDragMove}
onTouchEnd={handleDragEnd}
onModifyUnit={handleUnitModify}
terrainData={terrainData}
/>
{!hasInteracted && (
<EditableAreaOverlay>
<OverlayText>Click or drag units to edit your battle plan</OverlayText>
</EditableAreaOverlay>
)}
</PlayerPlanContainer>
{showInfoPanel && selectedUnit && (
<UnitInfoPanel unit={selectedUnit} position={infoPanelPosition} onModifyUnit={handleUnitModify} />
Expand Down Expand Up @@ -138,6 +154,41 @@ const PlayerPlanContainer = styled.div`
position: relative;
`;

const EditableAreaOverlay = styled.div`
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: rgba(255, 255, 255, 0.1);
display: flex;
justify-content: center;
align-items: center;
pointer-events: none;
animation: pulse 2s infinite;
@keyframes pulse {
0% {
background: rgba(255, 255, 255, 0.1);
}
50% {
background: rgba(255, 255, 255, 0.2);
}
100% {
background: rgba(255, 255, 255, 0.1);
}
}
`;

const OverlayText = styled.div`
color: white;
font-size: 24px;
text-shadow: 2px 2px 4px rgba(0, 0, 0, 0.5);
background: rgba(0, 0, 0, 0.7);
padding: 16px 32px;
border-radius: 8px;
`;

const DesignerControls = styled.div`
position: absolute;
top: 20px;
Expand All @@ -161,4 +212,4 @@ const StartBattleButton = styled.button`
&:hover {
background: rgba(0, 0, 0, 0.8);
}
`;
`;
48 changes: 41 additions & 7 deletions games/masterplan/src/screens/designer/opposition-plan.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,10 @@ import { TerrainData } from '../battle/game/terrain/terrain-generator';
interface OppositionPlanProps {
units: Unit[];
terrainData: TerrainData;
hasInteracted?: boolean;
}

export const OppositionPlan: React.FC<OppositionPlanProps> = ({ units, terrainData }) => {
export const OppositionPlan: React.FC<OppositionPlanProps> = ({ units, terrainData, hasInteracted = true }) => {
// Dummy handlers for CanvasGrid props (no interactions allowed for opposition plan)
const dummyHandler = () => {};

Expand All @@ -34,6 +35,11 @@ export const OppositionPlan: React.FC<OppositionPlanProps> = ({ units, terrainDa
isPlayerArea={false}
terrainData={terrainData}
/>
{!hasInteracted && (
<OppositionOverlay>
<OverlayText>Enemy battle plan</OverlayText>
</OppositionOverlay>
)}
</OppositionPlanContainer>
);
};
Expand All @@ -44,9 +50,37 @@ const OppositionPlanContainer = styled.div`
position: relative;
`;

// TODO: Implement more advanced AI for opposition plan generation
// This could include:
// - Analyzing the player's plan and adapting the opposition's strategy
// - Implementing different difficulty levels
// - Adding randomness to make each game unique
// - Considering various battle strategies and unit combinations
const OppositionOverlay = styled.div`
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: rgba(255, 0, 0, 0.1);
display: flex;
justify-content: center;
align-items: center;
pointer-events: none;
animation: pulseRed 2s infinite;
@keyframes pulseRed {
0% {
background: rgba(255, 0, 0, 0.1);
}
50% {
background: rgba(255, 0, 0, 0.2);
}
100% {
background: rgba(255, 0, 0, 0.1);
}
}
`;

const OverlayText = styled.div`
color: white;
font-size: 24px;
text-shadow: 2px 2px 4px rgba(0, 0, 0, 0.5);
background: rgba(0, 0, 0, 0.7);
padding: 16px 32px;
border-radius: 8px;
`;

0 comments on commit 77f1d6f

Please sign in to comment.