VirtualBox

source: vbox/trunk/src/VBox/Frontends/VirtualBox/ui/VBoxVMLogViewer.ui.h@ 3123

Last change on this file since 3123 was 3018, checked in by vboxsync, 17 years ago

1952: Easy way to store the RELEASE log using the GUI:

Last access Date/Time of the log file used for default new file name during saving.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Date Revision Author Id
File size: 11.2 KB
Line 
1/**
2 *
3 * VBox frontends: Qt GUI ("VirtualBox"):
4 * "Virtual Log Viewer" dialog UI include (Qt Designer)
5 */
6
7/*
8 * Copyright (C) 2006 innotek GmbH
9 *
10 * This file is part of VirtualBox Open Source Edition (OSE), as
11 * available from http://www.virtualbox.org. This file is free software;
12 * you can redistribute it and/or modify it under the terms of the GNU
13 * General Public License as published by the Free Software Foundation,
14 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
15 * distribution. VirtualBox OSE is distributed in the hope that it will
16 * be useful, but WITHOUT ANY WARRANTY of any kind.
17 *
18 * If you received this file as part of a commercial VirtualBox
19 * distribution, then only the terms of your commercial VirtualBox
20 * license agreement apply instead of the previous paragraph.
21 */
22
23/****************************************************************************
24** ui.h extension file, included from the uic-generated form implementation.
25**
26** If you wish to add, delete or rename functions or slots use
27** Qt Designer which will update this file, preserving your code. Create an
28** init() function in place of a constructor, and a destroy() function in
29** place of a destructor.
30*****************************************************************************/
31
32
33VBoxVMLogViewer::LogViewersMap VBoxVMLogViewer::mSelfArray = LogViewersMap();
34
35void VBoxVMLogViewer::createLogViewer (CMachine &aMachine)
36{
37 if (mSelfArray.find (aMachine.GetName()) == mSelfArray.end())
38 {
39 /* creating new log viewer if there is no one existing */
40 mSelfArray [aMachine.GetName()] = new VBoxVMLogViewer (0,
41 "VBoxVMLogViewer", WType_TopLevel | WDestructiveClose);
42 /* read new machine data for this log viewer */
43 mSelfArray [aMachine.GetName()]->setup (aMachine);
44 }
45
46 VBoxVMLogViewer *viewer = mSelfArray [aMachine.GetName()];
47 viewer->show();
48 viewer->setWindowState (viewer->windowState() & ~WindowMinimized);
49 viewer->setActiveWindow();
50}
51
52
53void VBoxVMLogViewer::init()
54{
55 /* prepare dialog to first run */
56 mFirstRun = true;
57
58 /* dialog initially is not polished */
59 mIsPolished = false;
60
61 /* search the default button */
62 mDefaultButton = searchDefaultButton();
63 qApp->installEventFilter (this);
64
65 /* setup a dialog icon */
66 setIcon (QPixmap::fromMimeSource ("show_logs_16px.png"));
67
68 /* statusbar initially disabled */
69 statusBar()->setHidden (true);
70
71 /* setup size grip */
72 mSizeGrip = new QSizeGrip (centralWidget(), "mSizeGrip");
73 mSizeGrip->resize (mSizeGrip->sizeHint());
74 mSizeGrip->stackUnder (mCloseButton);
75
76 /* logs list creation */
77 mLogList = new QTabWidget (mLogsFrame, "mLogList");
78 QVBoxLayout *logsFrameLayout = new QVBoxLayout (mLogsFrame);
79 logsFrameLayout->addWidget (mLogList);
80
81 /* applying language settings */
82 languageChangeImp();
83}
84
85
86void VBoxVMLogViewer::destroy()
87{
88 mSelfArray.erase (mMachine.GetName());
89}
90
91
92void VBoxVMLogViewer::setup (CMachine &aMachine)
93{
94 /* saving related machine */
95 mMachine = aMachine;
96
97 /* reading log files */
98 refresh();
99
100 /* loading language constants */
101 languageChangeImp();
102}
103
104
105const CMachine& VBoxVMLogViewer::machine()
106{
107 return mMachine;
108}
109
110
111void VBoxVMLogViewer::languageChangeImp()
112{
113 /* setup a dialog caption */
114 if (!mMachine.isNull())
115 setCaption (tr ("%1 - VirtualBox Log Viewer").arg (mMachine.GetName()));
116}
117
118
119QPushButton* VBoxVMLogViewer::searchDefaultButton()
120{
121 /* this mechanism is used for searching the default dialog button
122 * and similar the same mechanism in Qt::QDialog inner source */
123 QPushButton *button = 0;
124 QObjectList *list = queryList ("QPushButton");
125 QObjectListIt it (*list);
126 while ((button = (QPushButton*)it.current()) && !button->isDefault())
127 ++ it;
128 return button;
129}
130
131
132bool VBoxVMLogViewer::eventFilter (QObject *aObject, QEvent *aEvent)
133{
134 switch (aEvent->type())
135 {
136 /* auto-default button focus-in processor used to move the "default"
137 * button property into the currently focused button */
138 case QEvent::FocusIn:
139 {
140 if (aObject->inherits ("QPushButton") &&
141 aObject->parent() == centralWidget())
142 {
143 ((QPushButton*)aObject)->setDefault (aObject != mDefaultButton);
144 if (mDefaultButton)
145 mDefaultButton->setDefault (aObject == mDefaultButton);
146 }
147 break;
148 }
149 /* auto-default button focus-out processor used to remove the "default"
150 * button property from the previously focused button */
151 case QEvent::FocusOut:
152 {
153 if (aObject->inherits ("QPushButton") &&
154 aObject->parent() == centralWidget())
155 {
156 if (mDefaultButton)
157 mDefaultButton->setDefault (aObject != mDefaultButton);
158 ((QPushButton*)aObject)->setDefault (aObject == mDefaultButton);
159 }
160 break;
161 }
162 default:
163 break;
164 }
165 return QMainWindow::eventFilter (aObject, aEvent);
166}
167
168
169bool VBoxVMLogViewer::event (QEvent *aEvent)
170{
171 bool result = QMainWindow::event (aEvent);
172 switch (aEvent->type())
173 {
174 case QEvent::LanguageChange:
175 {
176 languageChangeImp();
177 break;
178 }
179 default:
180 break;
181 }
182 return result;
183}
184
185
186void VBoxVMLogViewer::keyPressEvent (QKeyEvent *aEvent)
187{
188 if (aEvent->state() == 0 ||
189 (aEvent->state() & Keypad && aEvent->key() == Key_Enter))
190 {
191 switch (aEvent->key())
192 {
193 /* processing the return keypress for the auto-default button */
194 case Key_Enter:
195 case Key_Return:
196 {
197 QPushButton *currentDefault = searchDefaultButton();
198 if (currentDefault)
199 currentDefault->animateClick();
200 break;
201 }
202 /* processing the escape keypress as the close dialog action */
203 case Key_Escape:
204 {
205 close();
206 break;
207 }
208 }
209 }
210 else
211 aEvent->ignore();
212}
213
214
215void VBoxVMLogViewer::showEvent (QShowEvent *aEvent)
216{
217 QMainWindow::showEvent (aEvent);
218
219 /* one may think that QWidget::polish() is the right place to do things
220 * below, but apparently, by the time when QWidget::polish() is called,
221 * the widget style & layout are not fully done, at least the minimum
222 * size hint is not properly calculated. Since this is sometimes necessary,
223 * we provide our own "polish" implementation. */
224
225 if (mIsPolished)
226 return;
227
228 mIsPolished = true;
229
230 VBoxGlobal::centerWidget (this, parentWidget());
231}
232
233
234void VBoxVMLogViewer::resizeEvent (QResizeEvent*)
235{
236 /* adjust the size-grip location for the current resize event */
237 mSizeGrip->move (centralWidget()->rect().bottomRight() -
238 QPoint (mSizeGrip->rect().width() - 1,
239 mSizeGrip->rect().height() - 1));
240}
241
242
243void VBoxVMLogViewer::refresh()
244{
245 /* clearing old data if any */
246 mLogFilesList.clear();
247 while (mLogList->count())
248 {
249 QWidget *logPage = mLogList->page (0);
250 mLogList->removePage (logPage);
251 delete logPage;
252 }
253
254 bool isAnyLogPresent = false;
255
256 /* entering log files folder */
257 QString logFilesPath = mMachine.GetLogFolder();
258 QDir logFilesDir (logFilesPath);
259 if (logFilesDir.exists())
260 {
261 /* reading log files folder */
262 QStringList logList = logFilesDir.entryList (QDir::Files);
263 if (!logList.empty()) isAnyLogPresent = true;
264 for (QStringList::Iterator it = logList.begin(); it != logList.end(); ++it)
265 loadLogFile (logFilesDir.filePath (*it));
266 }
267
268 /* create an empty log page if there are no logs at all */
269 if (!isAnyLogPresent)
270 {
271 QTextBrowser *dummyLog = createLogPage ("VBox.log");
272 dummyLog->setTextFormat (Qt::RichText);
273 dummyLog->setWordWrap (QTextEdit::WidgetWidth);
274 dummyLog->setText (tr ("<p>No log files found. Press the <b>Refresh</b> "
275 "button to rescan the log folder <nobr><b>%1</b></nobr>.</p>")
276 .arg (logFilesPath));
277 /* we don't want it to remain white */
278 dummyLog->setPaper (backgroundBrush());
279 }
280
281 /* restore previous tab-widget margin which was reseted when
282 * the tab widget's children was removed */
283 mLogList->setMargin (10);
284
285 /* show the first tab widget's page after the refresh */
286 mLogList->showPage (mLogList->page(0));
287
288 /* enable/disable save button & tab widget according log presence */
289 mSaveButton->setEnabled (isAnyLogPresent);
290 mLogList->setEnabled (isAnyLogPresent);
291
292 if (mFirstRun)
293 {
294 /* resize the whole log-viewer to fit 80 symbols in text-browser for
295 * the first time started */
296 QTextBrowser *firstPage = static_cast <QTextBrowser *> (mLogList->page(0));
297 int fullWidth = firstPage->fontMetrics().width (QChar ('x')) * 80 +
298 firstPage->verticalScrollBar()->width() +
299 firstPage->frameWidth() * 2 +
300 5 + 4 /* left text margin + QTabWidget frame width */ +
301 mLogList->margin() * 2 +
302 centralWidget()->layout()->margin() * 2;
303 resize (fullWidth, height());
304 mFirstRun = false;
305 }
306}
307
308
309void VBoxVMLogViewer::loadLogFile (const QString &aFileName)
310{
311 /* prepare log file */
312 QFile logFile (aFileName);
313 if (!logFile.exists() || !logFile.open (IO_ReadOnly))
314 return;
315
316 /* read log file and write it into the log page */
317 QTextBrowser *logViewer = createLogPage (QFileInfo (aFileName).fileName());
318 logViewer->setText (logFile.readAll());
319
320 mLogFilesList << aFileName;
321}
322
323
324QTextBrowser* VBoxVMLogViewer::createLogPage (const QString &aName)
325{
326 QTextBrowser *logViewer = new QTextBrowser();
327 logViewer->setTextFormat (Qt::PlainText);
328 QFont font = logViewer->currentFont();
329 font.setFamily ("Courier New,courier");
330 logViewer->setFont (font);
331 logViewer->setWordWrap (QTextEdit::NoWrap);
332 logViewer->setVScrollBarMode (QScrollView::AlwaysOn);
333 mLogList->addTab (logViewer, aName);
334 return logViewer;
335}
336
337
338void VBoxVMLogViewer::save()
339{
340 /* prepare "save as" dialog */
341 QFileInfo fileInfo (mLogFilesList [mLogList->currentPageIndex()]);
342 QDateTime dtInfo = fileInfo.lastModified();
343 QString dtString = dtInfo.toString ("yyyy-MM-dd-hh-mm-ss");
344 QString defaultFileName = QString ("%1-%2.log")
345 .arg (mMachine.GetName()).arg (dtString);
346 QString defaultFullName = QDir::convertSeparators (QDir::home().absPath() +
347 "/" + defaultFileName);
348
349 QString newFileName = QFileDialog::getSaveFileName (defaultFullName,
350 QString::null, this, "SaveLogAsDialog", tr ("Save VirtualBox Log As"));
351
352 /* save new log into the file */
353 if (!newFileName.isEmpty())
354 {
355 /* reread log data */
356 QFile oldFile (mLogFilesList [mLogList->currentPageIndex()]);
357 QFile newFile (newFileName);
358 if (!oldFile.open (IO_ReadOnly) || !newFile.open (IO_WriteOnly))
359 return;
360
361 /* save log data into the new file */
362 newFile.writeBlock (oldFile.readAll());
363 }
364}
365
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette