Extract portWidget from streamsWidget

This commit is contained in:
Srivats P 2021-11-06 14:21:40 +05:30
parent 295fc93e7b
commit 14993073fe
9 changed files with 78 additions and 688 deletions

View File

@ -57,6 +57,7 @@ HEADERS += \
portstatsproxymodel.h \ portstatsproxymodel.h \
portstatswindow.h \ portstatswindow.h \
portswindow.h \ portswindow.h \
portwidget.h \
preferences.h \ preferences.h \
settings.h \ settings.h \
streamconfigdialog.h \ streamconfigdialog.h \
@ -79,6 +80,7 @@ FORMS += \
portstatsfilter.ui \ portstatsfilter.ui \
portstatswindow.ui \ portstatswindow.ui \
portswindow.ui \ portswindow.ui \
portwidget.ui \
preferences.ui \ preferences.ui \
streamconfigdialog.ui \ streamconfigdialog.ui \
streamstatswindow.ui \ streamstatswindow.ui \
@ -111,6 +113,7 @@ SOURCES += \
portstatsfilterdialog.cpp \ portstatsfilterdialog.cpp \
portstatswindow.cpp \ portstatswindow.cpp \
portswindow.cpp \ portswindow.cpp \
portwidget.cpp \
preferences.cpp \ preferences.cpp \
streamconfigdialog.cpp \ streamconfigdialog.cpp \
streamlistdelegate.cpp \ streamlistdelegate.cpp \

View File

@ -24,6 +24,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#include "fileformat.pb.h" #include "fileformat.pb.h"
#include "portconfigdialog.h" #include "portconfigdialog.h"
#include "portgrouplist.h" #include "portgrouplist.h"
#include "portwidget.h"
#include "settings.h" #include "settings.h"
#include "streamswidget.h" #include "streamswidget.h"
@ -44,6 +45,7 @@ PortsWindow::PortsWindow(PortGroupList *pgl, QWidget *parent)
setupUi(this); setupUi(this);
applyMsg_ = new ApplyMessage(); applyMsg_ = new ApplyMessage();
portWidget->setPortGroupList(plm);
streamsWidget->setPortGroupList(plm); streamsWidget->setPortGroupList(plm);
devicesWidget->setPortGroupList(plm); devicesWidget->setPortGroupList(plm);
@ -99,6 +101,10 @@ PortsWindow::PortsWindow(PortGroupList *pgl, QWidget *parent)
SIGNAL(currentChanged(const QModelIndex&, const QModelIndex&)), SIGNAL(currentChanged(const QModelIndex&, const QModelIndex&)),
this, SLOT(when_portView_currentChanged(const QModelIndex&, this, SLOT(when_portView_currentChanged(const QModelIndex&,
const QModelIndex&))); const QModelIndex&)));
connect(this,
SIGNAL(currentPortChanged(const QModelIndex&, const QModelIndex&)),
portWidget, SLOT(setCurrentPortIndex(const QModelIndex&)));
connect(this, connect(this,
SIGNAL(currentPortChanged(const QModelIndex&, const QModelIndex&)), SIGNAL(currentPortChanged(const QModelIndex&, const QModelIndex&)),
streamsWidget, SLOT(setCurrentPortIndex(const QModelIndex&))); streamsWidget, SLOT(setCurrentPortIndex(const QModelIndex&)));

View File

@ -212,6 +212,9 @@
<string>Streams</string> <string>Streams</string>
</attribute> </attribute>
<layout class="QVBoxLayout"> <layout class="QVBoxLayout">
<item>
<widget class="PortWidget" name="portWidget" native="true"/>
</item>
<item> <item>
<widget class="StreamsWidget" name="streamsWidget" native="true"/> <widget class="StreamsWidget" name="streamsWidget" native="true"/>
</item> </item>
@ -303,6 +306,12 @@
<header>streamswidget.h</header> <header>streamswidget.h</header>
<container>1</container> <container>1</container>
</customwidget> </customwidget>
<customwidget>
<class>PortWidget</class>
<extends>QWidget</extends>
<header>portwidget.h</header>
<container>1</container>
</customwidget>
</customwidgets> </customwidgets>
<resources> <resources>
<include location="ostinato.qrc"/> <include location="ostinato.qrc"/>

View File

