blob: 25e0c57a4df050f6b7408d93a437f4572ebe52d4 [file] [log] [blame]
chudy@google.com902ebe52012-06-29 14:21:22 +00001/*
2 * Copyright 2012 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
chudy@google.com902ebe52012-06-29 14:21:22 +00008#include "SkDebuggerGUI.h"
chudy@google.combbad34d2012-08-13 14:26:36 +00009#include "SkGraphics.h"
scroggo@google.comb4467e62012-11-06 23:10:09 +000010#include "SkImageDecoder.h"
chudy@google.com902ebe52012-06-29 14:21:22 +000011#include <QListWidgetItem>
robertphillips@google.com2bde91d2012-11-15 14:57:57 +000012#include "PictureRenderer.h"
robertphillips@google.com2bde91d2012-11-15 14:57:57 +000013#include "SkPictureRecord.h"
14#include "SkPicturePlayback.h"
robertphillips@google.come174a8b2012-11-27 16:04:42 +000015
16#if defined(SK_BUILD_FOR_WIN32)
17 #include "BenchSysTimer_windows.h"
18#elif defined(SK_BUILD_FOR_MAC)
19 #include "BenchSysTimer_mach.h"
20#elif defined(SK_BUILD_FOR_UNIX) || defined(SK_BUILD_FOR_ANDROID)
21 #include "BenchSysTimer_posix.h"
22#else
23 #include "BenchSysTimer_c.h"
24#endif
25
chudy@google.com902ebe52012-06-29 14:21:22 +000026
27SkDebuggerGUI::SkDebuggerGUI(QWidget *parent) :
chudy@google.comc432f002012-07-10 13:19:25 +000028 QMainWindow(parent)
chudy@google.com2d537a12012-07-31 12:49:52 +000029 , fCentralWidget(this)
30 , fStatusBar(this)
31 , fToolBar(this)
chudy@google.comc432f002012-07-10 13:19:25 +000032 , fActionOpen(this)
33 , fActionBreakpoint(this)
robertphillips@google.comd26c7062012-11-12 20:42:12 +000034 , fActionProfile(this)
chudy@google.comc432f002012-07-10 13:19:25 +000035 , fActionCancel(this)
chudy@google.com7e4cfbf2012-07-17 15:40:51 +000036 , fActionClearBreakpoints(this)
chudy@google.come504de02012-07-16 18:35:23 +000037 , fActionClearDeletes(this)
chudy@google.comc432f002012-07-10 13:19:25 +000038 , fActionClose(this)
chudy@google.come504de02012-07-16 18:35:23 +000039 , fActionCreateBreakpoint(this)
chudy@google.comc432f002012-07-10 13:19:25 +000040 , fActionDelete(this)
41 , fActionDirectory(this)
42 , fActionGoToLine(this)
43 , fActionInspector(this)
44 , fActionPlay(this)
chudy@google.come504de02012-07-16 18:35:23 +000045 , fActionPause(this)
chudy@google.comc432f002012-07-10 13:19:25 +000046 , fActionRewind(this)
chudy@google.com0ab03392012-07-28 20:16:11 +000047 , fActionSave(this)
48 , fActionSaveAs(this)
chudy@google.com7e4cfbf2012-07-17 15:40:51 +000049 , fActionShowDeletes(this)
chudy@google.comc432f002012-07-10 13:19:25 +000050 , fActionStepBack(this)
51 , fActionStepForward(this)
chudy@google.coma1226312012-07-26 20:26:44 +000052 , fActionZoomIn(this)
53 , fActionZoomOut(this)
54 , fMapper(this)
chudy@google.comc432f002012-07-10 13:19:25 +000055 , fListWidget(&fCentralWidget)
56 , fDirectoryWidget(&fCentralWidget)
chudy@google.com607357f2012-08-07 16:12:23 +000057 , fCanvasWidget(this, &fDebugger)
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +000058 , fImageWidget(&fDebugger)
chudy@google.comc432f002012-07-10 13:19:25 +000059 , fMenuBar(this)
60 , fMenuFile(this)
61 , fMenuNavigate(this)
62 , fMenuView(this)
chudy@google.com7e4cfbf2012-07-17 15:40:51 +000063 , fBreakpointsActivated(false)
64 , fDeletesActivated(false)
65 , fPause(false)
chudy@google.comd3058f52012-07-19 13:41:27 +000066 , fLoading(false)
chudy@google.comc432f002012-07-10 13:19:25 +000067{
chudy@google.com902ebe52012-06-29 14:21:22 +000068 setupUi(this);
chudy@google.comea5488b2012-07-26 19:38:22 +000069 connect(&fListWidget, SIGNAL(currentItemChanged(QListWidgetItem*, QListWidgetItem*)), this, SLOT(registerListClick(QListWidgetItem *)));
chudy@google.comc432f002012-07-10 13:19:25 +000070 connect(&fActionOpen, SIGNAL(triggered()), this, SLOT(openFile()));
chudy@google.comea5488b2012-07-26 19:38:22 +000071 connect(&fActionDirectory, SIGNAL(triggered()), this, SLOT(toggleDirectory()));
72 connect(&fDirectoryWidget, SIGNAL(currentItemChanged(QListWidgetItem*, QListWidgetItem*)), this, SLOT(loadFile(QListWidgetItem *)));
chudy@google.comc432f002012-07-10 13:19:25 +000073 connect(&fActionDelete, SIGNAL(triggered()), this, SLOT(actionDelete()));
chudy@google.comea5488b2012-07-26 19:38:22 +000074 connect(&fListWidget, SIGNAL(itemDoubleClicked(QListWidgetItem*)), this, SLOT(toggleBreakpoint()));
chudy@google.comc432f002012-07-10 13:19:25 +000075 connect(&fActionRewind, SIGNAL(triggered()), this, SLOT(actionRewind()));
76 connect(&fActionPlay, SIGNAL(triggered()), this, SLOT(actionPlay()));
77 connect(&fActionStepBack, SIGNAL(triggered()), this, SLOT(actionStepBack()));
chudy@google.comea5488b2012-07-26 19:38:22 +000078 connect(&fActionStepForward, SIGNAL(triggered()), this, SLOT(actionStepForward()));
79 connect(&fActionBreakpoint, SIGNAL(triggered()), this, SLOT(actionBreakpoints()));
80 connect(&fActionInspector, SIGNAL(triggered()), this, SLOT(actionInspector()));
81 connect(&fActionInspector, SIGNAL(triggered()), this, SLOT(actionSettings()));
82 connect(&fFilter, SIGNAL(activated(QString)), this, SLOT(toggleFilter(QString)));
robertphillips@google.comd26c7062012-11-12 20:42:12 +000083 connect(&fActionProfile, SIGNAL(triggered()), this, SLOT(actionProfile()));
chudy@google.comc432f002012-07-10 13:19:25 +000084 connect(&fActionCancel, SIGNAL(triggered()), this, SLOT(actionCancel()));
chudy@google.com7e4cfbf2012-07-17 15:40:51 +000085 connect(&fActionClearBreakpoints, SIGNAL(triggered()), this, SLOT(actionClearBreakpoints()));
86 connect(&fActionClearDeletes, SIGNAL(triggered()), this, SLOT(actionClearDeletes()));
chudy@google.comc432f002012-07-10 13:19:25 +000087 connect(&fActionClose, SIGNAL(triggered()), this, SLOT(actionClose()));
chudy@google.comea5488b2012-07-26 19:38:22 +000088 connect(fSettingsWidget.getVisibilityButton(), SIGNAL(toggled(bool)), this, SLOT(actionCommandFilter()));
89 connect(fSettingsWidget.getGLCheckBox(), SIGNAL(toggled(bool)), this, SLOT(actionGLWidget(bool)));
90 connect(fSettingsWidget.getRasterCheckBox(), SIGNAL(toggled(bool)), this, SLOT(actionRasterWidget(bool)));
91 connect(&fActionPause, SIGNAL(toggled(bool)), this, SLOT(pauseDrawing(bool)));
chudy@google.come504de02012-07-16 18:35:23 +000092 connect(&fActionCreateBreakpoint, SIGNAL(activated()), this, SLOT(toggleBreakpoint()));
chudy@google.com7e4cfbf2012-07-17 15:40:51 +000093 connect(&fActionShowDeletes, SIGNAL(triggered()), this, SLOT(showDeletes()));
chudy@google.comea5488b2012-07-26 19:38:22 +000094 connect(&fCanvasWidget, SIGNAL(hitChanged(int)), this, SLOT(selectCommand(int)));
95 connect(&fCanvasWidget, SIGNAL(hitChanged(int)), &fSettingsWidget, SLOT(updateHit(int)));
96 connect(&fCanvasWidget, SIGNAL(scaleFactorChanged(float)), this, SLOT(actionScale(float)));
97 connect(&fCanvasWidget, SIGNAL(commandChanged(int)), &fSettingsWidget, SLOT(updateCommand(int)));
chudy@google.com0ab03392012-07-28 20:16:11 +000098 connect(&fActionSaveAs, SIGNAL(triggered()), this, SLOT(actionSaveAs()));
99 connect(&fActionSave, SIGNAL(triggered()), this, SLOT(actionSave()));
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000100
chudy@google.coma1226312012-07-26 20:26:44 +0000101 fMapper.setMapping(&fActionZoomIn, 1);
102 fMapper.setMapping(&fActionZoomOut, -1);
103
104 connect(&fActionZoomIn, SIGNAL(triggered()), &fMapper, SLOT(map()));
105 connect(&fActionZoomOut, SIGNAL(triggered()), &fMapper, SLOT(map()));
106 connect(&fMapper, SIGNAL(mapped(int)), &fCanvasWidget, SLOT(keyZoom(int)));
107
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000108 fInspectorWidget.setDisabled(true);
chudy@google.comd3058f52012-07-19 13:41:27 +0000109 fMenuEdit.setDisabled(true);
110 fMenuNavigate.setDisabled(true);
111 fMenuView.setDisabled(true);
chudy@google.combbad34d2012-08-13 14:26:36 +0000112
113 SkGraphics::Init();
chudy@google.com902ebe52012-06-29 14:21:22 +0000114}
115
chudy@google.combbad34d2012-08-13 14:26:36 +0000116SkDebuggerGUI::~SkDebuggerGUI() {
117 SkGraphics::Term();
118}
chudy@google.com902ebe52012-06-29 14:21:22 +0000119
120void SkDebuggerGUI::actionBreakpoints() {
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000121 fBreakpointsActivated = !fBreakpointsActivated;
chudy@google.comc432f002012-07-10 13:19:25 +0000122 for (int row = 0; row < fListWidget.count(); row++) {
123 QListWidgetItem *item = fListWidget.item(row);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000124 item->setHidden(item->checkState() == Qt::Unchecked && fBreakpointsActivated);
125 }
126}
chudy@google.com902ebe52012-06-29 14:21:22 +0000127
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000128void SkDebuggerGUI::showDeletes() {
129 fDeletesActivated = !fDeletesActivated;
130 for (int row = 0; row < fListWidget.count(); row++) {
131 QListWidgetItem *item = fListWidget.item(row);
chudy@google.com607357f2012-08-07 16:12:23 +0000132 item->setHidden(fDebugger.isCommandVisible(row)
133 && fDeletesActivated);
chudy@google.com902ebe52012-06-29 14:21:22 +0000134 }
135}
136
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000137// The timed picture playback uses the SkPicturePlayback's profiling stubs
138// to time individual commands. The offsets are needed to map SkPicture
139// offsets to individual commands.
140class SkTimedPicturePlayback : public SkPicturePlayback {
141public:
142 SkTimedPicturePlayback(SkStream* stream, const SkPictInfo& info, bool* isValid,
143 SkSerializationHelpers::DecodeBitmap decoder,
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000144 const SkTDArray<size_t>& offsets)
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000145 : INHERITED(stream, info, isValid, decoder)
146 , fTot(0.0)
147 , fCurCommand(0)
148 , fOffsets(offsets) {
149 fTimes.setCount(fOffsets.count());
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000150 fTypeTimes.setCount(LAST_DRAWTYPE_ENUM+1);
151 this->resetTimes();
152 }
153
154 void resetTimes() {
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000155 for (int i = 0; i < fOffsets.count(); ++i) {
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000156 fTimes[i] = 0.0;
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000157 }
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000158 for (int i = 0; i < fTypeTimes.count(); ++i) {
159 fTypeTimes[i] = 0.0f;
160 }
161 fTot = 0.0;
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000162 }
163
164 int count() const { return fTimes.count(); }
165
166 double time(int index) const { return fTimes[index] / fTot; }
167
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000168 const SkTDArray<double>* typeTimes() const { return &fTypeTimes; }
169
170 double totTime() const { return fTot; }
171
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000172protected:
robertphillips@google.come174a8b2012-11-27 16:04:42 +0000173 BenchSysTimer fTimer;
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000174 SkTDArray<size_t> fOffsets; // offset in the SkPicture for each command
175 SkTDArray<double> fTimes; // sum of time consumed for each command
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000176 SkTDArray<double> fTypeTimes; // sum of time consumed for each type of command (e.g., drawPath)
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000177 double fTot; // total of all times in 'fTimes'
178 size_t fCurOffset;
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000179 int fCurType;
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000180 int fCurCommand; // the current command being executed/timed
181
182 virtual void preDraw(size_t offset, int type) {
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000183 // This search isn't as bad as it seems. In normal playback mode, the
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000184 // base class steps through the commands in order and can only skip ahead
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000185 // a bit on a clip. This class is only used during profiling so we
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000186 // don't have to worry about forward/backward scrubbing through commands.
187 for (int i = 0; offset != fOffsets[fCurCommand]; ++i) {
188 fCurCommand = (fCurCommand+1) % fOffsets.count();
189 SkASSERT(i <= fOffsets.count()); // should always find the offset in the list
190 }
191
192 fCurOffset = offset;
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000193 fCurType = type;
194 // The SkDebugCanvas doesn't recognize these types. This class needs to
195 // convert or else we'll wind up with a mismatch between the type counts
196 // the debugger displays and the profile times.
197 if (DRAW_POS_TEXT_TOP_BOTTOM == type) {
198 fCurType = DRAW_POS_TEXT;
199 } else if (DRAW_POS_TEXT_H_TOP_BOTTOM == type) {
200 fCurType = DRAW_POS_TEXT_H;
201 }
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000202
robertphillips@google.come174a8b2012-11-27 16:04:42 +0000203#if defined(SK_BUILD_FOR_WIN32)
204 // CPU timer doesn't work well on Windows
205 fTimer.startWall();
206#else
207 fTimer.startCpu();
208#endif
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000209 }
210
211 virtual void postDraw(size_t offset) {
robertphillips@google.come174a8b2012-11-27 16:04:42 +0000212#if defined(SK_BUILD_FOR_WIN32)
213 // CPU timer doesn't work well on Windows
214 double time = fTimer.endWall();
215#else
216 double time = fTimer.endCpu();
217#endif
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000218
219 SkASSERT(offset == fCurOffset);
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000220 SkASSERT(fCurType <= LAST_DRAWTYPE_ENUM);
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000221
robertphillips@google.come174a8b2012-11-27 16:04:42 +0000222 fTimes[fCurCommand] += time;
223 fTypeTimes[fCurType] += time;
224 fTot += time;
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000225 }
226
227private:
228 typedef SkPicturePlayback INHERITED;
229};
230
231// Wrap SkPicture to allow installation of an SkTimedPicturePlayback object
232class SkTimedPicture : public SkPicture {
233public:
234 explicit SkTimedPicture(SkStream* stream,
235 bool* success,
236 SkSerializationHelpers::DecodeBitmap decoder,
237 const SkTDArray<size_t>& offsets) {
238 if (success) {
239 *success = false;
240 }
241 fRecord = NULL;
242 fPlayback = NULL;
243 fWidth = fHeight = 0;
244
245 SkPictInfo info;
246
247 if (!stream->read(&info, sizeof(info))) {
248 return;
249 }
250 if (SkPicture::PICTURE_VERSION != info.fVersion) {
251 return;
252 }
253
254 if (stream->readBool()) {
255 bool isValid = false;
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000256 fPlayback = SkNEW_ARGS(SkTimedPicturePlayback,
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000257 (stream, info, &isValid, decoder, offsets));
258 if (!isValid) {
259 SkDELETE(fPlayback);
260 fPlayback = NULL;
261 return;
262 }
263 }
264
265 // do this at the end, so that they will be zero if we hit an error.
266 fWidth = info.fWidth;
267 fHeight = info.fHeight;
268 if (success) {
269 *success = true;
270 }
271 }
272
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000273 void resetTimes() { ((SkTimedPicturePlayback*) fPlayback)->resetTimes(); }
274
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000275 int count() const { return ((SkTimedPicturePlayback*) fPlayback)->count(); }
276
277 // return the fraction of the total time this command consumed
278 double time(int index) const { return ((SkTimedPicturePlayback*) fPlayback)->time(index); }
279
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000280 const SkTDArray<double>* typeTimes() const { return ((SkTimedPicturePlayback*) fPlayback)->typeTimes(); }
281
282 double totTime() const { return ((SkTimedPicturePlayback*) fPlayback)->totTime(); }
283
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000284private:
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000285 // disallow default ctor b.c. we don't have a good way to setup the fPlayback ptr
286 SkTimedPicture();
287 // disallow the copy ctor - enabling would require copying code from SkPicture
288 SkTimedPicture(const SkTimedPicture& src);
289
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000290 typedef SkPicture INHERITED;
291};
292
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000293// This is a simplification of PictureBenchmark's run with the addition of
294// clearing of the times after the first pass (in resetTimes)
skia.committer@gmail.com34587162012-11-20 02:01:23 +0000295void SkDebuggerGUI::run(SkTimedPicture* pict,
296 sk_tools::PictureRenderer* renderer,
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000297 int repeats) {
298 SkASSERT(pict);
299 if (NULL == pict) {
300 return;
301 }
302
303 SkASSERT(renderer != NULL);
304 if (NULL == renderer) {
305 return;
306 }
307
308 renderer->init(pict);
309
310 renderer->setup();
311 renderer->render(NULL);
312 renderer->resetState();
313
314 // We throw this away the first batch of times to remove first time effects (such as paging in this program)
315 pict->resetTimes();
316
317 for (int i = 0; i < repeats; ++i) {
318 renderer->setup();
319 renderer->render(NULL);
320 renderer->resetState();
321 }
322
323 renderer->end();
324}
325
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000326void SkDebuggerGUI::actionProfile() {
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000327 // In order to profile we pass the command offsets (that were read-in
328 // in loadPicture by the SkOffsetPicture) to an SkTimedPlaybackPicture.
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000329 // The SkTimedPlaybackPicture in turn passes the offsets to an
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000330 // SkTimedPicturePlayback object which uses them to track the performance
331 // of individual commands.
332 if (fFileName.isEmpty()) {
333 return;
334 }
335
336 SkFILEStream inputStream;
337
338 inputStream.setPath(fFileName.c_str());
339 if (!inputStream.isValid()) {
340 return;
341 }
342
343 bool success = false;
344 SkTimedPicture picture(&inputStream, &success, &SkImageDecoder::DecodeStream, fOffsets);
345 if (!success) {
346 return;
347 }
348
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000349 // For now this #if allows switching between tiled and simple rendering
350 // modes. Eventually this will be accomplished via the GUI
robertphillips@google.come174a8b2012-11-27 16:04:42 +0000351#if 0
352 // With the current batch of SysTimers, profiling in tiled mode
353 // gets swamped by the timing overhead:
354 //
355 // tile mode simple mode
356 // debugger 64.2ms 12.8ms
357 // bench_pictures 16.9ms 12.4ms
358 //
359 // This is b.c. in tiled mode each command is called many more times
360 // but typically does less work on each invocation (due to clipping)
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000361 sk_tools::TiledPictureRenderer* renderer = NULL;
362
363 renderer = SkNEW(sk_tools::TiledPictureRenderer);
364 renderer->setTileWidth(256);
365 renderer->setTileHeight(256);
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000366#else
367 sk_tools::SimplePictureRenderer* renderer = NULL;
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000368
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000369 renderer = SkNEW(sk_tools::SimplePictureRenderer);
370#endif
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000371
robertphillips@google.come174a8b2012-11-27 16:04:42 +0000372 static const int kNumRepeats = 10;
373
374 run(&picture, renderer, kNumRepeats);
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000375
376 SkASSERT(picture.count() == fListWidget.count());
377
378 // extract the individual command times from the SkTimedPlaybackPicture
379 for (int i = 0; i < picture.count(); ++i) {
380 double temp = picture.time(i);
381
382 QListWidgetItem* item = fListWidget.item(i);
383
384 item->setData(Qt::UserRole + 4, 100.0*temp);
385 }
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000386
387 setupOverviewText(picture.typeTimes(), picture.totTime());
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000388}
389
chudy@google.com902ebe52012-06-29 14:21:22 +0000390void SkDebuggerGUI::actionCancel() {
chudy@google.comc432f002012-07-10 13:19:25 +0000391 for (int row = 0; row < fListWidget.count(); row++) {
392 fListWidget.item(row)->setHidden(false);
chudy@google.com902ebe52012-06-29 14:21:22 +0000393 }
394}
395
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000396void SkDebuggerGUI::actionClearBreakpoints() {
397 for (int row = 0; row < fListWidget.count(); row++) {
398 QListWidgetItem* item = fListWidget.item(row);
399 item->setCheckState(Qt::Unchecked);
400 item->setData(Qt::DecorationRole,
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000401 QPixmap(":/blank.png"));
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000402 }
403}
404
405void SkDebuggerGUI::actionClearDeletes() {
406 for (int row = 0; row < fListWidget.count(); row++) {
407 QListWidgetItem* item = fListWidget.item(row);
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000408 item->setData(Qt::UserRole + 2, QPixmap(":/blank.png"));
chudy@google.com607357f2012-08-07 16:12:23 +0000409 fDebugger.setCommandVisible(row, true);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000410 }
411 if (fPause) {
412 fCanvasWidget.drawTo(fPausedRow);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000413 fImageWidget.draw();
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000414 } else {
415 fCanvasWidget.drawTo(fListWidget.currentRow());
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000416 fImageWidget.draw();
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000417 }
418}
419
chudy@google.com902ebe52012-06-29 14:21:22 +0000420void SkDebuggerGUI::actionCommandFilter() {
chudy@google.com607357f2012-08-07 16:12:23 +0000421 fDebugger.highlightCurrentCommand(
chudy@google.comc432f002012-07-10 13:19:25 +0000422 fSettingsWidget.getVisibilityButton()->isChecked());
423 fCanvasWidget.drawTo(fListWidget.currentRow());
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000424 fImageWidget.draw();
chudy@google.com902ebe52012-06-29 14:21:22 +0000425}
426
427void SkDebuggerGUI::actionClose() {
428 this->close();
429}
430
431void SkDebuggerGUI::actionDelete() {
chudy@google.comc432f002012-07-10 13:19:25 +0000432 int currentRow = fListWidget.currentRow();
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000433 QListWidgetItem* item = fListWidget.currentItem();
434
chudy@google.com607357f2012-08-07 16:12:23 +0000435 if (fDebugger.isCommandVisible(currentRow)) {
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000436 item->setData(Qt::UserRole + 2, QPixmap(":/delete.png"));
chudy@google.com607357f2012-08-07 16:12:23 +0000437 fDebugger.setCommandVisible(currentRow, false);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000438 } else {
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000439 item->setData(Qt::UserRole + 2, QPixmap(":/blank.png"));
chudy@google.com607357f2012-08-07 16:12:23 +0000440 fDebugger.setCommandVisible(currentRow, true);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000441 }
442
chudy@google.come504de02012-07-16 18:35:23 +0000443 if (fPause) {
444 fCanvasWidget.drawTo(fPausedRow);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000445 fImageWidget.draw();
chudy@google.come504de02012-07-16 18:35:23 +0000446 } else {
447 fCanvasWidget.drawTo(currentRow);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000448 fImageWidget.draw();
chudy@google.come504de02012-07-16 18:35:23 +0000449 }
chudy@google.com902ebe52012-06-29 14:21:22 +0000450}
451
chudy@google.comea5488b2012-07-26 19:38:22 +0000452void SkDebuggerGUI::actionGLWidget(bool isToggled) {
453 fCanvasWidget.setWidgetVisibility(SkCanvasWidget::kGPU_WidgetType, !isToggled);
454}
455
chudy@google.com902ebe52012-06-29 14:21:22 +0000456void SkDebuggerGUI::actionInspector() {
chudy@google.comc432f002012-07-10 13:19:25 +0000457 if (fInspectorWidget.isHidden()) {
458 fInspectorWidget.setHidden(false);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000459 fImageWidget.setHidden(false);
chudy@google.com902ebe52012-06-29 14:21:22 +0000460 } else {
chudy@google.comc432f002012-07-10 13:19:25 +0000461 fInspectorWidget.setHidden(true);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000462 fImageWidget.setHidden(true);
chudy@google.com902ebe52012-06-29 14:21:22 +0000463 }
464}
465
466void SkDebuggerGUI::actionPlay() {
chudy@google.comc432f002012-07-10 13:19:25 +0000467 for (int row = fListWidget.currentRow() + 1; row < fListWidget.count();
chudy@google.com7dcae672012-07-09 20:26:53 +0000468 row++) {
chudy@google.comc432f002012-07-10 13:19:25 +0000469 QListWidgetItem *item = fListWidget.item(row);
chudy@google.com902ebe52012-06-29 14:21:22 +0000470 if (item->checkState() == Qt::Checked) {
chudy@google.comc432f002012-07-10 13:19:25 +0000471 fListWidget.setCurrentItem(item);
chudy@google.com902ebe52012-06-29 14:21:22 +0000472 return;
473 }
474 }
chudy@google.comc432f002012-07-10 13:19:25 +0000475 fListWidget.setCurrentRow(fListWidget.count() - 1);
chudy@google.com902ebe52012-06-29 14:21:22 +0000476}
477
chudy@google.comea5488b2012-07-26 19:38:22 +0000478void SkDebuggerGUI::actionRasterWidget(bool isToggled) {
479 fCanvasWidget.setWidgetVisibility(SkCanvasWidget::kRaster_8888_WidgetType, !isToggled);
480}
481
chudy@google.com902ebe52012-06-29 14:21:22 +0000482void SkDebuggerGUI::actionRewind() {
chudy@google.come504de02012-07-16 18:35:23 +0000483 fListWidget.setCurrentRow(0);
chudy@google.com902ebe52012-06-29 14:21:22 +0000484}
485
chudy@google.com0ab03392012-07-28 20:16:11 +0000486void SkDebuggerGUI::actionSave() {
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000487 fFileName = fPath.toAscii();
488 fFileName.append("/");
489 fFileName.append(fDirectoryWidget.currentItem()->text().toAscii());
490 saveToFile(fFileName);
chudy@google.com0ab03392012-07-28 20:16:11 +0000491}
492
493void SkDebuggerGUI::actionSaveAs() {
494 QString filename = QFileDialog::getSaveFileName(this, "Save File", "",
495 "Skia Picture (*skp)");
chudy@google.com38b08ce2012-07-28 23:26:10 +0000496 if (!filename.endsWith(".skp", Qt::CaseInsensitive)) {
chudy@google.com0ab03392012-07-28 20:16:11 +0000497 filename.append(".skp");
498 }
djsollen@google.comc3c82162012-11-13 18:35:10 +0000499 saveToFile(SkString(filename.toAscii().data()));
chudy@google.com0ab03392012-07-28 20:16:11 +0000500}
501
chudy@google.com7dcae672012-07-09 20:26:53 +0000502void SkDebuggerGUI::actionScale(float scaleFactor) {
chudy@google.comc432f002012-07-10 13:19:25 +0000503 fSettingsWidget.setZoomText(scaleFactor);
chudy@google.com7dcae672012-07-09 20:26:53 +0000504}
505
chudy@google.com902ebe52012-06-29 14:21:22 +0000506void SkDebuggerGUI::actionSettings() {
chudy@google.comc432f002012-07-10 13:19:25 +0000507 if (fSettingsWidget.isHidden()) {
508 fSettingsWidget.setHidden(false);
chudy@google.com902ebe52012-06-29 14:21:22 +0000509 } else {
chudy@google.comc432f002012-07-10 13:19:25 +0000510 fSettingsWidget.setHidden(true);
chudy@google.com902ebe52012-06-29 14:21:22 +0000511 }
512}
513
514void SkDebuggerGUI::actionStepBack() {
chudy@google.comc432f002012-07-10 13:19:25 +0000515 int currentRow = fListWidget.currentRow();
chudy@google.com902ebe52012-06-29 14:21:22 +0000516 if (currentRow != 0) {
chudy@google.comc432f002012-07-10 13:19:25 +0000517 fListWidget.setCurrentRow(currentRow - 1);
chudy@google.com902ebe52012-06-29 14:21:22 +0000518 }
519}
520
521void SkDebuggerGUI::actionStepForward() {
chudy@google.comc432f002012-07-10 13:19:25 +0000522 int currentRow = fListWidget.currentRow();
chudy@google.com902ebe52012-06-29 14:21:22 +0000523 QString curRow = QString::number(currentRow);
chudy@google.comc432f002012-07-10 13:19:25 +0000524 QString curCount = QString::number(fListWidget.count());
525 if (currentRow < fListWidget.count() - 1) {
526 fListWidget.setCurrentRow(currentRow + 1);
chudy@google.com902ebe52012-06-29 14:21:22 +0000527 }
528}
529
chudy@google.coma9e937c2012-08-03 17:32:05 +0000530void SkDebuggerGUI::drawComplete() {
chudy@google.com607357f2012-08-07 16:12:23 +0000531 fInspectorWidget.setMatrix(fDebugger.getCurrentMatrix());
532 fInspectorWidget.setClip(fDebugger.getCurrentClip());
chudy@google.coma9e937c2012-08-03 17:32:05 +0000533}
534
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000535void SkDebuggerGUI::saveToFile(const SkString& filename) {
536 SkFILEWStream file(filename.c_str());
chudy@google.com607357f2012-08-07 16:12:23 +0000537 fDebugger.makePicture()->serialize(&file);
chudy@google.com0ab03392012-07-28 20:16:11 +0000538}
539
chudy@google.com902ebe52012-06-29 14:21:22 +0000540void SkDebuggerGUI::loadFile(QListWidgetItem *item) {
541 if (fDirectoryWidgetActive) {
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000542 fFileName = fPath.toAscii();
543 fFileName.append("/");
544 fFileName.append(item->text().toAscii());
545 loadPicture(fFileName);
chudy@google.com902ebe52012-06-29 14:21:22 +0000546 }
547}
548
549void SkDebuggerGUI::openFile() {
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000550 QString temp = QFileDialog::getOpenFileName(this, tr("Open File"), "",
chudy@google.com7dcae672012-07-09 20:26:53 +0000551 tr("Files (*.*)"));
chudy@google.com902ebe52012-06-29 14:21:22 +0000552 fDirectoryWidgetActive = false;
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000553 if (!temp.isEmpty()) {
554 QFileInfo pathInfo(temp);
chudy@google.com902ebe52012-06-29 14:21:22 +0000555 fPath = pathInfo.path();
djsollen@google.comc3c82162012-11-13 18:35:10 +0000556 loadPicture(SkString(temp.toAscii().data()));
chudy@google.com902ebe52012-06-29 14:21:22 +0000557 setupDirectoryWidget();
558 }
chudy@google.com902ebe52012-06-29 14:21:22 +0000559 fDirectoryWidgetActive = true;
560}
561
chudy@google.comc432f002012-07-10 13:19:25 +0000562void SkDebuggerGUI::pauseDrawing(bool isPaused) {
chudy@google.com607357f2012-08-07 16:12:23 +0000563 fPause = isPaused;
564 fPausedRow = fListWidget.currentRow();
565 fCanvasWidget.drawTo(fPausedRow);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000566 fImageWidget.draw();
chudy@google.com7dcae672012-07-09 20:26:53 +0000567}
568
chudy@google.com902ebe52012-06-29 14:21:22 +0000569void SkDebuggerGUI::registerListClick(QListWidgetItem *item) {
chudy@google.comd3058f52012-07-19 13:41:27 +0000570 if(!fLoading) {
571 int currentRow = fListWidget.currentRow();
chudy@google.comd3058f52012-07-19 13:41:27 +0000572
chudy@google.comea5488b2012-07-26 19:38:22 +0000573 if (currentRow != -1) {
574 if (!fPause) {
575 fCanvasWidget.drawTo(currentRow);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000576 fImageWidget.draw();
chudy@google.comd3058f52012-07-19 13:41:27 +0000577 }
chudy@google.com97cee972012-08-07 20:41:37 +0000578 SkTDArray<SkString*> *currInfo = fDebugger.getCommandInfo(
chudy@google.comea5488b2012-07-26 19:38:22 +0000579 currentRow);
580
581 /* TODO(chudy): Add command type before parameters. Rename v
582 * to something more informative. */
chudy@google.com97cee972012-08-07 20:41:37 +0000583 if (currInfo) {
chudy@google.comea5488b2012-07-26 19:38:22 +0000584 QString info;
585 info.append("<b>Parameters: </b><br/>");
chudy@google.com97cee972012-08-07 20:41:37 +0000586 for (int i = 0; i < currInfo->count(); i++) {
587
588 info.append(QString((*currInfo)[i]->c_str()));
chudy@google.comea5488b2012-07-26 19:38:22 +0000589 info.append("<br/>");
590 }
chudy@google.com6bd109a2012-08-14 19:34:13 +0000591 fInspectorWidget.setText(info, SkInspectorWidget::kDetail_TabType);
chudy@google.comea5488b2012-07-26 19:38:22 +0000592 fInspectorWidget.setDisabled(false);
chudy@google.comea5488b2012-07-26 19:38:22 +0000593 }
chudy@google.comd3058f52012-07-19 13:41:27 +0000594 }
chudy@google.comea5488b2012-07-26 19:38:22 +0000595
chudy@google.com902ebe52012-06-29 14:21:22 +0000596 }
597}
598
chudy@google.com9ca9bfe2012-07-12 21:58:14 +0000599void SkDebuggerGUI::selectCommand(int command) {
600 if (fPause) {
601 fListWidget.setCurrentRow(command);
602 }
603}
604
chudy@google.com902ebe52012-06-29 14:21:22 +0000605void SkDebuggerGUI::toggleBreakpoint() {
chudy@google.comc432f002012-07-10 13:19:25 +0000606 QListWidgetItem* item = fListWidget.currentItem();
chudy@google.com902ebe52012-06-29 14:21:22 +0000607 if (item->checkState() == Qt::Unchecked) {
608 item->setCheckState(Qt::Checked);
chudy@google.come565de42012-07-12 14:15:54 +0000609 item->setData(Qt::DecorationRole,
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000610 QPixmap(":/breakpoint_16x16.png"));
chudy@google.com902ebe52012-06-29 14:21:22 +0000611 } else {
chudy@google.com902ebe52012-06-29 14:21:22 +0000612 item->setCheckState(Qt::Unchecked);
chudy@google.come565de42012-07-12 14:15:54 +0000613 item->setData(Qt::DecorationRole,
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000614 QPixmap(":/blank.png"));
chudy@google.com902ebe52012-06-29 14:21:22 +0000615 }
616}
617
618void SkDebuggerGUI::toggleDirectory() {
chudy@google.com607357f2012-08-07 16:12:23 +0000619 fDirectoryWidget.setHidden(!fDirectoryWidget.isHidden());
chudy@google.com902ebe52012-06-29 14:21:22 +0000620}
621
622void SkDebuggerGUI::toggleFilter(QString string) {
chudy@google.comc432f002012-07-10 13:19:25 +0000623 for (int row = 0; row < fListWidget.count(); row++) {
624 QListWidgetItem *item = fListWidget.item(row);
chudy@google.com607357f2012-08-07 16:12:23 +0000625 item->setHidden(item->text() != string);
chudy@google.com902ebe52012-06-29 14:21:22 +0000626 }
627}
628
629void SkDebuggerGUI::setupUi(QMainWindow *SkDebuggerGUI) {
630 QIcon windowIcon;
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000631 windowIcon.addFile(QString::fromUtf8(":/skia.png"), QSize(),
chudy@google.com7dcae672012-07-09 20:26:53 +0000632 QIcon::Normal, QIcon::Off);
chudy@google.com902ebe52012-06-29 14:21:22 +0000633 SkDebuggerGUI->setObjectName(QString::fromUtf8("SkDebuggerGUI"));
634 SkDebuggerGUI->resize(1200, 1000);
635 SkDebuggerGUI->setWindowIcon(windowIcon);
chudy@google.comc432f002012-07-10 13:19:25 +0000636 SkDebuggerGUI->setWindowTitle("Skia Debugger");
chudy@google.com902ebe52012-06-29 14:21:22 +0000637
chudy@google.come504de02012-07-16 18:35:23 +0000638 fActionOpen.setShortcuts(QKeySequence::Open);
chudy@google.comc432f002012-07-10 13:19:25 +0000639 fActionOpen.setText("Open");
chudy@google.com902ebe52012-06-29 14:21:22 +0000640
641 QIcon breakpoint;
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000642 breakpoint.addFile(QString::fromUtf8(":/breakpoint.png"),
chudy@google.com7dcae672012-07-09 20:26:53 +0000643 QSize(), QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000644 fActionBreakpoint.setShortcut(QKeySequence(tr("Ctrl+B")));
chudy@google.comc432f002012-07-10 13:19:25 +0000645 fActionBreakpoint.setIcon(breakpoint);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000646 fActionBreakpoint.setText("Breakpoints");
chudy@google.com902ebe52012-06-29 14:21:22 +0000647
648 QIcon cancel;
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000649 cancel.addFile(QString::fromUtf8(":/reload.png"), QSize(),
chudy@google.com7dcae672012-07-09 20:26:53 +0000650 QIcon::Normal, QIcon::Off);
chudy@google.comc432f002012-07-10 13:19:25 +0000651 fActionCancel.setIcon(cancel);
652 fActionCancel.setText("Clear Filter");
chudy@google.com902ebe52012-06-29 14:21:22 +0000653
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000654 fActionClearBreakpoints.setShortcut(QKeySequence(tr("Alt+B")));
655 fActionClearBreakpoints.setText("Clear Breakpoints");
656
657 fActionClearDeletes.setShortcut(QKeySequence(tr("Alt+X")));
658 fActionClearDeletes.setText("Clear Deletes");
659
chudy@google.come504de02012-07-16 18:35:23 +0000660 fActionClose.setShortcuts(QKeySequence::Quit);
chudy@google.comc432f002012-07-10 13:19:25 +0000661 fActionClose.setText("Exit");
chudy@google.com902ebe52012-06-29 14:21:22 +0000662
chudy@google.come504de02012-07-16 18:35:23 +0000663 fActionCreateBreakpoint.setShortcut(QKeySequence(tr("B")));
664 fActionCreateBreakpoint.setText("Set Breakpoint");
665
666 fActionDelete.setShortcut(QKeySequence(tr("X")));
chudy@google.comc432f002012-07-10 13:19:25 +0000667 fActionDelete.setText("Delete Command");
chudy@google.com902ebe52012-06-29 14:21:22 +0000668
chudy@google.come504de02012-07-16 18:35:23 +0000669 fActionDirectory.setShortcut(QKeySequence(tr("Ctrl+D")));
670 fActionDirectory.setText("Directory");
chudy@google.com902ebe52012-06-29 14:21:22 +0000671
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000672 QIcon profile;
robertphillips@google.comd1636362012-11-19 18:25:09 +0000673 profile.addFile(QString::fromUtf8(":/profile.png"), QSize(),
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000674 QIcon::Normal, QIcon::Off);
675 fActionProfile.setIcon(profile);
676 fActionProfile.setText("Profile");
robertphillips@google.come099bc42012-11-19 16:26:40 +0000677 fActionProfile.setDisabled(true);
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000678
chudy@google.comc432f002012-07-10 13:19:25 +0000679 QIcon inspector;
robertphillips@google.comd1636362012-11-19 18:25:09 +0000680 inspector.addFile(QString::fromUtf8(":/inspector.png"),
chudy@google.comc432f002012-07-10 13:19:25 +0000681 QSize(), QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000682 fActionInspector.setShortcut(QKeySequence(tr("Ctrl+I")));
chudy@google.comc432f002012-07-10 13:19:25 +0000683 fActionInspector.setIcon(inspector);
chudy@google.come504de02012-07-16 18:35:23 +0000684 fActionInspector.setText("Inspector");
chudy@google.com902ebe52012-06-29 14:21:22 +0000685
chudy@google.comc432f002012-07-10 13:19:25 +0000686 QIcon play;
robertphillips@google.comd1636362012-11-19 18:25:09 +0000687 play.addFile(QString::fromUtf8(":/play.png"), QSize(),
chudy@google.comc432f002012-07-10 13:19:25 +0000688 QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000689 fActionPlay.setShortcut(QKeySequence(tr("Ctrl+P")));
chudy@google.comc432f002012-07-10 13:19:25 +0000690 fActionPlay.setIcon(play);
691 fActionPlay.setText("Play");
chudy@google.com902ebe52012-06-29 14:21:22 +0000692
chudy@google.come504de02012-07-16 18:35:23 +0000693 QIcon pause;
robertphillips@google.comd1636362012-11-19 18:25:09 +0000694 pause.addFile(QString::fromUtf8(":/pause.png"), QSize(),
chudy@google.comc432f002012-07-10 13:19:25 +0000695 QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000696 fActionPause.setShortcut(QKeySequence(tr("Space")));
697 fActionPause.setCheckable(true);
698 fActionPause.setIcon(pause);
699 fActionPause.setText("Pause");
700
chudy@google.comc432f002012-07-10 13:19:25 +0000701 QIcon rewind;
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000702 rewind.addFile(QString::fromUtf8(":/rewind.png"), QSize(),
chudy@google.comc432f002012-07-10 13:19:25 +0000703 QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000704 fActionRewind.setShortcut(QKeySequence(tr("Ctrl+R")));
chudy@google.comc432f002012-07-10 13:19:25 +0000705 fActionRewind.setIcon(rewind);
706 fActionRewind.setText("Rewind");
chudy@google.com902ebe52012-06-29 14:21:22 +0000707
chudy@google.com0ab03392012-07-28 20:16:11 +0000708 fActionSave.setShortcut(QKeySequence::Save);
709 fActionSave.setText("Save");
710 fActionSave.setDisabled(true);
711 fActionSaveAs.setShortcut(QKeySequence::SaveAs);
712 fActionSaveAs.setText("Save As");
713 fActionSaveAs.setDisabled(true);
714
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000715 fActionShowDeletes.setShortcut(QKeySequence(tr("Ctrl+X")));
716 fActionShowDeletes.setText("Deleted Commands");
717
chudy@google.comc432f002012-07-10 13:19:25 +0000718 QIcon stepBack;
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000719 stepBack.addFile(QString::fromUtf8(":/previous.png"), QSize(),
chudy@google.comc432f002012-07-10 13:19:25 +0000720 QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000721 fActionStepBack.setShortcut(QKeySequence(tr("[")));
chudy@google.comc432f002012-07-10 13:19:25 +0000722 fActionStepBack.setIcon(stepBack);
723 fActionStepBack.setText("Step Back");
chudy@google.com902ebe52012-06-29 14:21:22 +0000724
chudy@google.comc432f002012-07-10 13:19:25 +0000725 QIcon stepForward;
robertphillips@google.com8e41a162012-11-19 17:39:18 +0000726 stepForward.addFile(QString::fromUtf8(":/next.png"),
chudy@google.comc432f002012-07-10 13:19:25 +0000727 QSize(), QIcon::Normal, QIcon::Off);
chudy@google.come504de02012-07-16 18:35:23 +0000728 fActionStepForward.setShortcut(QKeySequence(tr("]")));
chudy@google.comc432f002012-07-10 13:19:25 +0000729 fActionStepForward.setIcon(stepForward);
730 fActionStepForward.setText("Step Forward");
731
chudy@google.coma1226312012-07-26 20:26:44 +0000732 fActionZoomIn.setShortcut(QKeySequence(tr("Ctrl+=")));
733 fActionZoomIn.setText("Zoom In");
734 fActionZoomOut.setShortcut(QKeySequence(tr("Ctrl+-")));
735 fActionZoomOut.setText("Zoom Out");
736
chudy@google.comc432f002012-07-10 13:19:25 +0000737 fListWidget.setItemDelegate(new SkListWidget(&fListWidget));
738 fListWidget.setObjectName(QString::fromUtf8("listWidget"));
739 fListWidget.setMaximumWidth(250);
740
741 fFilter.addItem("--Filter By Available Commands--");
742
743 fDirectoryWidget.setMaximumWidth(250);
744 fDirectoryWidget.setStyleSheet("QListWidget::Item {padding: 5px;}");
745
746 fCanvasWidget.setSizePolicy(QSizePolicy::Expanding,
chudy@google.com7dcae672012-07-09 20:26:53 +0000747 QSizePolicy::Expanding);
chudy@google.com902ebe52012-06-29 14:21:22 +0000748
skia.committer@gmail.com1c9c0d32012-11-22 02:02:41 +0000749 fImageWidget.setFixedSize(SkImageWidget::kImageWidgetWidth,
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000750 SkImageWidget::kImageWidgetHeight);
751
chudy@google.comc432f002012-07-10 13:19:25 +0000752 fInspectorWidget.setSizePolicy(QSizePolicy::Expanding,
chudy@google.com7dcae672012-07-09 20:26:53 +0000753 QSizePolicy::Expanding);
chudy@google.comc432f002012-07-10 13:19:25 +0000754 fInspectorWidget.setMaximumHeight(300);
chudy@google.com902ebe52012-06-29 14:21:22 +0000755
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000756 fSettingsAndImageLayout.setSpacing(6);
757 fSettingsAndImageLayout.addWidget(&fSettingsWidget);
758 fSettingsAndImageLayout.addWidget(&fImageWidget);
759
chudy@google.comc432f002012-07-10 13:19:25 +0000760 fSettingsWidget.setSizePolicy(QSizePolicy::Expanding,
761 QSizePolicy::Expanding);
762 fSettingsWidget.setMaximumWidth(250);
chudy@google.com902ebe52012-06-29 14:21:22 +0000763
chudy@google.comc432f002012-07-10 13:19:25 +0000764 fLeftColumnLayout.setSpacing(6);
765 fLeftColumnLayout.addWidget(&fListWidget);
766 fLeftColumnLayout.addWidget(&fDirectoryWidget);
chudy@google.com902ebe52012-06-29 14:21:22 +0000767
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000768 fCanvasSettingsAndImageLayout.setSpacing(6);
769 fCanvasSettingsAndImageLayout.addWidget(&fCanvasWidget);
770 fCanvasSettingsAndImageLayout.addLayout(&fSettingsAndImageLayout);
771
chudy@google.com902ebe52012-06-29 14:21:22 +0000772
chudy@google.comc432f002012-07-10 13:19:25 +0000773 fMainAndRightColumnLayout.setSpacing(6);
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +0000774 fMainAndRightColumnLayout.addLayout(&fCanvasSettingsAndImageLayout);
chudy@google.comc432f002012-07-10 13:19:25 +0000775 fMainAndRightColumnLayout.addWidget(&fInspectorWidget);
chudy@google.com902ebe52012-06-29 14:21:22 +0000776
chudy@google.com2d537a12012-07-31 12:49:52 +0000777 fCentralWidget.setLayout(&fContainerLayout);
chudy@google.comc432f002012-07-10 13:19:25 +0000778 fContainerLayout.setSpacing(6);
779 fContainerLayout.setContentsMargins(11, 11, 11, 11);
780 fContainerLayout.addLayout(&fLeftColumnLayout);
781 fContainerLayout.addLayout(&fMainAndRightColumnLayout);
782
783 SkDebuggerGUI->setCentralWidget(&fCentralWidget);
784 SkDebuggerGUI->setStatusBar(&fStatusBar);
785
chudy@google.come504de02012-07-16 18:35:23 +0000786 fToolBar.setIconSize(QSize(32, 32));
chudy@google.comc432f002012-07-10 13:19:25 +0000787 fToolBar.setToolButtonStyle(Qt::ToolButtonTextUnderIcon);
788 SkDebuggerGUI->addToolBar(Qt::TopToolBarArea, &fToolBar);
chudy@google.com902ebe52012-06-29 14:21:22 +0000789
chudy@google.com0ab03392012-07-28 20:16:11 +0000790 fSpacer.setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
chudy@google.com902ebe52012-06-29 14:21:22 +0000791
chudy@google.comc432f002012-07-10 13:19:25 +0000792 fToolBar.addAction(&fActionRewind);
793 fToolBar.addAction(&fActionStepBack);
chudy@google.come504de02012-07-16 18:35:23 +0000794 fToolBar.addAction(&fActionPause);
chudy@google.comc432f002012-07-10 13:19:25 +0000795 fToolBar.addAction(&fActionStepForward);
796 fToolBar.addAction(&fActionPlay);
797 fToolBar.addSeparator();
chudy@google.come504de02012-07-16 18:35:23 +0000798 fToolBar.addAction(&fActionInspector);
chudy@google.comc432f002012-07-10 13:19:25 +0000799 fToolBar.addSeparator();
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000800 fToolBar.addAction(&fActionProfile);
801
802 fToolBar.addSeparator();
chudy@google.com0ab03392012-07-28 20:16:11 +0000803 fToolBar.addWidget(&fSpacer);
chudy@google.comc432f002012-07-10 13:19:25 +0000804 fToolBar.addWidget(&fFilter);
805 fToolBar.addAction(&fActionCancel);
chudy@google.com902ebe52012-06-29 14:21:22 +0000806
807 // TODO(chudy): Remove static call.
808 fDirectoryWidgetActive = false;
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000809 fPath = "";
810 fFileName = "";
chudy@google.com902ebe52012-06-29 14:21:22 +0000811 setupDirectoryWidget();
812 fDirectoryWidgetActive = true;
813
chudy@google.com902ebe52012-06-29 14:21:22 +0000814 // Menu Bar
chudy@google.comc432f002012-07-10 13:19:25 +0000815 fMenuFile.setTitle("File");
816 fMenuFile.addAction(&fActionOpen);
chudy@google.com0ab03392012-07-28 20:16:11 +0000817 fMenuFile.addAction(&fActionSave);
818 fMenuFile.addAction(&fActionSaveAs);
chudy@google.comc432f002012-07-10 13:19:25 +0000819 fMenuFile.addAction(&fActionClose);
chudy@google.come504de02012-07-16 18:35:23 +0000820
821 fMenuEdit.setTitle("Edit");
822 fMenuEdit.addAction(&fActionDelete);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000823 fMenuEdit.addAction(&fActionClearDeletes);
824 fMenuEdit.addSeparator();
chudy@google.come504de02012-07-16 18:35:23 +0000825 fMenuEdit.addAction(&fActionCreateBreakpoint);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000826 fMenuEdit.addAction(&fActionClearBreakpoints);
chudy@google.come504de02012-07-16 18:35:23 +0000827
chudy@google.comc432f002012-07-10 13:19:25 +0000828 fMenuNavigate.setTitle("Navigate");
chudy@google.come504de02012-07-16 18:35:23 +0000829 fMenuNavigate.addAction(&fActionRewind);
830 fMenuNavigate.addAction(&fActionStepBack);
831 fMenuNavigate.addAction(&fActionStepForward);
832 fMenuNavigate.addAction(&fActionPlay);
833 fMenuNavigate.addAction(&fActionPause);
chudy@google.comc432f002012-07-10 13:19:25 +0000834 fMenuNavigate.addAction(&fActionGoToLine);
chudy@google.come504de02012-07-16 18:35:23 +0000835
chudy@google.comc432f002012-07-10 13:19:25 +0000836 fMenuView.setTitle("View");
chudy@google.come504de02012-07-16 18:35:23 +0000837 fMenuView.addAction(&fActionBreakpoint);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000838 fMenuView.addAction(&fActionShowDeletes);
chudy@google.coma1226312012-07-26 20:26:44 +0000839 fMenuView.addAction(&fActionZoomIn);
840 fMenuView.addAction(&fActionZoomOut);
chudy@google.come504de02012-07-16 18:35:23 +0000841
842 fMenuWindows.setTitle("Window");
843 fMenuWindows.addAction(&fActionInspector);
844 fMenuWindows.addAction(&fActionDirectory);
chudy@google.comc432f002012-07-10 13:19:25 +0000845
846 fActionGoToLine.setText("Go to Line...");
847 fActionGoToLine.setDisabled(true);
848 fMenuBar.addAction(fMenuFile.menuAction());
chudy@google.come504de02012-07-16 18:35:23 +0000849 fMenuBar.addAction(fMenuEdit.menuAction());
chudy@google.comc432f002012-07-10 13:19:25 +0000850 fMenuBar.addAction(fMenuView.menuAction());
851 fMenuBar.addAction(fMenuNavigate.menuAction());
chudy@google.come504de02012-07-16 18:35:23 +0000852 fMenuBar.addAction(fMenuWindows.menuAction());
chudy@google.com902ebe52012-06-29 14:21:22 +0000853
chudy@google.com7dcae672012-07-09 20:26:53 +0000854 fPause = false;
855
chudy@google.comc432f002012-07-10 13:19:25 +0000856 SkDebuggerGUI->setMenuBar(&fMenuBar);
chudy@google.com902ebe52012-06-29 14:21:22 +0000857 QMetaObject::connectSlotsByName(SkDebuggerGUI);
858}
859
860void SkDebuggerGUI::setupDirectoryWidget() {
chudy@google.comc432f002012-07-10 13:19:25 +0000861 QDir dir(fPath);
chudy@google.com902ebe52012-06-29 14:21:22 +0000862 QRegExp r(".skp");
chudy@google.comc432f002012-07-10 13:19:25 +0000863 fDirectoryWidget.clear();
864 const QStringList files = dir.entryList();
chudy@google.com902ebe52012-06-29 14:21:22 +0000865 foreach (QString f, files) {
chudy@google.com7dcae672012-07-09 20:26:53 +0000866 if (f.contains(r))
chudy@google.comc432f002012-07-10 13:19:25 +0000867 fDirectoryWidget.addItem(f);
chudy@google.com902ebe52012-06-29 14:21:22 +0000868 }
869}
870
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000871// SkOffsetPicturePlayback records the offset of each command in the picture.
872// These are needed by the profiling system.
873class SkOffsetPicturePlayback : public SkPicturePlayback {
874public:
875 SkOffsetPicturePlayback(SkStream* stream, const SkPictInfo& info, bool* isValid,
876 SkSerializationHelpers::DecodeBitmap decoder)
877 : INHERITED(stream, info, isValid, decoder) {
878 }
879
880 const SkTDArray<size_t>& offsets() const { return fOffsets; }
881
882protected:
883 SkTDArray<size_t> fOffsets;
884
885 virtual void preDraw(size_t offset, int type) {
886 *fOffsets.append() = offset;
887 }
888
889private:
890 typedef SkPicturePlayback INHERITED;
891};
892
893// Picture to wrap an SkOffsetPicturePlayback.
894class SkOffsetPicture : public SkPicture {
895public:
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000896 SkOffsetPicture(SkStream* stream,
897 bool* success,
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000898 SkSerializationHelpers::DecodeBitmap decoder) {
899 if (success) {
900 *success = false;
901 }
902 fRecord = NULL;
903 fPlayback = NULL;
904 fWidth = fHeight = 0;
905
906 SkPictInfo info;
907
908 if (!stream->read(&info, sizeof(info))) {
909 return;
910 }
911 if (PICTURE_VERSION != info.fVersion) {
912 return;
913 }
914
915 if (stream->readBool()) {
916 bool isValid = false;
917 fPlayback = SkNEW_ARGS(SkOffsetPicturePlayback, (stream, info, &isValid, decoder));
918 if (!isValid) {
919 SkDELETE(fPlayback);
920 fPlayback = NULL;
921 return;
922 }
923 }
924
925 // do this at the end, so that they will be zero if we hit an error.
926 fWidth = info.fWidth;
927 fHeight = info.fHeight;
928 if (success) {
929 *success = true;
930 }
931 }
932
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +0000933 const SkTDArray<size_t>& offsets() const {
934 return ((SkOffsetPicturePlayback*) fPlayback)->offsets();
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000935 }
936
937private:
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000938 // disallow default ctor b.c. we don't have a good way to setup the fPlayback ptr
939 SkOffsetPicture();
940 // disallow the copy ctor - enabling would require copying code from SkPicture
941 SkOffsetPicture(const SkOffsetPicture& src);
942
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000943 typedef SkPicture INHERITED;
944};
945
946
947
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000948void SkDebuggerGUI::loadPicture(const SkString& fileName) {
949 fFileName = fileName;
chudy@google.comd3058f52012-07-19 13:41:27 +0000950 fLoading = true;
robertphillips@google.comd26c7062012-11-12 20:42:12 +0000951 SkStream* stream = SkNEW_ARGS(SkFILEStream, (fileName.c_str()));
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000952 SkOffsetPicture* picture = SkNEW_ARGS(SkOffsetPicture, (stream, NULL, &SkImageDecoder::DecodeStream));
953
chudy@google.com686e6802012-08-14 16:00:32 +0000954 fCanvasWidget.resetWidgetTransform();
chudy@google.com607357f2012-08-07 16:12:23 +0000955 fDebugger.loadPicture(picture);
chudy@google.com4c7962e2012-08-14 19:38:31 +0000956
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000957 fOffsets = picture->offsets();
958
chudy@google.com607357f2012-08-07 16:12:23 +0000959 SkSafeUnref(stream);
960 SkSafeUnref(picture);
961
chudy@google.com97cee972012-08-07 20:41:37 +0000962 // Will this automatically clear out due to nature of refcnt?
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000963 SkTArray<SkString>* commands = fDebugger.getDrawCommandsAsStrings();
chudy@google.com607357f2012-08-07 16:12:23 +0000964
robertphillips@google.comfe830a42012-11-15 16:33:31 +0000965 // If SkPicturePlayback is compiled w/o SK_PICTURE_PROFILING_STUBS
966 // the offset count will always be zero
967 SkASSERT(0 == fOffsets.count() || commands->count() == fOffsets.count());
robertphillips@google.come099bc42012-11-19 16:26:40 +0000968 if (commands->count() == fOffsets.count()) {
969 fActionProfile.setDisabled(false);
robertphillips@google.comfe830a42012-11-15 16:33:31 +0000970 }
robertphillips@google.com2bde91d2012-11-15 14:57:57 +0000971
chudy@google.com7dcae672012-07-09 20:26:53 +0000972 /* fDebugCanvas is reinitialized every load picture. Need it to retain value
chudy@google.com607357f2012-08-07 16:12:23 +0000973 * of the visibility filter.
974 * TODO(chudy): This should be deprecated since fDebugger is not
975 * recreated.
976 * */
977 fDebugger.highlightCurrentCommand(fSettingsWidget.getVisibilityButton()->isChecked());
978
chudy@google.com97cee972012-08-07 20:41:37 +0000979 setupListWidget(commands);
980 setupComboBox(commands);
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000981 setupOverviewText(NULL, 0.0);
chudy@google.com7e4cfbf2012-07-17 15:40:51 +0000982 fInspectorWidget.setDisabled(false);
chudy@google.come606d6e2012-07-12 14:31:25 +0000983 fSettingsWidget.setDisabled(false);
chudy@google.comd3058f52012-07-19 13:41:27 +0000984 fMenuEdit.setDisabled(false);
985 fMenuNavigate.setDisabled(false);
986 fMenuView.setDisabled(false);
chudy@google.com0ab03392012-07-28 20:16:11 +0000987 fActionSave.setDisabled(false);
988 fActionSaveAs.setDisabled(false);
chudy@google.comd3058f52012-07-19 13:41:27 +0000989 fLoading = false;
990 actionPlay();
chudy@google.com902ebe52012-06-29 14:21:22 +0000991}
992
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000993void SkDebuggerGUI::setupListWidget(SkTArray<SkString>* command) {
chudy@google.comc432f002012-07-10 13:19:25 +0000994 fListWidget.clear();
chudy@google.com902ebe52012-06-29 14:21:22 +0000995 int counter = 0;
robertphillips@google.com30d35f22012-11-06 16:45:36 +0000996 int indent = 0;
chudy@google.com97cee972012-08-07 20:41:37 +0000997 for (int i = 0; i < command->count(); i++) {
chudy@google.com902ebe52012-06-29 14:21:22 +0000998 QListWidgetItem *item = new QListWidgetItem();
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +0000999 item->setData(Qt::DisplayRole, (*command)[i].c_str());
chudy@google.com902ebe52012-06-29 14:21:22 +00001000 item->setData(Qt::UserRole + 1, counter++);
robertphillips@google.com30d35f22012-11-06 16:45:36 +00001001
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001002 if (0 == strcmp("Restore", (*command)[i].c_str())) {
robertphillips@google.com30d35f22012-11-06 16:45:36 +00001003 indent -= 10;
1004 }
1005
1006 item->setData(Qt::UserRole + 3, indent);
1007
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001008 if (0 == strcmp("Save", (*command)[i].c_str()) ||
1009 0 == strcmp("Save Layer", (*command)[i].c_str())) {
robertphillips@google.com30d35f22012-11-06 16:45:36 +00001010 indent += 10;
1011 }
1012
robertphillips@google.comd26c7062012-11-12 20:42:12 +00001013 item->setData(Qt::UserRole + 4, -1.0);
1014
chudy@google.comc432f002012-07-10 13:19:25 +00001015 fListWidget.addItem(item);
chudy@google.com902ebe52012-06-29 14:21:22 +00001016 }
1017}
1018
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001019void SkDebuggerGUI::setupOverviewText(const SkTDArray<double>* typeTimes, double totTime) {
chudy@google.com902ebe52012-06-29 14:21:22 +00001020
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001021 const SkTDArray<SkDrawCommand*>& commands = fDebugger.getDrawCommands();
1022
1023 SkTDArray<int> counts;
1024 counts.setCount(LAST_DRAWTYPE_ENUM+1);
1025 for (int i = 0; i < LAST_DRAWTYPE_ENUM+1; ++i) {
1026 counts[i] = 0;
1027 }
1028
1029 for (int i = 0; i < commands.count(); i++) {
1030 counts[commands[i]->getType()]++;
chudy@google.com902ebe52012-06-29 14:21:22 +00001031 }
1032
1033 QString overview;
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001034 int total = 0;
1035#ifdef SK_DEBUG
1036 double totPercent = 0, tempSum = 0;
1037#endif
1038 for (int i = 0; i < LAST_DRAWTYPE_ENUM+1; ++i) {
1039 if (0 == counts[i]) {
1040 // if there were no commands of this type then they should've consumed no time
1041 SkASSERT(NULL == typeTimes || 0.0 == (*typeTimes)[i]);
1042 continue;
1043 }
1044
1045 overview.append(SkDrawCommand::GetCommandString((DrawType) i));
chudy@google.com902ebe52012-06-29 14:21:22 +00001046 overview.append(": ");
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001047 overview.append(QString::number(counts[i]));
1048 if (NULL != typeTimes) {
1049 overview.append(" - ");
1050 overview.append(QString::number((*typeTimes)[i], 'f', 1));
1051 overview.append("ms");
1052 overview.append(" - ");
1053 double percent = 100.0*(*typeTimes)[i]/totTime;
1054 overview.append(QString::number(percent, 'f', 1));
1055 overview.append("%");
1056#ifdef SK_DEBUG
1057 totPercent += percent;
1058 tempSum += (*typeTimes)[i];
1059#endif
1060 }
chudy@google.com902ebe52012-06-29 14:21:22 +00001061 overview.append("<br/>");
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001062 total += counts[i];
chudy@google.com902ebe52012-06-29 14:21:22 +00001063 }
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001064#ifdef SK_DEBUG
1065 if (NULL != typeTimes) {
1066 SkASSERT(SkScalarNearlyEqual(totPercent, 100.0));
1067 SkASSERT(SkScalarNearlyEqual(tempSum, totTime));
1068 }
1069#endif
1070
1071 if (totTime > 0.0) {
1072 overview.append("Total Time: ");
1073 overview.append(QString::number(totTime, 'f', 2));
1074 overview.append("ms");
1075#ifdef SK_DEBUG
1076 overview.append(" ");
1077 overview.append(QString::number(totPercent));
1078 overview.append("% ");
1079#endif
1080 overview.append("<br/>");
1081 }
1082
1083 QString totalStr;
1084 totalStr.append("Total Draw Commands: ");
1085 totalStr.append(QString::number(total));
1086 totalStr.append("<br/>");
1087 overview.insert(0, totalStr);
chudy@google.com902ebe52012-06-29 14:21:22 +00001088
1089 overview.append("<br/>");
chudy@google.com607357f2012-08-07 16:12:23 +00001090 overview.append("SkPicture Width: ");
chudy@google.com902ebe52012-06-29 14:21:22 +00001091 // NOTE(chudy): This is where we can pull out the SkPictures width.
chudy@google.com607357f2012-08-07 16:12:23 +00001092 overview.append(QString::number(fDebugger.pictureWidth()));
chudy@google.com902ebe52012-06-29 14:21:22 +00001093 overview.append("px<br/>");
chudy@google.com607357f2012-08-07 16:12:23 +00001094 overview.append("SkPicture Height: ");
1095 overview.append(QString::number(fDebugger.pictureHeight()));
chudy@google.com902ebe52012-06-29 14:21:22 +00001096 overview.append("px");
chudy@google.com6bd109a2012-08-14 19:34:13 +00001097 fInspectorWidget.setText(overview, SkInspectorWidget::kOverview_TabType);
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001098}
1099
1100void SkDebuggerGUI::setupComboBox(SkTArray<SkString>* command) {
1101 fFilter.clear();
1102 fFilter.addItem("--Filter By Available Commands--");
1103
1104 std::map<std::string, int> map;
1105 for (int i = 0; i < command->count(); i++) {
1106 map[(*command)[i].c_str()]++;
1107 }
1108
skia.committer@gmail.com34587162012-11-20 02:01:23 +00001109 for (std::map<std::string, int>::iterator it = map.begin(); it != map.end();
robertphillips@google.com8a1cdae2012-11-19 20:44:29 +00001110 ++it) {
1111 fFilter.addItem((it->first).c_str());
1112 }
chudy@google.com902ebe52012-06-29 14:21:22 +00001113
1114 // NOTE(chudy): Makes first item unselectable.
chudy@google.com7dcae672012-07-09 20:26:53 +00001115 QStandardItemModel* model = qobject_cast<QStandardItemModel*>(
chudy@google.comc432f002012-07-10 13:19:25 +00001116 fFilter.model());
1117 QModelIndex firstIndex = model->index(0, fFilter.modelColumn(),
1118 fFilter.rootModelIndex());
chudy@google.com902ebe52012-06-29 14:21:22 +00001119 QStandardItem* firstItem = model->itemFromIndex(firstIndex);
1120 firstItem->setSelectable(false);
1121}