40 #define SCREEN_INITIAL_WIDTH 1280
41 #define SCREEN_INITIAL_HEIGHT 1024
53 typedef typename GC::CORE_CONFIG CC;
54 typedef typename CC::PARAM_CONFIG P;
55 typedef typename CC::ATOM_TYPE T;
56 enum { W = GC::GRID_WIDTH};
57 enum { H = GC::GRID_HEIGHT};
58 enum { R = P::EVENT_WINDOW_RADIUS};
59 enum { TILE_SIDE_CACHE_SITES = P::TILE_WIDTH};
60 enum { TILE_SIDE_LIVE_SITES = TILE_SIDE_CACHE_SITES - 2*R};
61 enum { MAX_BUCKET_FILL_DEPTH = 10000 };
63 static const u32 EVENT_WINDOW_RADIUS = R;
64 static const u32 GRID_WIDTH_TILES = W;
65 static const u32 GRID_HEIGHT_TILES = H;
67 static const u32 GRID_WIDTH_LIVE_SITES = W * TILE_SIDE_LIVE_SITES;
68 static const u32 GRID_HEIGHT_LIVE_TILES = H * TILE_SIDE_LIVE_SITES;
76 SPoint m_leftButtonDragStart;
77 SPoint m_leftButtonGridStart;
78 bool m_paintingEnabled;
81 u32 m_bucketFillStartType;
90 m_paintingEnabled(
false),
91 m_bucketFillStartType(0),
92 m_cloneOrigin(-1, -1),
93 m_cloneDestination(-1, -1)
95 SetName(
"Grid Panel");
96 SetDimensions(SCREEN_INITIAL_WIDTH,
97 SCREEN_INITIAL_HEIGHT);
98 SetRenderPoint(
SPoint(0, 0));
105 m_atomViewPanel.SetName(
"AtomViewer");
106 m_atomViewPanel.SetRenderPoint(
SPoint(326, 0));
107 m_atomViewPanel.SetBackground(Drawing::BLACK);
108 m_atomViewPanel.SetForeground(Drawing::GREY70);
109 m_atomViewPanel.SetVisibility(
false);
111 Panel::Insert(&m_atomViewPanel, NULL);
116 return &m_atomViewPanel;
119 void SetGrid(
OurGrid* mainGrid)
121 m_mainGrid = mainGrid;
122 m_atomViewPanel.SetGrid(m_mainGrid);
125 void ToggleAtomViewPanel()
127 m_atomViewPanel.ToggleVisibility();
130 void ToggleDrawAtomsAsSquares()
134 m_grend->ToggleDrawAtomsAsSquares();
145 m_toolboxPanel = toolboxPanel;
146 m_atomViewPanel.SetToolboxPanel(m_toolboxPanel);
149 void SetPaintingEnabled(
bool isPaintingEnabled)
151 m_paintingEnabled = isPaintingEnabled;
154 void DeselectAtomAndTile()
156 m_grend->DeselectTile();
157 m_grend->DeselectAtom();
158 m_cloneOrigin.
Set(-1, -1);
159 m_grend->SetCloneOrigin(m_cloneOrigin);
160 m_atomViewPanel.SetAtom(NULL);
168 m_grend->RenderGrid(drawing, *m_mainGrid, m_toolboxPanel->GetBrushSize());
174 pt.
Set(mbe.m_event.button.x - pt.
GetX(),
175 mbe.m_event.button.y - pt.
GetY());
177 m_grend->SelectTile(*m_mainGrid, pt);
180 void HandleAtomSelectorTool(MouseButtonEvent& mbe)
182 HandleAtomSelectorTool(mbe.m_event.button.button,
183 SPoint(mbe.m_event.button.x,
184 mbe.m_event.button.y));
187 void HandlePencilTool(MouseButtonEvent& mbe)
189 HandlePencilTool(mbe.m_event.button.button,
190 SPoint(mbe.m_event.button.x,
191 mbe.m_event.button.y));
194 void HandleBrushTool(MouseButtonEvent& mbe)
196 HandleBrushTool(mbe.m_event.button.button,
197 SPoint(mbe.m_event.button.x,
198 mbe.m_event.button.y));
201 void HandleEraserTool(MouseButtonEvent& mbe)
203 HandleEraserTool(mbe.m_event.button.button,
204 SPoint(mbe.m_event.button.x,
205 mbe.m_event.button.y));
208 void HandleBucketTool(MouseButtonEvent& mbe)
210 HandleBucketTool(mbe.m_event.button.button,
211 SPoint(mbe.m_event.button.x,
212 mbe.m_event.button.y));
215 void HandleXRayTool(MouseButtonEvent& mbe)
217 HandleXRayTool(mbe.m_event.button.button,
218 SPoint(mbe.m_event.button.x,
219 mbe.m_event.button.y));
222 void HandleAirbrushTool(MouseButtonEvent& mbe)
224 HandleAirbrushTool(mbe.m_event.button.button,
225 SPoint(mbe.m_event.button.x,
226 mbe.m_event.button.y));
229 SPoint ClickPointToAtom(
const SPoint& clickPt)
232 abs.Set(clickPt.GetX() - abs.GetX(),
233 clickPt.GetY() - abs.GetY());
235 TileRenderer& tileRenderer = m_grend->GetTileRenderer();
236 const SPoint& offset = tileRenderer.GetWindowTL();
239 abs.
Set(abs.GetX() - offset.GetX(),
240 abs.GetY() - offset.GetY());
242 u32 atomSize = tileRenderer.GetAtomSize();
244 abs.Set(abs.GetX() / atomSize,
245 abs.GetY() / atomSize);
250 void HandleCloneTool(MouseButtonEvent& mbe)
252 if(mbe.m_event.button.button == SDL_BUTTON_LEFT)
254 m_cloneDestination = ClickPointToAtom(SPoint(mbe.m_event.button.x,
255 mbe.m_event.button.y));
257 HandleCloneTool(mbe.m_event.button.button,
258 SPoint(mbe.m_event.button.x,
259 mbe.m_event.button.y));
262 void HandleAtomSelectorTool(u8 button, SPoint clickPt)
265 pt.Set(clickPt.GetX() - pt.GetX(),
266 clickPt.GetY() - pt.GetY());
268 m_grend->SelectAtom(*m_mainGrid, pt);
269 SPoint selectedAtom = m_grend->GetSelectedAtom();
270 m_atomViewPanel.SetAtom(m_mainGrid->GetWritableAtom(selectedAtom));
273 void HandlePencilTool(u8 button, SPoint clickPt)
275 T atom = (button == SDL_BUTTON_LEFT) ?
276 m_toolboxPanel->GetPrimaryElement()->GetDefaultAtom() :
277 m_toolboxPanel->GetSecondaryElement()->GetDefaultAtom();
279 PaintAtom(button, clickPt, 0, atom, TOOL_PENCIL);
282 void HandleBrushTool(u8 button, SPoint clickPt)
284 T atom = (button == SDL_BUTTON_LEFT) ?
285 m_toolboxPanel->GetPrimaryElement()->GetDefaultAtom() :
286 m_toolboxPanel->GetSecondaryElement()->GetDefaultAtom();
288 PaintAtom(button, clickPt, (s32)m_toolboxPanel->GetBrushSize(), atom, TOOL_BRUSH);
291 void HandleAirbrushTool(u8 button, SPoint clickPt)
293 T atom = (button == SDL_BUTTON_LEFT) ?
294 m_toolboxPanel->GetPrimaryElement()->GetDefaultAtom() :
295 m_toolboxPanel->GetSecondaryElement()->GetDefaultAtom();
297 PaintAtom(button, clickPt, (s32)m_toolboxPanel->GetBrushSize(), atom, TOOL_AIRBRUSH);
300 void HandleEraserTool(u8 button, SPoint clickPt)
302 PaintAtom(button, clickPt, (s32)m_toolboxPanel->GetBrushSize(),
303 Element_Empty<CC>::THE_INSTANCE.GetDefaultAtom(), TOOL_ERASER);
306 void HandleBucketTool(u8 button, SPoint clickPt)
308 T atom = (button == SDL_BUTTON_LEFT) ?
309 m_toolboxPanel->GetPrimaryElement()->GetDefaultAtom() :
310 m_toolboxPanel->GetSecondaryElement()->GetDefaultAtom();
312 PaintAtom(button, clickPt, 0, atom, TOOL_BUCKET);
315 void HandleXRayTool(u8 button, SPoint clickPt)
317 PaintAtom(button, clickPt, (s32)m_toolboxPanel->GetBrushSize(),
318 Element_Empty<CC>::THE_INSTANCE.GetDefaultAtom(), TOOL_XRAY);
321 void HandleCloneTool(u8 button, SPoint clickPt)
323 PaintAtom(button, clickPt, (s32)m_toolboxPanel->GetBrushSize(),
324 Element_Empty<CC>::THE_INSTANCE.GetDefaultAtom(), TOOL_CLONE);
327 void PaintAtom(u8 button, SPoint& clickPt, s32 brushSize,
328 const T& atom, EditingTool tool)
332 if(!m_grend->IsRenderingTilesSeparated())
334 Grid<GC>& grid = *m_mainGrid;
335 SPoint cp = ClickPointToAtom(clickPt);
341 const s32 brushSqr = brushSize * brushSize;
343 for(s32 y = -brushSize; y <= brushSize; y++)
346 for(s32 x = -brushSize; x <= brushSize; x++)
348 SPoint pt(cp.GetX() + x, cp.GetY() + y);
349 if(((x * x) + ysqr) <= brushSqr &&
350 grid.MapGridToTile(pt, tile, site))
352 if(tool == TOOL_XRAY)
354 grid.MaybeXRayAtom(pt);
356 else if(tool == TOOL_CLONE)
358 if(button == SDL_BUTTON_RIGHT)
361 if(grid.MapGridToTile(cp, tile, site))
363 m_cloneOrigin.
Set(cp.GetX(), cp.GetY());
364 m_grend->SetCloneOrigin(m_cloneOrigin);
370 if(m_cloneOrigin.
GetX() >= 0 && m_cloneOrigin.
GetY() >= 0)
372 SPoint clonePt(m_cloneOrigin.
GetX() +
373 (pt.GetX() - m_cloneDestination.
GetX()),
374 m_cloneOrigin.
GetY() +
375 (pt.GetY() - m_cloneDestination.
GetY()));
377 if(grid.MapGridToTile(clonePt, tile, site))
379 const T* a = grid.GetAtom(clonePt);
380 grid.PlaceAtom(*a, pt);
385 else if((tool != TOOL_AIRBRUSH) ||
386 (m_mainGrid->GetRandom().
OneIn(50)))
388 grid.PlaceAtom(atom, SPoint(cp.GetX() + x, cp.GetY() + y));
394 else if(cp.GetX() >= 0 && cp.GetY() >= 0 &&
395 cp.GetX() < TILE_SIDE_LIVE_SITES * W &&
396 cp.GetY() < TILE_SIDE_LIVE_SITES * H)
398 if(tool == TOOL_BUCKET)
401 if(grid.MapGridToTile(cp, tile, site))
403 m_bucketFillStartType = grid.GetTile(tile).GetAtom(site)->GetType();
404 if(m_bucketFillStartType != atom.GetType())
406 BucketFill(grid, atom, cp, MAX_BUCKET_FILL_DEPTH);
410 else if(tool == TOOL_CLONE)
412 if(button == SDL_BUTTON_RIGHT)
415 if(grid.MapGridToTile(cp, tile, site))
417 m_cloneOrigin.
Set(cp.GetX(), cp.GetY());
418 LOG.
Debug(
"Clone Origin Set: (%d, %d)", cp.GetX(), cp.GetY());
423 SPoint clonePt(m_cloneOrigin.
GetX() +
424 (cp.GetX() - m_cloneDestination.
GetX()),
425 m_cloneOrigin.
GetY() +
426 (cp.GetY() - m_cloneDestination.
GetY()));
428 LOG.
Debug(
"Cloning from (%d, %d) to (%d, %d) [clone dest = (%d, %d)]",
429 clonePt.GetX(), clonePt.GetY(),
430 cp.GetX(), cp.GetY(),
431 m_cloneDestination.
GetX(), m_cloneDestination.
GetY());
432 if(grid.MapGridToTile(clonePt, tile, site))
434 const T* a = grid.GetAtom(clonePt);
435 grid.PlaceAtom(*a, cp);
441 grid.PlaceAtom(atom, cp);
447 void BucketFill(Grid<GC>& grid,
const T& atom, SPoint& pt, u32 depth)
449 grid.PlaceAtom(atom, pt);
451 for(u32 i = MDist<1>::get().GetFirstIndex(1); i <= MDist<1>::get().GetLastIndex(1); i++)
454 npt.Add(pt.GetX(), pt.GetY());
456 if(npt.GetX() >= 0 && npt.GetY() >= 0 &&
457 npt.GetX() < TILE_SIDE_LIVE_SITES * W &&
458 npt.GetY() < TILE_SIDE_LIVE_SITES * H)
460 if(Atom<CC>::IsType(*grid.GetAtom(npt),
461 m_bucketFillStartType))
465 BucketFill(grid, atom, npt, depth - 1);
474 SDL_MouseButtonEvent &
event = mbe.m_event.button;
475 if(event.type == SDL_MOUSEBUTTONDOWN)
479 event.y - pt.
GetY());
481 switch (event.button)
483 case SDL_BUTTON_LEFT:
484 m_leftButtonDragStart = pt;
485 m_leftButtonGridStart = m_grend->GetDrawOrigin();
487 case SDL_BUTTON_MIDDLE:
488 case SDL_BUTTON_RIGHT:
489 if(!mbe.m_keyboard.CtrlHeld() && m_paintingEnabled)
491 switch(mbe.m_selectedTool)
494 HandleSelectorTool(mbe);
496 case TOOL_ATOM_SELECTOR:
497 HandleAtomSelectorTool(mbe);
500 HandlePencilTool(mbe);
503 HandleEraserTool(mbe);
506 HandleBrushTool(mbe);
509 HandleBucketTool(mbe);
515 HandleCloneTool(mbe);
518 HandleAirbrushTool(mbe);
525 case SDL_BUTTON_WHEELUP:
526 m_grend->IncreaseAtomSize(pt);
528 case SDL_BUTTON_WHEELDOWN:
529 m_grend->DecreaseAtomSize(pt);
538 SDL_MouseMotionEvent &
event = mbe.m_event.motion;
539 if (mbe.m_keyboard.CtrlHeld())
541 if(mbe.m_buttonMask & (1 << SDL_BUTTON_LEFT))
543 SPoint nowAt(event.x, event.y);
544 SPoint delta = nowAt - m_leftButtonDragStart;
545 m_grend->SetDrawOrigin(m_leftButtonGridStart+delta);
551 if(mbe.m_buttonMask & (1 << SDL_BUTTON_LEFT))
553 mask = SDL_BUTTON_LEFT;
555 else if(mbe.m_buttonMask & (1 << SDL_BUTTON_RIGHT))
557 mask = SDL_BUTTON_RIGHT;
560 m_grend->SetHoveredAtom(*m_mainGrid,
SPoint(event.x, event.y));
564 m_grend->SetHoveredAtom(*m_mainGrid,
SPoint(event.x, event.y));
566 else if(mask && !mbe.m_keyboard.CtrlHeld() && m_paintingEnabled)
568 switch(mbe.m_selectedTool)
571 HandlePencilTool(mask,
SPoint(event.x, event.y));
574 HandleEraserTool(mask,
SPoint(event.x, event.y));
577 HandleBrushTool(mask,
SPoint(event.x, event.y));
580 HandleXRayTool(mask,
SPoint(event.x, event.y));
582 case TOOL_ATOM_SELECTOR:
583 HandleAtomSelectorTool(mask,
SPoint(event.x, event.y));
586 HandleCloneTool(mask,
SPoint(event.x, event.y));
589 HandleAirbrushTool(mask,
SPoint(event.x, event.y));
598 m_grend->DeselectHoveredAtom();
u32 SetForeground(const u32 color)
Definition: Panel.h:256
virtual void PaintComponent(Drawing &drawing)
Definition: GridPanel.h:164
void Set(T x, T y)
Definition: Point.tcc:183
bool OneIn(u32 odds)
Definition: Random.h:96
T GetY() const
Definition: Point.tcc:40
Definition: GridRenderer.h:46
SPoint GetAbsoluteLocation()
Definition: Panel.cpp:173
virtual void PaintComponent(Drawing &config)
Definition: Panel.cpp:230
virtual bool Handle(MouseMotionEvent &mbe)
Definition: GridPanel.h:536
virtual bool Handle(MouseButtonEvent &mbe)
Definition: GridPanel.h:472
void Debug(const char *format,...)
Definition: Logger.h:301
static MDist< R > & get()
Definition: MDist.tcc:193
Definition: GridPanel.h:49
Definition: AtomViewPanel.h:37
u32 SetBackground(const u32 color)
Definition: Panel.h:220
T GetX() const
Definition: Point.tcc:34