@ -17,122 +17,36 @@ You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/> along with this program. If not, see <http://www.gnu.org/licenses/>
*/ */
#include "streamswidget.h" #include "portwidget.h"
#include "clipboardhelper.h"
#include "portgrouplist.h" #include "portgrouplist.h"
#include "streamconfigdialog.h"
#include "streamfileformat.h"
#include "streamlistdelegate.h"
#include "xqlocale.h" #include "xqlocale.h"
#include <QInputDialog> PortWidget::PortWidget(QWidget *parent)
#include <QItemSelectionModel>
#include <QMessageBox>
extern ClipboardHelper *clipboardHelper;
StreamsWidget::StreamsWidget(QWidget *parent)
: QWidget(parent) : QWidget(parent)
{ {
setupUi(this); setupUi(this);
delegate = new StreamListDelegate;
tvStreamList->setItemDelegate(delegate);
tvStreamList->verticalHeader()->setDefaultSectionSize(
tvStreamList->verticalHeader()->minimumSectionSize());
// Populate StreamList Context Menu Actions
tvStreamList->addAction(actionNew_Stream);
tvStreamList->addAction(actionEdit_Stream);
tvStreamList->addAction(actionDuplicate_Stream);
tvStreamList->addAction(actionDelete_Stream);
QAction *sep2 = new QAction(this);
sep2->setSeparator(true);
tvStreamList->addAction(sep2);
tvStreamList->addAction(actionOpen_Streams);
tvStreamList->addAction(actionSave_Streams);
// StreamWidget's actions is an aggegate of all sub-widget's actions
addActions(tvStreamList->actions());
// Add the clipboard actions to the context menu of streamList
// but not to StreamsWidget's actions since they are already available
// in the global Edit Menu
QAction *sep3 = new QAction("Clipboard", this);
sep3->setSeparator(true);
tvStreamList->insertAction(sep2, sep3);
tvStreamList->insertActions(sep2, clipboardHelper->actions());
} }
void StreamsWidget::setPortGroupList(PortGroupList *portGroups) void PortWidget::setPortGroupList(PortGroupList *portGroups)
{ {
plm = portGroups; plm = portGroups;
tvStreamList->setModel(plm->getStreamModel());
connect(plm->getStreamModel(), SIGNAL(rowsInserted(QModelIndex, int, int)), connect(plm->getStreamModel(), SIGNAL(rowsInserted(QModelIndex, int, int)),
SLOT(updateStreamViewActions())); SLOT(updatePortActions()));
connect(plm->getStreamModel(), SIGNAL(rowsRemoved(QModelIndex, int, int)), connect(plm->getStreamModel(), SIGNAL(rowsRemoved(QModelIndex, int, int)),
SLOT(updateStreamViewActions())); SLOT(updatePortActions()));
connect(plm->getStreamModel(), SIGNAL(modelReset()),
SLOT(updatePortActions()));
connect(tvStreamList->selectionModel(), updatePortActions();
SIGNAL(currentChanged(const QModelIndex&, const QModelIndex&)),
SLOT(updateStreamViewActions()));
connect(tvStreamList->selectionModel(),
SIGNAL(selectionChanged(const QItemSelection&, const QItemSelection&)),
SLOT(updateStreamViewActions()));
tvStreamList->resizeColumnToContents(StreamModel::StreamIcon);
tvStreamList->resizeColumnToContents(StreamModel::StreamStatus);
updateStreamViewActions();
connect(plm->getStreamModel(),
SIGNAL(dataChanged(const QModelIndex&, const QModelIndex&)),
this, SLOT(streamModelDataChanged()));
connect(plm->getStreamModel(),
SIGNAL(modelReset()),
this, SLOT(streamModelDataChanged()));
} }
void StreamsWidget::streamModelDataChanged() PortWidget::~PortWidget()
{ {
if (plm->isPort(currentPortIndex_))
plm->port(currentPortIndex_).recalculateAverageRates();
} }
StreamsWidget::~StreamsWidget() void PortWidget::setCurrentPortIndex(const QModelIndex &portIndex)
{
delete delegate;
}
void StreamsWidget::on_tvStreamList_activated(const QModelIndex & index)
{
if (!index.isValid())
{
qDebug("%s: invalid index", __FUNCTION__);
return;
}
qDebug("stream list activated\n");
Port &curPort = plm->port(currentPortIndex_);
QList<Stream*> streams;
streams.append(curPort.mutableStreamByIndex(index.row(), false));
StreamConfigDialog scd(streams, curPort, this);
if (scd.exec() == QDialog::Accepted) {
curPort.recalculateAverageRates();
curPort.setLocalConfigChanged(true);
}
}
void StreamsWidget::setCurrentPortIndex(const QModelIndex &portIndex)
{ {
if (!plm) if (!plm)
return; return;
@ -150,18 +64,18 @@ void StreamsWidget::setCurrentPortIndex(const QModelIndex &portIndex)
this, SLOT(updatePortRates())); this, SLOT(updatePortRates()));
currentPortIndex_ = portIndex; currentPortIndex_ = portIndex;
plm->getStreamModel()->setCurrentPortIndex(portIndex);
// Connect current port // Connect current port
if (plm->isPort(currentPortIndex_)) if (plm->isPort(currentPortIndex_))
connect(&(plm->port(currentPortIndex_)), connect(&(plm->port(currentPortIndex_)),
SIGNAL(portRateChanged(int, int)), SIGNAL(portRateChanged(int, int)),
this, SLOT(updatePortRates())); this, SLOT(updatePortRates()));
updatePortRates(); updatePortRates();
updateStreamViewActions(); updatePortActions();
} }
void StreamsWidget::on_startTx_clicked() void PortWidget::on_startTx_clicked()
{ {
Q_ASSERT(plm->isPort(currentPortIndex_)); Q_ASSERT(plm->isPort(currentPortIndex_));
@ -173,7 +87,7 @@ void StreamsWidget::on_startTx_clicked()
plm->portGroup(curPortGroup).startTx(&portList); plm->portGroup(curPortGroup).startTx(&portList);
} }
void StreamsWidget::on_stopTx_clicked() void PortWidget::on_stopTx_clicked()
{ {
Q_ASSERT(plm->isPort(currentPortIndex_)); Q_ASSERT(plm->isPort(currentPortIndex_));
@ -185,7 +99,7 @@ void StreamsWidget::on_stopTx_clicked()
plm->portGroup(curPortGroup).stopTx(&portList); plm->portGroup(curPortGroup).stopTx(&portList);
} }
void StreamsWidget::on_averagePacketsPerSec_editingFinished() void PortWidget::on_averagePacketsPerSec_editingFinished()
{ {
Q_ASSERT(plm->isPort(currentPortIndex_)); Q_ASSERT(plm->isPort(currentPortIndex_));
@ -195,7 +109,7 @@ void StreamsWidget::on_averagePacketsPerSec_editingFinished()
plm->port(currentPortIndex_).setAveragePacketRate(pps); plm->port(currentPortIndex_).setAveragePacketRate(pps);
} }
void StreamsWidget::on_averageBitsPerSec_editingFinished() void PortWidget::on_averageBitsPerSec_editingFinished()
{ {
Q_ASSERT(plm->isPort(currentPortIndex_)); Q_ASSERT(plm->isPort(currentPortIndex_));
@ -205,7 +119,7 @@ void StreamsWidget::on_averageBitsPerSec_editingFinished()
plm->port(currentPortIndex_).setAverageBitRate(bps); plm->port(currentPortIndex_).setAverageBitRate(bps);
} }
void StreamsWidget::updatePortRates() void PortWidget::updatePortRates()
{ {
if (!currentPortIndex_.isValid()) if (!currentPortIndex_.isValid())
return; return;
@ -219,287 +133,11 @@ void StreamsWidget::updatePortRates()
.arg(plm->port(currentPortIndex_).averageBitRate(), 0, 'f', 0)); .arg(plm->port(currentPortIndex_).averageBitRate(), 0, 'f', 0));
} }
void StreamsWidget::updateStreamViewActions() void PortWidget::updatePortActions()
{ {
// For some reason hasSelection() returns true even if selection size is 0 if (!plm->isPort(currentPortIndex_))
// so additional check for size introduced
if (tvStreamList->selectionModel()->hasSelection() &&
(tvStreamList->selectionModel()->selection().size() > 0))
{
qDebug("Has selection %d",
tvStreamList->selectionModel()->selection().size());
// If more than one non-contiguous ranges selected,
// disable "New" and "Edit"
if (tvStreamList->selectionModel()->selection().size() > 1)
{
actionNew_Stream->setDisabled(true);
actionEdit_Stream->setDisabled(true);
}
else
{
actionNew_Stream->setEnabled(true);
actionEdit_Stream->setEnabled(true);
}
// Duplicate/Delete are always enabled as long as we have a selection
actionDuplicate_Stream->setEnabled(true);
actionDelete_Stream->setEnabled(true);
}
else
{
qDebug("No selection");
if (plm->isPort(currentPortIndex_))
actionNew_Stream->setEnabled(true);
else
actionNew_Stream->setDisabled(true);
actionEdit_Stream->setDisabled(true);
actionDuplicate_Stream->setDisabled(true);
actionDelete_Stream->setDisabled(true);
}
actionOpen_Streams->setEnabled(plm->isPort(currentPortIndex_));
actionSave_Streams->setEnabled(tvStreamList->model()->rowCount() > 0);
startTx->setEnabled(tvStreamList->model()->rowCount() > 0);
stopTx->setEnabled(tvStreamList->model()->rowCount() > 0);
}
void StreamsWidget::on_actionNew_Stream_triggered()
{
qDebug("New Stream Action");
QItemSelectionModel* selectionModel = tvStreamList->selectionModel();
if (selectionModel->selection().size() > 1) {
qDebug("%s: Unexpected selection size %d, can't add", __FUNCTION__,
selectionModel->selection().size());
return;
}
// In case nothing is selected, insert 1 row at the end
StreamModel *streamModel = plm->getStreamModel();
int row = streamModel->rowCount(), count = 1;
// In case we have a single range selected; insert as many rows as
// in the singe selected range before the top of the selected range
if (selectionModel->selection().size() == 1)
{
row = selectionModel->selection().at(0).top();
count = selectionModel->selection().at(0).height();
}
Port &curPort = plm->port(currentPortIndex_);
QList<Stream*> streams;
for (int i = 0; i < count; i++)
streams.append(new Stream);
StreamConfigDialog scd(streams, curPort, this);
scd.setWindowTitle(tr("Add Stream"));
if (scd.exec() == QDialog::Accepted)
streamModel->insert(row, streams);
}
void StreamsWidget::on_actionEdit_Stream_triggered()
{
qDebug("Edit Stream Action");
QItemSelectionModel* streamModel = tvStreamList->selectionModel();
if (!streamModel->hasSelection())
return; return;
Port &curPort = plm->port(currentPortIndex_); startTx->setEnabled(plm->port(currentPortIndex_).numStreams() > 0);
stopTx->setEnabled(plm->port(currentPortIndex_).numStreams() > 0);
QList<Stream*> streams;
foreach(QModelIndex index, streamModel->selectedRows())
streams.append(curPort.mutableStreamByIndex(index.row(), false));
StreamConfigDialog scd(streams, curPort, this);
if (scd.exec() == QDialog::Accepted) {
curPort.recalculateAverageRates();
curPort.setLocalConfigChanged(true);
}
} }
void StreamsWidget::on_actionDuplicate_Stream_triggered()
{
QItemSelectionModel* model = tvStreamList->selectionModel();
qDebug("Duplicate Stream Action");
if (model->hasSelection())
{
bool isOk;
int count = QInputDialog::getInt(this, "Duplicate Streams",
"Count", 1, 1, 9999, 1, &isOk);
if (!isOk)
return;
QList<int> list;
foreach(QModelIndex index, model->selectedRows())
list.append(index.row());
plm->port(currentPortIndex_).duplicateStreams(list, count);
}
else
qDebug("No selection");
}
void StreamsWidget::on_actionDelete_Stream_triggered()
{
qDebug("Delete Stream Action");
QModelIndex index;
if (tvStreamList->selectionModel()->hasSelection())
{
qDebug("SelectedIndexes %d",
tvStreamList->selectionModel()->selectedRows().size());
while(tvStreamList->selectionModel()->selectedRows().size())
{
index = tvStreamList->selectionModel()->selectedRows().at(0);
plm->getStreamModel()->removeRows(index.row(), 1);
}
}
else
qDebug("No selection");
}
void StreamsWidget::on_actionOpen_Streams_triggered()
{
qDebug("Open Streams Action");
QStringList fileTypes = StreamFileFormat::supportedFileTypes(
StreamFileFormat::kOpenFile);
QString fileType;
static QString dirName;
QString fileName;
QString errorStr;
bool append = true;
bool ret;
Q_ASSERT(plm->isPort(currentPortIndex_));
if (fileTypes.size())
fileType = fileTypes.at(0);
fileName = QFileDialog::getOpenFileName(this, tr("Open Streams"),
dirName, fileTypes.join(";;"), &fileType);
if (fileName.isEmpty())
goto _exit;
if (tvStreamList->model()->rowCount())
{
QMessageBox msgBox(QMessageBox::Question, qApp->applicationName(),
tr("Append to existing streams? Or overwrite?"),
QMessageBox::NoButton, this);
QPushButton *appendBtn = msgBox.addButton(tr("Append"),
QMessageBox::ActionRole);
QPushButton *overwriteBtn = msgBox.addButton(tr("Overwrite"),
QMessageBox::ActionRole);
QPushButton *cancelBtn = msgBox.addButton(QMessageBox::Cancel);
msgBox.exec();
if (msgBox.clickedButton() == cancelBtn)
goto _exit;
else if (msgBox.clickedButton() == appendBtn)
append = true;
else if (msgBox.clickedButton() == overwriteBtn)
append = false;
else
Q_ASSERT(false);
}
ret = plm->port(currentPortIndex_).openStreams(fileName, append, errorStr);
if (!ret || !errorStr.isEmpty())
{
QMessageBox msgBox(this);
QStringList str = errorStr.split("\n\n\n\n");
msgBox.setIcon(ret ? QMessageBox::Warning : QMessageBox::Critical);
msgBox.setWindowTitle(qApp->applicationName());
msgBox.setText(str.at(0));
if (str.size() > 1)
msgBox.setDetailedText(str.at(1));
msgBox.setStandardButtons(QMessageBox::Ok);
msgBox.exec();
}
dirName = QFileInfo(fileName).absolutePath();
updateStreamViewActions();
_exit:
return;
}
void StreamsWidget::on_actionSave_Streams_triggered()
{
qDebug("Save Streams Action");
static QString fileName;
QStringList fileTypes = StreamFileFormat::supportedFileTypes(
StreamFileFormat::kSaveFile);
QString fileType;
QString errorStr;
QFileDialog::Options options;
// On Mac OS with Native Dialog, getSaveFileName() ignores fileType
// which we need
#if defined(Q_OS_MAC)
options |= QFileDialog::DontUseNativeDialog;
#endif
if (fileTypes.size())
fileType = fileTypes.at(0);
Q_ASSERT(plm->isPort(currentPortIndex_));
_retry:
fileName = QFileDialog::getSaveFileName(this, tr("Save Streams"),
fileName, fileTypes.join(";;"), &fileType, options);
if (fileName.isEmpty())
goto _exit;
if (QFileInfo(fileName).suffix().isEmpty()) {
QString fileExt = fileType.section(QRegExp("[\\*\\)]"), 1, 1);
qDebug("Adding extension '%s' to '%s'",
qPrintable(fileExt), qPrintable(fileName));
fileName.append(fileExt);
if (QFileInfo(fileName).exists()) {
if (QMessageBox::warning(this, tr("Overwrite File?"),
QString("The file \"%1\" already exists.\n\n"
"Do you wish to overwrite it?")
.arg(QFileInfo(fileName).fileName()),
QMessageBox::Yes|QMessageBox::No,
QMessageBox::No) != QMessageBox::Yes)
goto _retry;
}
}
fileType = fileType.remove(QRegExp("\\(.*\\)")).trimmed();
if (!fileType.startsWith("Ostinato")
&& !fileType.startsWith("Python"))
{
if (QMessageBox::warning(this, tr("Ostinato"),
QString("You have chosen to save in %1 format. All stream "
"attributes may not be saved in this format.\n\n"
"It is recommended to save in native Ostinato format.\n\n"
"Continue to save in %2 format?").arg(fileType).arg(fileType),
QMessageBox::Yes|QMessageBox::No,
QMessageBox::No) != QMessageBox::Yes)
goto _retry;
}
// TODO: all or selected?
if (!plm->port(currentPortIndex_).saveStreams(fileName, fileType, errorStr))
QMessageBox::critical(this, qApp->applicationName(), errorStr);
else if (!errorStr.isEmpty())
QMessageBox::warning(this, qApp->applicationName(), errorStr);
fileName = QFileInfo(fileName).absolutePath();
_exit:
return;
}

