Feature to add arbitrray phone numbers

This commit is contained in:
Aniket Kumar 2020-03-22 15:03:04 +05:30 committed by Simon Redman
parent a9d0cb64b7
commit d26cfd427f
5 changed files with 99 additions and 1 deletions

View file

@ -263,3 +263,32 @@ void ConversationListModel::displayContacts() {
}
}
}
bool ConversationListModel::isPhoneNumberValid(const QString& number) {
return SmsHelper::isPhoneNumberValid(number);
}
QString ConversationListModel::getDisplayNameForAddress(const QString &address) {
const auto item = getConversationForAddress(address);
if (!item) {
return QString();
}
return item->data(Qt::DisplayRole).toString();
}
void ConversationListModel::createConversationForAddress(const QString& address) {
QStandardItem* item = new QStandardItem();
item->setText(address);
QList<ConversationAddress> addresses;
addresses.append(ConversationAddress(address));
item->setData(QVariant::fromValue(addresses), AddressesRole);
QString displayBody = i18n("%1", address);
item->setData(displayBody, Qt::ToolTipRole);
item->setData(false, MultitargetRole);
item->setData(qint64(INVALID_THREAD_ID), ConversationIdRole);
item->setData(qint64(INVALID_DATE), DateRole);
item->setData(address, SenderRole);
appendRow(item);
}

View file

@ -57,6 +57,22 @@ public:
Q_SCRIPTABLE void refresh();
/**
* This method gets name of conversations or contact if it find any matching address
* Needed for checking if the converstion already or contact already exist or no before adding an arbbitrary contact
*/
Q_INVOKABLE QString getDisplayNameForAddress(const QString& address);
/* This method creates conversation with an arbitrary address */
Q_INVOKABLE void createConversationForAddress(const QString& address);
/**
* This method ensurse whether the phone number format is valid or not
* TODO: This is here because I don't know how to make the QML call the smshelper directly
* but that is what should be happening!
*/
Q_INVOKABLE bool isPhoneNumberValid(const QString& number);
public Q_SLOTS:
void handleCreatedConversation(const QDBusVariant& msg);
void handleConversationUpdated(const QDBusVariant& msg);

View file

@ -125,6 +125,7 @@ Kirigami.ScrollablePage
readonly property bool deviceConnected: devicesCombo.enabled
readonly property QtObject device: devicesCombo.currentIndex >= 0 ? devicesModel.data(devicesModel.index(devicesCombo.currentIndex, 0), DevicesModel.DeviceRole) : null
readonly property alias lastDeviceId: conversationListModel.deviceId
property string displayName
Component {
id: chatView
@ -147,6 +148,7 @@ Kirigami.ScrollablePage
}
}
header: TextField {
/**
* Used as the filter of the list of messages
@ -154,6 +156,7 @@ Kirigami.ScrollablePage
id: filter
placeholderText: i18nd("kdeconnect-sms", "Filter...")
width: parent.width
height: addButton.height
z: 10
onTextChanged: {
if (filter.text != "") {
@ -164,6 +167,15 @@ Kirigami.ScrollablePage
view.model.setFilterFixedString(filter.text)
view.currentIndex = 0
if (conversationListModel.isPhoneNumberValid(filter.text)) {
addButton.visible = true
addButton.focus = true
} else {
addButton.visible = false
addButton.focus = false
filter.width = view.width
}
}
onAccepted: {
view.currentItem.startChat()
@ -181,10 +193,39 @@ Kirigami.ScrollablePage
onActivated: filter.forceActiveFocus()
}
}
headerPositioning: ListView.OverlayHeader
Keys.forwardTo: [headerItem]
Button {
id: addButton
text: i18nd("kdeconnect-sms", "Add")
anchors.right: parent.right
height: view.headerItem.height
visible: false
onClicked: {
// We have to disable the filter temporarily in order to avoid getting key inputs accidently while processing the request
view.headerItem.enabled = false
// If the address entered by the user already exists, fetch the name of the contact otherwise it will return empty string
displayName = conversationListModel.getDisplayNameForAddress(view.headerItem.text)
if (displayName != "") {
view.headerItem.text = displayName
} else {
conversationListModel.createConversationForAddress(view.headerItem.text)
}
view.headerItem.enabled = true
addButton.visible = false
view.headerItem.width = view.width
}
Keys.onReturnPressed: {
event.clicked = true
addButton.onClicked()
}
}
delegate: Kirigami.AbstractListItem
{
id: listItem

View file

@ -127,6 +127,13 @@ QString SmsHelper::canonicalizePhoneNumber(const QString& phoneNumber)
return toReturn;
}
bool SmsHelper::isPhoneNumberValid(const QString& phoneNumber)
{
// This regular expression matches a wide range of international Phone number formats, minimum of 3 digits and maximum upto 15 digits
QRegularExpression validNumberPattern(QStringLiteral("^((\\+?(\\d{2}))\\s?)?((\\d{2})|(\\((\\d{2})\\))\\s?)?(\\d{3,15})(\\-(\\d{3,15}))?$"));
return validNumberPattern.match(phoneNumber).hasMatch();
}
class PersonsCache : public QObject {
public:
PersonsCache() {

View file

@ -118,6 +118,11 @@ public:
static bool isInGsmAlphabet(const QChar& ch);
static bool isInGsmAlphabetExtension(const QChar& ch);
/**
* Used to validate arbitrary phone number entered by the user
*/
static bool isPhoneNumberValid(const QString& phoneNumber);
private:
SmsHelper(){};
~SmsHelper(){};