Skip to content

Commit

Permalink
add addressbook
Browse files Browse the repository at this point in the history
  • Loading branch information
leichaojian committed Nov 22, 2014
1 parent 56a2095 commit 3646ef9
Show file tree
Hide file tree
Showing 14 changed files with 993 additions and 0 deletions.
40 changes: 40 additions & 0 deletions addressbook/adddialog.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
#include "adddialog.h"

#include <QtWidgets>

//实现增加姓名--地址的对话框
AddDialog::AddDialog(QWidget *parent)
: QDialog(parent)
{
nameLabel = new QLabel("Name");
addressLabel = new QLabel("Address");
okButton = new QPushButton("OK");
cancelButton = new QPushButton("Cancel");

nameText = new QLineEdit;
addressText = new QTextEdit;

//通过QGridLayout来进行排列
QGridLayout *gLayout = new QGridLayout;
gLayout->setColumnStretch(1, 2);
gLayout->addWidget(nameLabel, 0, 0);
gLayout->addWidget(nameText, 0, 1);

gLayout->addWidget(addressLabel, 1, 0, Qt::AlignLeft|Qt::AlignTop);
gLayout->addWidget(addressText, 1, 1, Qt::AlignLeft);

QHBoxLayout *buttonLayout = new QHBoxLayout;
buttonLayout->addWidget(okButton);
buttonLayout->addWidget(cancelButton);

gLayout->addLayout(buttonLayout, 2, 1, Qt::AlignRight);

QVBoxLayout *mainLayout = new QVBoxLayout;
mainLayout->addLayout(gLayout);
setLayout(mainLayout);

connect(okButton, SIGNAL(clicked()), this, SLOT(accept()));
connect(cancelButton, SIGNAL(clicked()), this, SLOT(reject()));

setWindowTitle(tr("Add a Contact"));
}
27 changes: 27 additions & 0 deletions addressbook/adddialog.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#ifndef ADDDIALOG_H
#define ADDDIALOG_H

#include <QDialog>

class QLabel;
class QPushButton;
class QTextEdit;
class QLineEdit;

class AddDialog : public QDialog
{
Q_OBJECT

public:
AddDialog(QWidget *parent = 0);
QLineEdit *nameText;
QTextEdit *addressText;

private:
QLabel *nameLabel;
QLabel *addressLabel;
QPushButton *okButton;
QPushButton *cancelButton;
};

#endif // ADDDIALOG_H
28 changes: 28 additions & 0 deletions addressbook/addressbook.pro
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
#-------------------------------------------------
#
# Project created by QtCreator 2014-11-19T19:28:57
#
#-------------------------------------------------

QT += core gui

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

TARGET = addressbook
TEMPLATE = app


SOURCES += main.cpp\
mainwindow.cpp \
tablemodel.cpp \
newaddresstab.cpp \
addresswidget.cpp \
adddialog.cpp

HEADERS += mainwindow.h \
tablemodel.h \
newaddresstab.h \
addresswidget.h \
adddialog.h

FORMS += mainwindow.ui
255 changes: 255 additions & 0 deletions addressbook/addressbook.pro.user

Large diffs are not rendered by default.

201 changes: 201 additions & 0 deletions addressbook/addresswidget.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,201 @@

#include "adddialog.h"
#include "addresswidget.h"

#include <QtWidgets>

AddressWidget::AddressWidget(QWidget *parent)
: QTabWidget(parent)
{
table = new TableModel(this);
newAddressTab = new NewAddressTab(this);
//新增一个地址时候,触发sendDetails信号,而addEntry接收到新增的“姓名--地址”数据
connect(newAddressTab, SIGNAL(sendDetails(QString, QString)),
this, SLOT(addEntry(QString, QString)));

addTab(newAddressTab, "Address Book");

setupTabs();
}

void AddressWidget::addEntry()
{
AddDialog aDialog;

if (aDialog.exec()) {
QString name = aDialog.nameText->text();
QString address = aDialog.addressText->toPlainText();

addEntry(name, address);
}
}

void AddressWidget::addEntry(QString name, QString address)
{
//当前table表格的数据(这里会产生9张table表格)
QList<QPair<QString, QString> >list = table->getList();
QPair<QString, QString> pair(name, address);

//姓名--地址不可重复
if (!list.contains(pair)) {
//在table的第0行0列(第一个参数)新增一行(第二个参数)
table->insertRows(0, 1, QModelIndex());

//index为第0行0列
QModelIndex index = table->index(0, 0, QModelIndex());
table->setData(index, name, Qt::EditRole);
//index为第0行第1列
index = table->index(0, 1, QModelIndex());
table->setData(index, address, Qt::EditRole);
//新增姓名--地址后,删除newAddressTab
removeTab(indexOf(newAddressTab));
} else {
QMessageBox::information(this, tr("Duplicate Name"),
tr("The name \"%1\" already exists.").arg(name));
}
}