View File

@ -17,23 +17,21 @@ You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/> along with this program. If not, see <http://www.gnu.org/licenses/>
*/ */
#ifndef _STREAMS_WIDGET_H #ifndef _PORT_WIDGET_H
#define _STREAMS_WIDGET_H #define _PORT_WIDGET_H
#include "ui_streamswidget.h" #include "ui_portwidget.h"
#include <QWidget> #include <QWidget>
//#include <QAbstractItemModel>
class PortGroupList; class PortGroupList;
class QAbstractItemDelegate;
class StreamsWidget : public QWidget, private Ui::StreamsWidget class PortWidget : public QWidget, private Ui::PortWidget
{ {
Q_OBJECT Q_OBJECT
public: public:
StreamsWidget(QWidget *parent = 0); PortWidget(QWidget *parent = 0);
~StreamsWidget(); ~PortWidget();
void setPortGroupList(PortGroupList *portGroups); void setPortGroupList(PortGroupList *portGroups);
@ -41,30 +39,19 @@ public slots:
void setCurrentPortIndex(const QModelIndex &portIndex); void setCurrentPortIndex(const QModelIndex &portIndex);
private slots: private slots:
void updateStreamViewActions();
void on_startTx_clicked(); void on_startTx_clicked();
void on_stopTx_clicked(); void on_stopTx_clicked();
void on_averagePacketsPerSec_editingFinished(); void on_averagePacketsPerSec_editingFinished();
void on_averageBitsPerSec_editingFinished(); void on_averageBitsPerSec_editingFinished();
void updatePortActions();
void updatePortRates(); void updatePortRates();
void on_tvStreamList_activated(const QModelIndex & index);
void on_actionNew_Stream_triggered();
void on_actionEdit_Stream_triggered();
void on_actionDuplicate_Stream_triggered();
void on_actionDelete_Stream_triggered();
void on_actionOpen_Streams_triggered();
void on_actionSave_Streams_triggered();
void streamModelDataChanged();
private: private:
PortGroupList *plm{nullptr}; // FIXME: rename to portGroups_? PortGroupList *plm{nullptr}; // FIXME: rename to portGroups_?
QModelIndex currentPortIndex_; QModelIndex currentPortIndex_;
QAbstractItemDelegate *delegate;
}; };
#endif #endif

