1 /*
2 Copyright (C) 2009 Facundo Domínguez
3
4 This file is part of Spacejunk.
5
6 Spacejunk is free software: you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation, either version 3 of the License, or
9 (at your option) any later version.
10
11 Foobar is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with Foobar. If not, see <http://www.gnu.org/licenses/>.
18 */
19
20 #include "editorcontrol.h"
21 #include "resourcemanager.h"
22 #include "serializer.h"
23
24 #include <stdio.h>
25 #include <sys/types.h>
26 #include <dirent.h>
27 #include <iostream>
28 #include <sstream>
29 #include <fstream>
30 #include <unistd.h>
31 #include "gcnlayouts.h"
32 #include "starship.h"
33 #include "debugmsg.h"
34
35 #define BASECOLOR (gcn::Color(90,90,90))
36 #define BACKCOLOR (gcn::Color(120,120,120))
37 #define SELECTIONCOLOR (gcn::Color(90,90,90))
38 #define BORDERCOLOR (gcn::Color(255,255,255))
39 #define FORECOLOR BORDERCOLOR
40
41
action(const gcn::ActionEvent & e)42 void EditObjectControl::action (const gcn::ActionEvent & e) {
43 action(e.getId());
44 }
45
action(const std::string & eventId)46 void EditObjectControl::action (const std::string& eventId) {
47 if (eventId=="setmass") {
48 if (ec->canvas.selected) {
49 char b[10];
50 double v=sldMass.getValue();
51 if (sldMass.getScaleEnd()<v) v=sldMass.getScaleEnd();
52 else if (v<sldMass.getScaleStart()) v=sldMass.getScaleStart();
53 snprintf(b,10,"%i",int(v));
54 lsetmass.setCaption(string("1e")+b);
55 ec->canvas.setMass(ec->canvas.selected,pow(10,v));
56 if (!updating && dynamic_cast<Starship*>(ec->canvas.selected))
57 update(ec->canvas.selected);
58 }
59 } else if (eventId=="setfuelcapacity") {
60 Starship * ship=dynamic_cast<Starship*>(ec->canvas.selected);
61 if (ship) {
62 char b[10];
63 double v=sldFuelCapacity.getValue();
64 if (sldFuelCapacity.getScaleEnd()<v)
65 v=sldFuelCapacity.getScaleEnd();
66 else if (v<sldFuelCapacity.getScaleStart())
67 v=sldFuelCapacity.getScaleStart();
68 snprintf(b,10,"%.2f",v);
69 lsetfuelcap.setCaption(b);
70 ship->maxFuel=v;
71 }
72 } else if (eventId=="setfuel") {
73 Starship * ship=dynamic_cast<Starship*>(ec->canvas.selected);
74 if (ship) {
75 char b[10];
76 double v=sldFuel.getValue();
77 if (ship && ship->maxFuel<v)
78 v=ship->maxFuel;
79 else if (v<sldFuel.getScaleStart())
80 v=sldFuel.getScaleStart();
81 snprintf(b,10,"%.2f",v);
82 lsetfuel.setCaption(b);
83 ship->setFuel(v);
84 if (!updating)
85 update(ship);
86 }
87 } else if (eventId=="setfixed") {
88 if (ec->canvas.selected) {
89 if (cbFixed.isSelected())
90 ec->canvas.selected->flags|=PhysicBody::FIXED;
91 else
92 ec->canvas.selected->flags&=~PhysicBody::FIXED;
93
94 ec->canvas.level->retrace();
95 ec->canvas.level->step(0);
96 }
97 } else {
98 CHERROR<<"Warning: Do not know anything about "<<eventId<<ENDL;
99 exit(1);
100 }
101 }
102
103
EditObjectControl(EditorControl * ec)104 EditObjectControl::EditObjectControl(EditorControl * ec) :
105 ec(ec),l1("Mass"),lsetmass("1e000"),lsetfuelcap("00000"),lsetfuel("00000"),
106 fuelcapacity("Fuel capacity"),fuel("Fuel"),
107 sl(5,5),sldMass(0,40),sldFuelCapacity(0,1000),sldFuel(0,1000),
108 cbFixed("Fixed"), updating(false) {
109 setOpaque(false);
110 sldMass.setDimension(gcn::Rectangle(0,0,Graphic::toScreenw(70),Graphic::toScreenh(10)));
111 sldMass.setBaseColor(BASECOLOR);
112 sldFuelCapacity.setDimension(gcn::Rectangle(0,0,Graphic::toScreenw(70),Graphic::toScreenh(10)));
113 sldFuelCapacity.setBaseColor(BASECOLOR);
114 sldFuel.setDimension(gcn::Rectangle(0,0,Graphic::toScreenw(70),Graphic::toScreenh(10)));
115 sldFuel.setBaseColor(BASECOLOR);
116 sldMass.setValue(0);
117 sldMass.addKeyListener(&ec->canvas);
118 sldFuelCapacity.addKeyListener(&ec->canvas);
119 sldFuel.addKeyListener(&ec->canvas);
120 cbFixed.addKeyListener(&ec->canvas);
121
122 sl.l=5;
123 clvl.add(&l1);
124 clvl.add(&sldMass);
125 sldMass.setActionEventId("setmass");
126 sldMass.addActionListener(this);
127 clvl.add(&lsetmass);
128 clvl.add(&cbFixed);
129 cbFixed.setActionEventId("setfixed");
130 cbFixed.addActionListener(this);
131 cbFixed.setBackgroundColor(BACKCOLOR);
132 cbFixed.setForegroundColor(FORECOLOR);
133
134 shipcl.add(&fuelcapacity);
135 shipcl.add(&sldFuelCapacity);
136 sldFuelCapacity.setActionEventId("setfuelcapacity");
137 sldFuelCapacity.addActionListener(this);
138 shipcl.add(&lsetfuelcap);
139 shipcl.setVisible(false);
140 shipcl.fitWidgets();
141 clvl.add(&shipcl);
142 shiptrashcl.add(&fuel);
143 shiptrashcl.add(&sldFuel);
144 sldFuel.setActionEventId("setfuel");
145 sldFuel.addActionListener(this);
146 shiptrashcl.add(&lsetfuel);
147 shiptrashcl.setVisible(false);
148 shiptrashcl.fitWidgets();
149 clvl.add(&shiptrashcl);
150 sl.setContainer(&clvl);
151
152 sl.fitWidgets();
153 setContent(&sl);
154
155 setFrameSize(1);
156 int w=getScrollbarWidth()+sl.getWidth();
157 setWidth(Graphic::toScreenw(115<w?115:w));
158 setHeight(Graphic::toScreenh(300));
159 sl.setOpaque(false);
160 clvl.setOpaque(false);
161 shipcl.setOpaque(false);
162 shiptrashcl.setOpaque(false);
163 setBaseColor(BASECOLOR);
164 }
165
update(GameBody * selected)166 void EditObjectControl::update(GameBody * selected) {
167 updating=true;
168 Starship * sh=dynamic_cast<Starship*>(selected);
169 if (sh) {
170 sldFuelCapacity.setValue(sh->maxFuel);
171 action(sldFuelCapacity.getActionEventId());
172 sldFuel.setValue(sh->getFuel());
173 action(sldFuel.getActionEventId());
174 }
175 shipcl.setVisible(sh);
176 shiptrashcl.setVisible(sh);
177
178 sldMass.setValue(log10(selected->mass));
179 action(sldMass.getActionEventId());
180 cbFixed.setSelected(selected->flags & PhysicBody::FIXED);
181 updating=false;
182 };
183
requestFocus()184 void PromptWindow::requestFocus() {
185 tb.requestFocus();
186 };
187
PromptWindow(string * text)188 PromptWindow::PromptWindow(string * text) : text(text), btDone("Done") {
189 tb.setText(*text);
190 tb.setBackgroundColor(BACKCOLOR);
191 tb.setBaseColor(BASECOLOR);
192 tb.setForegroundColor(FORECOLOR);
193
194 btDone.setBackgroundColor(BACKCOLOR);
195 btDone.setBaseColor(BASECOLOR);
196 btDone.setForegroundColor(FORECOLOR);
197
198 setBackgroundColor(BACKCOLOR);
199 setBaseColor(BASECOLOR);
200 setForegroundColor(FORECOLOR);
201
202 sa.setBackgroundColor(BACKCOLOR);
203 sa.setBaseColor(BASECOLOR);
204 sa.setForegroundColor(FORECOLOR);
205
206 vl.setBackgroundColor(BACKCOLOR);
207 vl.setBaseColor(BASECOLOR);
208 vl.setForegroundColor(FORECOLOR);
209
210 btDone.addActionListener(this);
211 sa.setContent(&tb);
212 sa.setWidth(Graphic::toScreenw(250));
213 sa.setHeight(Graphic::toScreenh(100));
214 vl.add(&sa);
215 vl.add(&btDone);
216 vl.fitWidgets();
217 add(&vl);
218 setWidth(vl.getWidth());
219 setHeight(vl.getHeight()+getTitleBarHeight());
220 }
action(const gcn::ActionEvent &)221 void PromptWindow::action(const gcn::ActionEvent& ) {
222 *text=tb.getText();
223 setVisible(false);
224 }
225
refresh()226 void PromptWindow::refresh() {
227 tb.setText(*text);
228 }
229
action(const gcn::ActionEvent & e)230 void EditorControl::action (const gcn::ActionEvent & e) {
231 action(e.getId());
232 }
233
action(const string & eventId)234 void EditorControl::action (const string & eventId) {
235 if (eventId=="save") {
236 ofstream f(patht.getText().c_str());
237 f<<canvas;
238 } else if (eventId=="load") {
239 if (!exists(patht.getText())) {
240 canvas.clear();
241 return;
242 }
243 ifstream f(patht.getText().c_str());
244 f>>canvas;
245 ostringstream s;
246 s<<canvas.level->getBonusTime();
247 txtTime->setText(s.str());
248 } else if (eventId=="play") {
249 canvas.play = true;
250 canvas.initTime();
251 } else if (eventId=="delete") {
252 if (d.isSelected()) canvas.mode=Canvas::DELETE;
253 } else if (eventId=="edit") {
254 if (e.isSelected()) {
255 canvas.mode=Canvas::EDIT;
256 ctlEdit->setVisible(true);
257 ddObjects.setVisible(true);
258 } else {
259 canvas.selected=NULL;
260 ctlEdit->setVisible(false);
261 ddObjects.setVisible(false);
262 }
263 } else if (eventId=="describe") {
264 desc.setVisible(true);
265 desc.requestFocus();
266 desc.refresh();
267 moveToTop(&desc);
268 } else if (eventId=="ddObjects") {
269 canvas.selectedType=lobjects[ddObjects.getSelected()];
270 }
271 }
272
exists(const string & f)273 bool EditorControl::exists(const string & f) {
274 return !access(f.c_str(),F_OK);
275 /* DIR * d=opendir(".");
276 struct dirent *ep;
277 while ((ep=readdir(d)) && ep->d_name!=f);
278 closedir(d);
279 return ep;
280 */
281 }
282
setTxtTime(EditorControl * ec,int n)283 void setTxtTime(EditorControl * ec,int n) {
284 ec->canvas.level->setBonusTime(n);
285 }
286
287
initializeAddButtons(int x,int y)288 void EditorControl::initializeAddButtons(int x,int y) {
289 // const int rbCount=13;
290 lobjects.push_back("player1");
291 lobjects.push_back("asteroid1");
292 lobjects.push_back("asteroid2");
293 lobjects.push_back("asteroid3");
294 lobjects.push_back("asteroid4");
295 lobjects.push_back("moon1");
296 lobjects.push_back("moon2");
297 lobjects.push_back("moon3");
298 lobjects.push_back("moon4");
299 lobjects.push_back("planet1");
300 lobjects.push_back("planet2");
301 lobjects.push_back("planet3");
302 lobjects.push_back("planet4");
303 lobjects.push_back("planet5");
304 lobjects.push_back("planet6");
305 lobjects.push_back("planet7");
306 lobjects.push_back("planet8");
307 lobjects.push_back("planet9");
308 lobjects.push_back("star1");
309 lobjects.push_back("star2");
310 lobjects.push_back("star3");
311 lobjects.push_back("galaxia0");
312 lobjects.push_back("galaxia0grande");
313 lobjects.push_back("galaxia1");
314 lobjects.push_back("galaxia2");
315 lobjects.push_back("galaxia3");
316 lobjects.push_back("galaxia4");
317 lobjects.push_back("galaxia4chica");
318 lobjects.push_back("galaxia4grande");
319 lobjects.push_back("nebula1");
320 lobjects.push_back("nebula2");
321 lobjects.push_back("nebula3");
322 lobjects.push_back("farstar1");
323 lobjects.push_back("farstar2");
324 lobjects.push_back("farstar3");
325 lobjects.push_back("farstargroup1");
326 lobjects.push_back("farstargroup2");
327 lobjects.push_back("farstargroup3");
328 lobjects.push_back("trash1");
329 lobjects.push_back("trash2");
330 lobjects.push_back("trash3");
331 lobjects.push_back("trash4");
332 lobjects.push_back("trash5");
333 lobjects.push_back("trash6");
334 lobjects.push_back("trash7");
335 lobjects.push_back("trash8");
336 lobjects.push_back("trash9");
337
338 ddObjects.setWidth(Graphic::toScreenw(90));
339 ddObjects.setBackgroundColor(BACKCOLOR);
340 ddObjects.setSelectionColor(SELECTIONCOLOR);
341 ddObjects.setBaseColor(BASECOLOR);
342 ddObjects.setListModel(&lobjects);
343 ddObjects.addKeyListener(&canvas);
344 ddObjects.addActionListener(this);
345 ddObjects.setActionEventId("ddObjects");
346 action("ddObjects");
347 add(&ddObjects,x,y);
348 }
349
350
initializeModeButtons(int x,int y)351 void EditorControl::initializeModeButtons(int x,int y) {
352 rbsMode.spacing=3;
353 txtTime->setWidth(Graphic::toScreenw(40));
354 txtTime->setHeight(Graphic::toScreenh(15));
355 txtTime->setText("300");
356 txtTime->setBackgroundColor(BACKCOLOR);
357 txtTime->setForegroundColor(FORECOLOR);
358 ltime.add(&*txtTime);
359 ltime.fitWidgets();
360 ltime.setBaseColor(BASECOLOR);
361 save.addActionListener(this);
362 save.setActionEventId("save");
363 save.setBaseColor(BASECOLOR);
364 load.addActionListener(this);
365 load.setActionEventId("load");
366 load.setBaseColor(BASECOLOR);
367 btDesc.setActionEventId("describe");
368 btDesc.setBaseColor(BASECOLOR);
369 btDesc.addActionListener(this);
370 play.setAlignment(gcn::Graphics::CENTER);
371 play.adjustSize();
372 play.setActionEventId("play");
373 play.addActionListener(this);
374 play.setBaseColor(BASECOLOR);
375 d.setActionEventId("delete");
376 d.addKeyListener(&canvas);
377 d.addActionListener(this);
378 e.setActionEventId("edit");
379 e.addKeyListener(&canvas);
380 e.addActionListener(this);
381 play.addKeyListener(&canvas);
382 save.addKeyListener(&canvas);
383 load.addKeyListener(&canvas);
384
385 d.setBackgroundColor(BACKCOLOR);
386 d.setForegroundColor(FORECOLOR);
387 e.setBackgroundColor(BACKCOLOR);
388 e.setForegroundColor(FORECOLOR);
389
390 rbsMode.add(&d);
391 rbsMode.add(&e);
392 rbsMode.setBackgroundColor(BASECOLOR);
393 rbsMode.setBaseColor(BORDERCOLOR);
394 bts1.add(&btDesc);
395 bts1.add(&play);
396 bts1.fitWidgets();
397 rbsMode.add(&bts1);
398 bts2.add(&save);
399 bts2.add(&load);
400 bts2.fitWidgets();
401 rbsMode.add(&bts2);
402 rbsMode.add(&patht);
403 patht.setBackgroundColor(BACKCOLOR);
404 patht.setForegroundColor(FORECOLOR);
405 rbsMode.add(<ime);
406 rbsMode.fitWidgets();
407 rbsMode.setFrameSize(1);
408 rbsMode.setX(x);
409 rbsMode.setY(y);
410 rbsMode.setOpaque(false);
411 }
412
initializeEditButtons(int x,int y)413 void EditorControl::initializeEditButtons(int x,int y) {
414 ctlEdit=new EditObjectControl(this);
415 ctlEdit->setX(x);
416 ctlEdit->setY(y);
417 }
418
EditorControl()419 EditorControl::EditorControl():
420 SpacingLayout(5,5,5,5),
421 d("Delete","mode"),
422 e("Edit","mode"),play("Play"),btDesc("Describe"),save("Save"),load("Load"),
423 patht("unamedlevel"), txtTime(numTextField(this,setTxtTime)),
424 ltime("Btime: "),
425 canvas(this), desc(&canvas.level->description) { //, backgroundFill(*(new gcn::Container()))
426 setBaseColor(BASECOLOR);
427
428 desc.setCaption("Brief level description");
429 add(&desc,Graphic::toScreenw(50),Graphic::toScreenh(50));
430 desc.setVisible(false);
431 setOpaque(false);
432
433 setDimension(gcn::Rectangle(Graphic::toScreenx(0), Graphic::toScreeny(0),
434 Graphic::toScreenw(LOGICAL_WIDTH), Graphic::toScreenh(LOGICAL_HEIGHT)));
435
436 canvas.setBaseColor(gcn::Color(0,0,0));
437 canvas.setDimension(gcn::Rectangle(0,0,Graphic::toScreenw(LOGICAL_WIDTH), Graphic::toScreenh(LOGICAL_HEIGHT)));
438 // canvas.setDimension(gcn::Rectangle(125, 10, 510, 465));
439 add(&canvas);
440
441 addKeyListener(&canvas);
442
443 initializeModeButtons(Graphic::toScreenw(5),Graphic::toScreenh(10));
444 initializeAddButtons(Graphic::toScreenw(5),rbsMode.getHeight()+rbsMode.getY()+Graphic::toScreenh(5));
445 initializeEditButtons(Graphic::toScreenw(5),rbsMode.getHeight()+rbsMode.getY()+Graphic::toScreenh(5)+ddObjects.getHeight());
446
447 add(&rbsMode);
448 add(ctlEdit);
449
450 e.setSelected(true),
451 setFocusable(true);
452 }
453
~EditorControl()454 EditorControl::~EditorControl() {
455 };
456