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

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

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2583 - (hide annotations) (download)
Fri May 30 21:03:25 2014 UTC (9 years, 10 months ago) by capela
File size: 8170 byte(s)
- Remove messages stdout/err capture redundant code.
1 capela 94 // qsamplerMessages.cpp
2     //
3     /****************************************************************************
4 capela 2582 Copyright (C) 2004-2014, rncbc aka Rui Nuno Capela. All rights reserved.
5 capela 1464 Copyright (C) 2007, Christian Schoenebeck
6 capela 94
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 capela 920 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 capela 94
21     *****************************************************************************/
22    
23 capela 1465 #include "qsamplerAbout.h"
24 capela 94 #include "qsamplerMessages.h"
25    
26 capela 1465 #include <QSocketNotifier>
27 capela 1738
28     #include <QFile>
29 capela 1465 #include <QTextEdit>
30     #include <QTextCursor>
31 capela 1738 #include <QTextStream>
32 capela 1465 #include <QTextBlock>
33 schoenebeck 1461 #include <QScrollBar>
34 capela 1465 #include <QDateTime>
35     #include <QIcon>
36 schoenebeck 1461
37 capela 115 #if !defined(WIN32)
38     #include <unistd.h>
39     #endif
40    
41 capela 1558
42     namespace QSampler {
43    
44 capela 94 // The default maximum number of message lines.
45     #define QSAMPLER_MESSAGES_MAXLINES 1000
46    
47     // Notification pipe descriptors
48     #define QSAMPLER_MESSAGES_FDNIL -1
49     #define QSAMPLER_MESSAGES_FDREAD 0
50     #define QSAMPLER_MESSAGES_FDWRITE 1
51    
52 capela 2582
53 capela 94 //-------------------------------------------------------------------------
54 capela 1558 // QSampler::Messages - Messages log dockable window.
55 capela 94 //
56    
57     // Constructor.
58 capela 1558 Messages::Messages ( QWidget *pParent )
59 capela 1739 : QDockWidget(pParent)
60 capela 94 {
61 capela 1465 // Surely a name is crucial (e.g.for storing geometry settings)
62     QDockWidget::setObjectName("qsamplerMessages");
63    
64 capela 1739 // Intialize stdout capture stuff.
65     m_pStdoutNotifier = NULL;
66     m_fdStdout[QSAMPLER_MESSAGES_FDREAD] = QSAMPLER_MESSAGES_FDNIL;
67     m_fdStdout[QSAMPLER_MESSAGES_FDWRITE] = QSAMPLER_MESSAGES_FDNIL;
68 capela 94
69 capela 1465 // Create local text view widget.
70 capela 1738 m_pMessagesTextView = new QTextEdit(this);
71     // QFont font(m_pMessagesTextView->font());
72 capela 94 // font.setFamily("Fixed");
73 capela 1738 // m_pMessagesTextView->setFont(font);
74     m_pMessagesTextView->setLineWrapMode(QTextEdit::NoWrap);
75     m_pMessagesTextView->setReadOnly(true);
76     m_pMessagesTextView->setUndoRedoEnabled(false);
77     // m_pMessagesTextView->setTextFormat(Qt::LogText);
78 capela 94
79 capela 1465 // Initialize default message limit.
80     m_iMessagesLines = 0;
81     setMessagesLimit(QSAMPLER_MESSAGES_MAXLINES);
82    
83 capela 1738 m_pMessagesLog = NULL;
84    
85 capela 1465 // Prepare the dockable window stuff.
86 capela 1738 QDockWidget::setWidget(m_pMessagesTextView);
87 capela 1465 QDockWidget::setFeatures(QDockWidget::AllDockWidgetFeatures);
88     QDockWidget::setAllowedAreas(
89     Qt::TopDockWidgetArea | Qt::BottomDockWidgetArea);
90 capela 772 // Some specialties to this kind of dock window...
91 capela 1465 QDockWidget::setMinimumHeight(120);
92 capela 94
93 capela 1465 // Finally set the default caption and tooltip.
94     const QString& sCaption = tr("Messages");
95     QDockWidget::setWindowTitle(sCaption);
96     // QDockWidget::setWindowIcon(QIcon(":/icons/qsamplerMessages.png"));
97     QDockWidget::setToolTip(sCaption);
98 capela 94 }
99    
100    
101     // Destructor.
102 capela 1558 Messages::~Messages (void)
103 capela 94 {
104 capela 1739 // Turn off and close logging.
105 capela 1738 setLogging(false);
106    
107 capela 1739 // No more notifications.
108     if (m_pStdoutNotifier)
109     delete m_pStdoutNotifier;
110 capela 94
111 capela 1739 // No need to delete child widgets, Qt does it all for us.
112 capela 94 }
113    
114    
115     // Own stdout/stderr socket notifier slot.
116 capela 1558 void Messages::stdoutNotify ( int fd )
117 capela 94 {
118     #if !defined(WIN32)
119 capela 1739 char achBuffer[1024];
120 capela 2582 const int cchBuffer = ::read(fd, achBuffer, sizeof(achBuffer) - 1);
121 capela 1739 if (cchBuffer > 0) {
122     achBuffer[cchBuffer] = (char) 0;
123     appendStdoutBuffer(achBuffer);
124     }
125 capela 94 #endif
126     }
127    
128    
129     // Stdout buffer handler -- now splitted by complete new-lines...
130 capela 1558 void Messages::appendStdoutBuffer ( const QString& s )
131 capela 94 {
132 capela 1465 m_sStdoutBuffer.append(s);
133 capela 94
134 capela 2582 const int iLength = m_sStdoutBuffer.lastIndexOf('\n');
135 capela 1465 if (iLength > 0) {
136 capela 2582 const QString& sTemp = m_sStdoutBuffer.left(iLength);
137 schoenebeck 1474 m_sStdoutBuffer.remove(0, iLength + 1);
138 capela 1465 QStringList list = sTemp.split('\n');
139     QStringListIterator iter(list);
140     while (iter.hasNext())
141     appendMessagesText(iter.next());
142     }
143 capela 94 }
144    
145    
146     // Stdout flusher -- show up any unfinished line...
147 capela 1558 void Messages::flushStdoutBuffer (void)
148 capela 94 {
149 capela 1739 if (!m_sStdoutBuffer.isEmpty()) {
150     appendMessagesText(m_sStdoutBuffer);
151     m_sStdoutBuffer.truncate(0);
152     }
153 capela 94 }
154    
155    
156     // Stdout capture accessors.
157 capela 1558 bool Messages::isCaptureEnabled (void)
158 capela 94 {
159 capela 2582 return (m_pStdoutNotifier != NULL);
160 capela 94 }
161    
162 capela 1558 void Messages::setCaptureEnabled ( bool bCapture )
163 capela 94 {
164 capela 1739 // Flush current buffer.
165     flushStdoutBuffer();
166 capela 94
167     #if !defined(WIN32)
168 capela 1465 // Destroy if already enabled.
169     if (!bCapture && m_pStdoutNotifier) {
170     delete m_pStdoutNotifier;
171     m_pStdoutNotifier = NULL;
172     // Close the notification pipes.
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 capela 94 #endif
189     }
190    
191    
192     // Message font accessors.
193 capela 1558 QFont Messages::messagesFont (void)
194 capela 94 {
195 capela 1739 return m_pMessagesTextView->font();
196 capela 94 }
197    
198 capela 1738 void Messages::setMessagesFont ( const QFont& font )
199 capela 94 {
200 capela 1739 m_pMessagesTextView->setFont(font);
201 capela 94 }
202    
203    
204     // Maximum number of message lines accessors.
205 capela 1558 int Messages::messagesLimit (void)
206 capela 94 {
207 capela 1739 return m_iMessagesLimit;
208 capela 94 }
209    
210 capela 1558 void Messages::setMessagesLimit ( int iMessagesLimit )
211 capela 94 {
212 capela 1739 m_iMessagesLimit = iMessagesLimit;
213     m_iMessagesHigh = iMessagesLimit + (iMessagesLimit / 3);
214 capela 94 }
215    
216 capela 1738 // Messages logging stuff.
217     bool Messages::isLogging (void) const
218     {
219     return (m_pMessagesLog != NULL);
220     }
221 capela 94
222 capela 1738 void Messages::setLogging ( bool bEnabled, const QString& sFilename )
223 capela 94 {
224 capela 1738 if (m_pMessagesLog) {
225     appendMessages(tr("Logging stopped --- %1 ---")
226     .arg(QDateTime::currentDateTime().toString()));
227     m_pMessagesLog->close();
228     delete m_pMessagesLog;
229     m_pMessagesLog = NULL;
230     }
231    
232     if (bEnabled) {
233     m_pMessagesLog = new QFile(sFilename);
234     if (m_pMessagesLog->open(QIODevice::Text | QIODevice::Append)) {
235     appendMessages(tr("Logging started --- %1 ---")
236     .arg(QDateTime::currentDateTime().toString()));
237     } else {
238     delete m_pMessagesLog;
239     m_pMessagesLog = NULL;
240     }
241     }
242 capela 94 }
243    
244 capela 1738
245     // Messages log output method.
246     void Messages::appendMessagesLog ( const QString& s )
247 capela 94 {
248 capela 1738 if (m_pMessagesLog) {
249     QTextStream(m_pMessagesLog) << s << endl;
250     m_pMessagesLog->flush();
251     }
252 capela 94 }
253    
254 capela 1738 // Messages widget output method.
255     void Messages::appendMessagesLine ( const QString& s )
256 capela 94 {
257 capela 1738 // Check for message line limit...
258     if (m_iMessagesLines > m_iMessagesHigh) {
259     m_pMessagesTextView->setUpdatesEnabled(false);
260     QTextCursor textCursor(m_pMessagesTextView->document()->begin());
261 capela 1465 while (m_iMessagesLines > m_iMessagesLimit) {
262     // Move cursor extending selection
263     // from start to next line-block...
264     textCursor.movePosition(
265     QTextCursor::NextBlock, QTextCursor::KeepAnchor);
266     m_iMessagesLines--;
267     }
268     // Remove the excessive line-blocks...
269     textCursor.removeSelectedText();
270 capela 1738 m_pMessagesTextView->setUpdatesEnabled(true);
271     }
272 capela 1465
273 capela 1738 m_pMessagesTextView->append(s);
274 capela 1465 m_iMessagesLines++;
275 capela 94 }
276    
277    
278 capela 1738 // The main utility methods.
279     void Messages::appendMessages ( const QString& s )
280     {
281 capela 1739 appendMessagesColor(s, "#999999");
282 capela 1738 }
283    
284     void Messages::appendMessagesColor ( const QString& s, const QString &c )
285     {
286 capela 2583 const QString& sText
287     = QTime::currentTime().toString("hh:mm:ss.zzz") + ' ' + s;
288 capela 1738 appendMessagesLine("<font color=\"" + c + "\">" + sText + "</font>");
289     appendMessagesLog(sText);
290     }
291    
292     void Messages::appendMessagesText ( const QString& s )
293     {
294     appendMessagesLine(s);
295     appendMessagesLog(s);
296     }
297    
298    
299 capela 1465 // History reset.
300 capela 1558 void Messages::clear (void)
301 capela 94 {
302 capela 1465 m_iMessagesLines = 0;
303 capela 1738 m_pMessagesTextView->clear();
304 capela 94 }
305    
306 capela 1558 } // namespace QSampler
307 capela 94
308 capela 1558
309 capela 94 // end of qsamplerMessages.cpp

  ViewVC Help
Powered by ViewVC