View File

@ -1,19 +1,31 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0"> <ui version="4.0">
<class>StreamsWidget</class> <class>PortWidget</class>
<widget class="QWidget" name="StreamsWidget"> <widget class="QWidget" name="PortWidget">
<property name="geometry"> <property name="geometry">
<rect> <rect>
<x>0</x> <x>0</x>
<y>0</y> <y>0</y>
<width>602</width> <width>532</width>
<height>364</height> <height>42</height>
</rect> </rect>
</property> </property>
<property name="windowTitle"> <property name="windowTitle">
<string>Form</string> <string>Form</string>
</property> </property>
<layout class="QVBoxLayout" name="verticalLayout"> <layout class="QVBoxLayout" name="verticalLayout">
<property name="leftMargin">
<number>0</number>
</property>
<property name="topMargin">
<number>0</number>
</property>
<property name="rightMargin">
<number>0</number>
</property>
<property name="bottomMargin">
<number>0</number>
</property>
<item> <item>
<layout class="QHBoxLayout"> <layout class="QHBoxLayout">
<item> <item>
@ -92,93 +104,8 @@
</item> </item>
</layout> </layout>
</item> </item>
<item>
<widget class="XTableView" name="tvStreamList">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
<horstretch>0</horstretch>
<verstretch>1</verstretch>
</sizepolicy>
</property>
<property name="contextMenuPolicy">
<enum>Qt::ActionsContextMenu</enum>
</property>
<property name="whatsThis">
<string>This is the stream list for the selected port
A stream is a sequence of one or more packets
Right-click to create a stream</string>
</property>
<property name="frameShape">
<enum>QFrame::StyledPanel</enum>
</property>
<property name="lineWidth">
<number>1</number>
</property>
<property name="selectionMode">
<enum>QAbstractItemView::ExtendedSelection</enum>
</property>
<property name="selectionBehavior">
<enum>QAbstractItemView::SelectRows</enum>
</property>
</widget>
</item>
</layout> </layout>
<action name="actionNew_Stream">
<property name="icon">
<iconset resource="ostinato.qrc">
<normaloff>:/icons/stream_add.png</normaloff>:/icons/stream_add.png</iconset>
</property>
<property name="text">
<string>New Stream</string>
</property>
</action>
<action name="actionDelete_Stream">
<property name="icon">
<iconset resource="ostinato.qrc">
<normaloff>:/icons/stream_delete.png</normaloff>:/icons/stream_delete.png</iconset>
</property>
<property name="text">
<string>Delete Stream</string>
</property>
</action>
<action name="actionEdit_Stream">
<property name="icon">
<iconset resource="ostinato.qrc">
<normaloff>:/icons/stream_edit.png</normaloff>:/icons/stream_edit.png</iconset>
</property>
<property name="text">
<string>Edit Stream</string>
</property>
</action>
<action name="actionOpen_Streams">
<property name="text">
<string>Open Streams ...</string>
</property>
</action>
<action name="actionSave_Streams">
<property name="text">
<string>Save Streams ...</string>
</property>
</action>
<action name="actionDuplicate_Stream">
<property name="icon">
<iconset resource="ostinato.qrc">
<normaloff>:/icons/stream_duplicate.png</normaloff>:/icons/stream_duplicate.png</iconset>
</property>
<property name="text">
<string>Duplicate Stream</string>
</property>
</action>
</widget> </widget>
<customwidgets>
<customwidget>
<class>XTableView</class>
<extends>QTableView</extends>
<header>xtableview.h</header>
</customwidget>
</customwidgets>
<resources> <resources>
<include location="ostinato.qrc"/> <include location="ostinato.qrc"/>
</resources> </resources>