void AddressWidget::editEntry()
{
//得到当前的QTableView
QTableView *temp = static_cast<QTableView*>(currentWidget());
//QSortFilterProxyModel在model和view之间提供排序和过滤
QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(temp->model());
//选择model
QItemSelectionModel *selectionModel = temp->selectionModel();

//得到当前所要被修改的索引---这里indexes实际上就一项(因为只允许选择一行)
QModelIndexList indexes = selectionModel->selectedRows();
QString name;
QString address;
int row = -1;

foreach (QModelIndex index, indexes) {
//mapToSource:Returns the source model index corresponding to the given proxyIndex from the sorting filter model.
row = proxy->mapToSource(index).row();
//得到姓名数据---这里table指针是一个模型,关联具体表格
QModelIndex nameIndex = table->index(row, 0, QModelIndex());
QVariant varName = table->data(nameIndex, Qt::DisplayRole);
name = varName.toString();

//得到地址数据
QModelIndex addressIndex = table->index(row, 1, QModelIndex());
QVariant varAddr = table->data(addressIndex, Qt::DisplayRole);
address = varAddr.toString();
}

AddDialog aDialog;
aDialog.setWindowTitle(tr("Edit a Contact"));

//只允许更改地址
aDialog.nameText->setReadOnly(true);
aDialog.nameText->setText(name);
aDialog.addressText->setText(address);

if (aDialog.exec()) {
QString newAddress = aDialog.addressText->toPlainText();
if (newAddress != address) {
//得到第row行第二列(1)的索引,通过setData来更新数据
QModelIndex index = table->index(row, 1, QModelIndex());
table->setData(index, newAddress, Qt::EditRole);
}
}
}

void AddressWidget::removeEntry()
{
QTableView *temp = static_cast<QTableView*>(currentWidget());
QSortFilterProxyModel *proxy = static_cast<QSortFilterProxyModel*>(temp->model());
QItemSelectionModel *selectionModel = temp->selectionModel();

QModelIndexList indexes = selectionModel->selectedRows();

foreach (QModelIndex index, indexes) {
int row = proxy->mapToSource(index).row();
//从row行开始删除一行
table->removeRows(row, 1, QModelIndex());
}

if (table->rowCount(QModelIndex()) == 0) {
insertTab(0, newAddressTab, "Address Book");
}
}

//实现九列表格框
void AddressWidget::setupTabs()
{
QStringList groups;
groups << "ABC" << "DEF" << "GHI" << "JKL" << "MNO" << "PQR" << "STU" << "VW" << "XYZ";

for (int i = 0; i < groups.size(); ++i) {
QString str = groups.at(i);
QString regExp = QString("^[%1].*").arg(str);

//设定过滤模型--在model(模型中专门用于处理数据,而view则用于显示数据)
proxyModel = new QSortFilterProxyModel(this);
proxyModel->setSourceModel(table);
proxyModel->setFilterRegExp(QRegExp(regExp, Qt::CaseInsensitive));
proxyModel->setFilterKeyColumn(0);

//将过滤模型添加到视图中:则数据显示之前会被自动过滤(这里的过滤是自动排序)
QTableView *tableView = new QTableView;
tableView->setModel(proxyModel);

//允许用户选择行
tableView->setSelectionBehavior(QAbstractItemView::SelectRows);
tableView->horizontalHeader()->setStretchLastSection(true);
tableView->verticalHeader()->hide();
tableView->setEditTriggers(QAbstractItemView::NoEditTriggers);
//允许用户选择一整行
tableView->setSelectionMode(QAbstractItemView::SingleSelection);

tableView->setSortingEnabled(true);

//此信号槽的作用不太理解---
connect(tableView->selectionModel(),
SIGNAL(selectionChanged(QItemSelection,QItemSelection)),
this, SIGNAL(selectionChanged(QItemSelection)));

//这里新建的一张表格是groups的一部分(groups包含九张表格)
addTab(tableView, str);
}
}

void AddressWidget::readFromFile(const QString &fileName)
{
QFile file(fileName);

if (!file.open(QIODevice::ReadOnly)) {
QMessageBox::information(this, tr("Unable to open file"),
file.errorString());
return;
}

QList<QPair<QString, QString> > pairs = table->getList();
QDataStream in(&file);
in >> pairs;

if (pairs.isEmpty()) {
QMessageBox::information(this, tr("No contacts in file"),
tr("The file you are attempting to open contains no contacts."));
} else {
for (int i=0; i<pairs.size(); ++i) {
QPair<QString, QString> p = pairs.at(i);
addEntry(p.first, p.second);
}
}
}

void AddressWidget::writeToFile(const QString &fileName)
{
QFile file(fileName);

if (!file.open(QIODevice::WriteOnly)) {
QMessageBox::information(this, tr("Unable to open file"), file.errorString());
return;
}

QList<QPair<QString, QString> > pairs = table->getList();
QDataStream out(&file);
out << pairs;
}
39 changes: 39 additions & 0 deletions addressbook/addresswidget.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
#ifndef ADDRESSWIDGET_H
#define ADDRESSWIDGET_H

#include "newaddresstab.h"
#include "tablemodel.h"

#include <QItemSelection>
#include <QTabWidget>

class QSortFilterProxyModel;
class QItemSelectionModel;

class AddressWidget : public QTabWidget
{
Q_OBJECT

public:
AddressWidget(QWidget *parent = 0);
void readFromFile(const QString &fileName);
void writeToFile(const QString &fileName);

public slots:
void addEntry();
void addEntry(QString name, QString address);
void editEntry();
void removeEntry();

signals:
void selectionChanged (const QItemSelection &selected);

private:
void setupTabs();

TableModel *table;
NewAddressTab *newAddressTab;
QSortFilterProxyModel *proxyModel;
};

#endif // ADDRESSWIDGET_H
11 changes: 11 additions & 0 deletions addressbook/main.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#include "mainwindow.h"
#include <QApplication>

int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow w;
w.show();

return a.exec();
}
Loading

0 comments on commit 3646ef9

Please sign in to comment.