/[svn]/qsampler/trunk/src/qsamplerMessages.cpp
ViewVC logotype

Contents of /qsampler/trunk/src/qsamplerMessages.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1470 - (show annotations) (download)
Sun Nov 4 23:37:47 2007 UTC (16 years, 5 months ago) by schoenebeck
File size: 7420 byte(s)
* Qt4 migration: fixed ghost signal connections

1 // qsamplerMessages.cpp
2 //
3 /****************************************************************************
4 Copyright (C) 2004-2007, rncbc aka Rui Nuno Capela. All rights reserved.
5 Copyright (C) 2007, Christian Schoenebeck
6
7 This program is free software; you can redistribute it and/or
8 modify it under the terms of the GNU General Public License
9 as published by the Free Software Foundation; either version 2
10 of the License, or (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License along
18 with this program; if not, write to the Free Software Foundation, Inc.,
19 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20
21 *****************************************************************************/
22
23 #include "qsamplerAbout.h"
24 #include "qsamplerMessages.h"
25
26 #include <QSocketNotifier>
27 #include <QTextEdit>
28 #include <QTextCursor>
29 #include <QTextBlock>
30 #include <QScrollBar>
31 #include <QDateTime>
32 #include <QIcon>
33
34 #if !defined(WIN32)
35 #include <unistd.h>
36 #endif
37
38 // The default maximum number of message lines.
39 #define QSAMPLER_MESSAGES_MAXLINES 1000
40
41 // Notification pipe descriptors
42 #define QSAMPLER_MESSAGES_FDNIL -1
43 #define QSAMPLER_MESSAGES_FDREAD 0
44 #define QSAMPLER_MESSAGES_FDWRITE 1
45
46
47 //-------------------------------------------------------------------------
48 // qsamplerMessages - Messages log dockable window.
49 //
50
51 // Constructor.
52 qsamplerMessages::qsamplerMessages ( QWidget *pParent )
53 : QDockWidget(pParent)
54 {
55 // Surely a name is crucial (e.g.for storing geometry settings)
56 QDockWidget::setObjectName("qsamplerMessages");
57
58 // Intialize stdout capture stuff.
59 m_pStdoutNotifier = NULL;
60 m_fdStdout[QSAMPLER_MESSAGES_FDREAD] = QSAMPLER_MESSAGES_FDNIL;
61 m_fdStdout[QSAMPLER_MESSAGES_FDWRITE] = QSAMPLER_MESSAGES_FDNIL;
62
63 // Create local text view widget.
64 m_pTextView = new QTextEdit(this);
65 // QFont font(m_pTextView->font());
66 // font.setFamily("Fixed");
67 // m_pTextView->setFont(font);
68 m_pTextView->setLineWrapMode(QTextEdit::NoWrap);
69 m_pTextView->setReadOnly(true);
70 m_pTextView->setUndoRedoEnabled(false);
71 // m_pTextView->setTextFormat(Qt::LogText);
72
73 // Initialize default message limit.
74 m_iMessagesLines = 0;
75 setMessagesLimit(QSAMPLER_MESSAGES_MAXLINES);
76
77 // Prepare the dockable window stuff.
78 QDockWidget::setWidget(m_pTextView);
79 QDockWidget::setFeatures(QDockWidget::AllDockWidgetFeatures);
80 QDockWidget::setAllowedAreas(
81 Qt::TopDockWidgetArea | Qt::BottomDockWidgetArea);
82 // Some specialties to this kind of dock window...
83 QDockWidget::setMinimumHeight(120);
84
85 // Finally set the default caption and tooltip.
86 const QString& sCaption = tr("Messages");
87 QDockWidget::setWindowTitle(sCaption);
88 // QDockWidget::setWindowIcon(QIcon(":/icons/qsamplerMessages.png"));
89 QDockWidget::setToolTip(sCaption);
90 }
91
92
93 // Destructor.
94 qsamplerMessages::~qsamplerMessages (void)
95 {
96 // No more notifications.
97 if (m_pStdoutNotifier)
98 delete m_pStdoutNotifier;
99
100 // No need to delete child widgets, Qt does it all for us.
101 }
102
103
104 void qsamplerMessages::showEvent (QShowEvent* event)
105 {
106 QDockWidget::showEvent(event);
107 emit visibilityChanged(isVisible());
108 }
109
110
111 // Own stdout/stderr socket notifier slot.
112 void qsamplerMessages::stdoutNotify ( int fd )
113 {
114 #if !defined(WIN32)
115 char achBuffer[1024];
116 int cchBuffer = ::read(fd, achBuffer, sizeof(achBuffer) - 1);
117 if (cchBuffer > 0) {
118 achBuffer[cchBuffer] = (char) 0;
119 appendStdoutBuffer(achBuffer);
120 }
121 #endif
122 }
123
124
125 // Stdout buffer handler -- now splitted by complete new-lines...
126 void qsamplerMessages::appendStdoutBuffer ( const QString& s )
127 {
128 m_sStdoutBuffer.append(s);
129
130 int iLength = m_sStdoutBuffer.lastIndexOf('\n') + 1;
131 if (iLength > 0) {
132 QString sTemp = m_sStdoutBuffer.left(iLength);
133 m_sStdoutBuffer.remove(0, iLength);
134 QStringList list = sTemp.split('\n');
135 QStringListIterator iter(list);
136 while (iter.hasNext())
137 appendMessagesText(iter.next());
138 }
139 }
140
141
142 // Stdout flusher -- show up any unfinished line...
143 void qsamplerMessages::flushStdoutBuffer (void)
144 {
145 if (!m_sStdoutBuffer.isEmpty()) {
146 appendMessagesText(m_sStdoutBuffer);
147 m_sStdoutBuffer.truncate(0);
148 }
149 }
150
151
152 // Stdout capture accessors.
153 bool qsamplerMessages::isCaptureEnabled (void)
154 {
155 return (bool) (m_pStdoutNotifier != NULL);
156 }
157
158 void qsamplerMessages::setCaptureEnabled ( bool bCapture )
159 {
160 // Flush current buffer.
161 flushStdoutBuffer();
162
163 #if !defined(WIN32)
164 // Destroy if already enabled.
165 if (!bCapture && m_pStdoutNotifier) {
166 delete m_pStdoutNotifier;
167 m_pStdoutNotifier = NULL;
168 // Close the notification pipes.
169 if (m_fdStdout[QSAMPLER_MESSAGES_FDREAD] != QSAMPLER_MESSAGES_FDNIL) {
170 ::close(m_fdStdout[QSAMPLER_MESSAGES_FDREAD]);
171 m_fdStdout[QSAMPLER_MESSAGES_FDREAD] = QSAMPLER_MESSAGES_FDNIL;
172 }
173 if (m_fdStdout[QSAMPLER_MESSAGES_FDREAD] != QSAMPLER_MESSAGES_FDNIL) {
174 ::close(m_fdStdout[QSAMPLER_MESSAGES_FDREAD]);
175 m_fdStdout[QSAMPLER_MESSAGES_FDREAD] = QSAMPLER_MESSAGES_FDNIL;
176 }
177 }
178 // Are we going to make up the capture?
179 if (bCapture && m_pStdoutNotifier == NULL && ::pipe(m_fdStdout) == 0) {
180 ::dup2(m_fdStdout[QSAMPLER_MESSAGES_FDWRITE], STDOUT_FILENO);
181 ::dup2(m_fdStdout[QSAMPLER_MESSAGES_FDWRITE], STDERR_FILENO);
182 m_pStdoutNotifier = new QSocketNotifier(
183 m_fdStdout[QSAMPLER_MESSAGES_FDREAD], QSocketNotifier::Read, this);
184 QObject::connect(m_pStdoutNotifier,
185 SIGNAL(activated(int)),
186 SLOT(stdoutNotify(int)));
187 }
188 #endif
189 }
190
191
192 // Message font accessors.
193 QFont qsamplerMessages::messagesFont (void)
194 {
195 return m_pTextView->font();
196 }
197
198 void qsamplerMessages::setMessagesFont( const QFont& font )
199 {
200 m_pTextView->setFont(font);
201 }
202
203
204 // Maximum number of message lines accessors.
205 int qsamplerMessages::messagesLimit (void)
206 {
207 return m_iMessagesLimit;
208 }
209
210 void qsamplerMessages::setMessagesLimit ( int iMessagesLimit )
211 {
212 m_iMessagesLimit = iMessagesLimit;
213 m_iMessagesHigh = iMessagesLimit + (iMessagesLimit / 3);
214 }
215
216
217 // The main utility methods.
218 void qsamplerMessages::appendMessages ( const QString& s )
219 {
220 appendMessagesColor(s, "#999999");
221 }
222
223 void qsamplerMessages::appendMessagesColor ( const QString& s, const QString &c )
224 {
225 appendMessagesText("<font color=\"" + c + "\">"
226 + QTime::currentTime().toString("hh:mm:ss.zzz")
227 + ' ' + s + "</font>");
228 }
229
230 void qsamplerMessages::appendMessagesText ( const QString& s )
231 {
232 // Check for message line limit...
233 if (m_iMessagesLines > m_iMessagesHigh) {
234 m_pTextView->setUpdatesEnabled(false);
235 QTextCursor textCursor(m_pTextView->document()->begin());
236 while (m_iMessagesLines > m_iMessagesLimit) {
237 // Move cursor extending selection
238 // from start to next line-block...
239 textCursor.movePosition(
240 QTextCursor::NextBlock, QTextCursor::KeepAnchor);
241 m_iMessagesLines--;
242 }
243 // Remove the excessive line-blocks...
244 textCursor.removeSelectedText();
245 m_pTextView->setUpdatesEnabled(true);
246 }
247
248 // Count always as a new line out there...
249 m_pTextView->append(s);
250 m_iMessagesLines++;
251 }
252
253
254 // History reset.
255 void qsamplerMessages::clear (void)
256 {
257 m_iMessagesLines = 0;
258 m_pTextView->clear();
259 }
260
261
262 // end of qsamplerMessages.cpp

  ViewVC Help
Powered by ViewVC