View File

@ -24,7 +24,6 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#include "streamconfigdialog.h" #include "streamconfigdialog.h"
#include "streamfileformat.h" #include "streamfileformat.h"
#include "streamlistdelegate.h" #include "streamlistdelegate.h"
#include "xqlocale.h"
#include <QInputDialog> #include <QInputDialog>
#include <QItemSelectionModel> #include <QItemSelectionModel>
@ -143,82 +142,12 @@ void StreamsWidget::setCurrentPortIndex(const QModelIndex &portIndex)
qDebug("In %s", __FUNCTION__); qDebug("In %s", __FUNCTION__);
// Disconnect previous port
if (plm->isPort(currentPortIndex_))
disconnect(&(plm->port(currentPortIndex_)),
SIGNAL(portRateChanged(int, int)),
this, SLOT(updatePortRates()));
currentPortIndex_ = portIndex; currentPortIndex_ = portIndex;
plm->getStreamModel()->setCurrentPortIndex(portIndex); plm->getStreamModel()->setCurrentPortIndex(portIndex);
// Connect current port
if (plm->isPort(currentPortIndex_))
connect(&(plm->port(currentPortIndex_)),
SIGNAL(portRateChanged(int, int)),
this, SLOT(updatePortRates()));
updatePortRates();
updateStreamViewActions(); updateStreamViewActions();
} }
void StreamsWidget::on_startTx_clicked()
{
Q_ASSERT(plm->isPort(currentPortIndex_));
QModelIndex curPortGroup = plm->getPortModel()->parent(currentPortIndex_);
Q_ASSERT(curPortGroup.isValid());
Q_ASSERT(plm->isPortGroup(curPortGroup));
QList<uint> portList({plm->port(currentPortIndex_).id()});
plm->portGroup(curPortGroup).startTx(&portList);
}
void StreamsWidget::on_stopTx_clicked()
{
Q_ASSERT(plm->isPort(currentPortIndex_));
QModelIndex curPortGroup = plm->getPortModel()->parent(currentPortIndex_);
Q_ASSERT(curPortGroup.isValid());
Q_ASSERT(plm->isPortGroup(curPortGroup));
QList<uint> portList({plm->port(currentPortIndex_).id()});
plm->portGroup(curPortGroup).stopTx(&portList);
}
void StreamsWidget::on_averagePacketsPerSec_editingFinished()
{
Q_ASSERT(plm->isPort(currentPortIndex_));
bool isOk;
double pps = XLocale().toDouble(averagePacketsPerSec->text(), &isOk);
plm->port(currentPortIndex_).setAveragePacketRate(pps);
}
void StreamsWidget::on_averageBitsPerSec_editingFinished()
{
Q_ASSERT(plm->isPort(currentPortIndex_));
bool isOk;
double bps = XLocale().toDouble(averageBitsPerSec->text(), &isOk);
plm->port(currentPortIndex_).setAverageBitRate(bps);
}
void StreamsWidget::updatePortRates()
{
if (!currentPortIndex_.isValid())
return;
if (!plm->isPort(currentPortIndex_))
return;
averagePacketsPerSec->setText(QString("%L1")
.arg(plm->port(currentPortIndex_).averagePacketRate(), 0, 'f', 4));
averageBitsPerSec->setText(QString("%L1")
.arg(plm->port(currentPortIndex_).averageBitRate(), 0, 'f', 0));
}
void StreamsWidget::updateStreamViewActions() void StreamsWidget::updateStreamViewActions()
{ {
// For some reason hasSelection() returns true even if selection size is 0 // For some reason hasSelection() returns true even if selection size is 0
@ -259,9 +188,6 @@ void StreamsWidget::updateStreamViewActions()
} }
actionOpen_Streams->setEnabled(plm->isPort(currentPortIndex_)); actionOpen_Streams->setEnabled(plm->isPort(currentPortIndex_));
actionSave_Streams->setEnabled(tvStreamList->model()->rowCount() > 0); actionSave_Streams->setEnabled(tvStreamList->model()->rowCount() > 0);
startTx->setEnabled(tvStreamList->model()->rowCount() > 0);
stopTx->setEnabled(tvStreamList->model()->rowCount() > 0);
} }
void StreamsWidget::on_actionNew_Stream_triggered() void StreamsWidget::on_actionNew_Stream_triggered()
@ -502,4 +428,3 @@ _exit:
return; return;
} }

View File

@ -22,7 +22,6 @@ along with this program. If not, see <http://www.gnu.org/licenses/>
#include "ui_streamswidget.h" #include "ui_streamswidget.h"
#include <QWidget> #include <QWidget>
//#include <QAbstractItemModel>
class PortGroupList; class PortGroupList;
class QAbstractItemDelegate; class QAbstractItemDelegate;
@ -43,11 +42,6 @@ public slots:
private slots: private slots:
void updateStreamViewActions(); void updateStreamViewActions();
void on_startTx_clicked();
void on_stopTx_clicked();
void on_averagePacketsPerSec_editingFinished();
void on_averageBitsPerSec_editingFinished();
void updatePortRates();
void on_tvStreamList_activated(const QModelIndex & index); void on_tvStreamList_activated(const QModelIndex & index);
void on_actionNew_Stream_triggered(); void on_actionNew_Stream_triggered();

View File

@ -14,84 +14,18 @@
<string>Form</string> <string>Form</string>
</property> </property>
<layout class="QVBoxLayout" name="verticalLayout"> <layout class="QVBoxLayout" name="verticalLayout">
<item> <property name="leftMargin">
<layout class="QHBoxLayout"> <number>0</number>
<item> </property>
<widget class="QToolButton" name="startTx"> <property name="topMargin">
<property name="toolTip"> <number>9</number>
<string>Start Transmit</string> </property>
</property> <property name="rightMargin">
<property name="statusTip"> <number>0</number>
<string>Start transmit on selected port</string> </property>
</property> <property name="bottomMargin">
<property name="text"> <number>0</number>
<string/> </property>
</property>
<property name="icon">
<iconset resource="ostinato.qrc">
<normaloff>:/icons/control_play.png</normaloff>:/icons/control_play.png</iconset>
</property>
</widget>
</item>
<item>
<widget class="QToolButton" name="stopTx">
<property name="toolTip">
<string>Stop Transmit</string>
</property>
<property name="statusTip">
<string>Stop transmit on selected port</string>
</property>
<property name="text">
<string/>
</property>
<property name="icon">
<iconset resource="ostinato.qrc">
<normaloff>:/icons/control_stop.png</normaloff>:/icons/control_stop.png</iconset>
</property>
</widget>
</item>
<item>
<spacer>
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
<item>
<widget class="QRadioButton" name="radioButton">
<property name="text">
<string>Avg pps</string>
</property>
<property name="checked">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<widget class="QLineEdit" name="averagePacketsPerSec"/>
</item>
<item>
<widget class="QRadioButton" name="radioButton_2">
<property name="text">
<string>Avg bps</string>
</property>
</widget>
</item>
<item>
<widget class="QLineEdit" name="averageBitsPerSec">
<property name="enabled">
<bool>false</bool>
</property>
</widget>
</item>
</layout>
</item>
<item> <item>
<widget class="XTableView" name="tvStreamList"> <widget class="XTableView" name="tvStreamList">
<property name="sizePolicy"> <property name="sizePolicy">
@ -182,38 +116,5 @@ Right-click to create a stream</string>
<resources> <resources>
<include location="ostinato.qrc"/> <include location="ostinato.qrc"/>
</resources> </resources>
<connections> <connections/>
<connection>
<sender>radioButton</sender>
<signal>toggled(bool)</signal>
<receiver>averagePacketsPerSec</receiver>
<slot>setEnabled(bool)</slot>
<hints>
<hint type="sourcelabel">
<x>326</x>
<y>80</y>
</hint>
<hint type="destinationlabel">
<x>454</x>
<y>79</y>
</hint>
</hints>
</connection>
<connection>
<sender>radioButton_2</sender>
<signal>toggled(bool)</signal>
<receiver>averageBitsPerSec</receiver>
<slot>setEnabled(bool)</slot>
<hints>
<hint type="sourcelabel">
<x>523</x>
<y>80</y>
</hint>
<hint type="destinationlabel">
<x>651</x>
<y>88</y>
</hint>
</hints>
</connection>
</connections>
</ui> </ui>