1 /*
2  * This file is part of Licq, an instant messaging client for UNIX.
3  * Copyright (C) 2000-2014 Licq developers <licq-dev@googlegroups.com>
4  *
5  * Licq is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2 of the License, or
8  * (at your option) any later version.
9  *
10  * Licq is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with Licq; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
18  */
19 
20 #include "mmuserview.h"
21 
22 #include "config.h"
23 
24 #include <boost/foreach.hpp>
25 #include <ctype.h>
26 
27 #include <QDragEnterEvent>
28 #include <QDropEvent>
29 #include <QHeaderView>
30 #include <QKeyEvent>
31 #include <QMenu>
32 #include <QMimeData>
33 #include <QMouseEvent>
34 
35 #include "config/contactlist.h"
36 
37 #include "contactlist/contactlist.h"
38 #include "contactlist/multicontactproxy.h"
39 
40 #include "core/gui-defines.h"
41 #include "core/licqgui.h"
42 #include "core/messagebox.h"
43 
44 using std::set;
45 using namespace LicqQtGui;
46 /* TRANSLATOR LicqQtGui::MMUserView */
47 
MMUserView(const Licq::UserId & userId,ContactListModel * contactList,QWidget * parent)48 MMUserView::MMUserView(const Licq::UserId& userId, ContactListModel* contactList, QWidget* parent)
49   : UserViewBase(contactList, false, parent),
50     myUserId(userId)
51 {
52   // Use a proxy model for sorting and filtering
53   myListProxy = new MultiContactProxy(myContactList, this);
54   setModel(myListProxy);
55   setRootIndex(dynamic_cast<MultiContactProxy*>(myListProxy)->rootIndex());
56 
57   // Setup popup menu
58   myMenu = new QMenu(this);
59   myMenu->addAction(tr("Remove"), this, SLOT(remove()));
60   myMenu->addAction(tr("Crop"), this, SLOT(crop()));
61   myMenu->addAction(tr("Clear"), this, SLOT(clear()));
62   myMenu->addSeparator();
63   myMenu->addAction(tr("Add Group"), this, SLOT(addCurrentGroup()));
64   myMenu->addAction(tr("Add All"), this, SLOT(addAll()));
65 
66   setSelectionMode(ExtendedSelection);
67   dynamic_cast<SortedContactListProxy*>(myListProxy)->sort(0);
68   header()->setVisible(Config::ContactList::instance()->showHeader());
69 
70   for (int i = 0; i < Config::ContactList::instance()->columnCount(); i++)
71     setColumnWidth(i, Config::ContactList::instance()->columnWidth(i));
72 }
73 
~MMUserView()74 MMUserView::~MMUserView()
75 {
76   // Empty
77 }
78 
add(const Licq::UserId & userId)79 void MMUserView::add(const Licq::UserId& userId)
80 {
81   if (userId == myUserId)
82     return;
83   dynamic_cast<MultiContactProxy*>(myListProxy)->add(userId);
84 }
85 
removeFirst()86 void MMUserView::removeFirst()
87 {
88   Licq::UserId userId = *contacts().begin();
89   dynamic_cast<MultiContactProxy*>(myListProxy)->remove(userId);
90 }
91 
contacts() const92 const set<Licq::UserId>& MMUserView::contacts() const
93 {
94   return dynamic_cast<MultiContactProxy*>(myListProxy)->contacts();
95 }
96 
remove()97 void MMUserView::remove()
98 {
99   dynamic_cast<MultiContactProxy*>(myListProxy)->remove(selectedIndexes());
100 }
101 
crop()102 void MMUserView::crop()
103 {
104   dynamic_cast<MultiContactProxy*>(myListProxy)->crop(selectedIndexes());
105 }
106 
clear()107 void MMUserView::clear()
108 {
109   dynamic_cast<MultiContactProxy*>(myListProxy)->clear();
110 }
111 
addCurrentGroup()112 void MMUserView::addCurrentGroup()
113 {
114   int groupId = Config::ContactList::instance()->groupId();
115 
116   if (groupId == ContactListModel::AllGroupsGroupId)
117     groupId = ContactListModel::MostUsersGroupId;
118 
119   dynamic_cast<MultiContactProxy*>(myListProxy)->addGroup(groupId);
120 
121   // Make sure current user isn't added
122   dynamic_cast<MultiContactProxy*>(myListProxy)->remove(myUserId);
123 }
124 
addAll()125 void MMUserView::addAll()
126 {
127   // Add all contacts from "All users" group
128   dynamic_cast<MultiContactProxy*>(myListProxy)->addGroup(ContactListModel::MostUsersGroupId);
129 
130   // Make sure current user isn't added
131   dynamic_cast<MultiContactProxy*>(myListProxy)->remove(myUserId);
132 }
133 
dragEnterEvent(QDragEnterEvent * event)134 void MMUserView::dragEnterEvent(QDragEnterEvent* event)
135 {
136   if (event->mimeData()->hasText())
137     event->acceptProposedAction();
138 }
139 
dropEvent(QDropEvent * event)140 void MMUserView::dropEvent(QDropEvent* event)
141 {
142   // We ignore the event per default and then accept it if we
143   // get to the end of this function.
144   event->ignore();
145 
146   Licq::UserId dropUserId(gLicqGui->userIdFromMimeData(*event->mimeData()));
147   if (!dropUserId.isValid())
148     return; // Not accepted
149 
150   add(dropUserId);
151 
152   event->acceptProposedAction();
153 }
154 
mousePressEvent(QMouseEvent * event)155 void MMUserView::mousePressEvent(QMouseEvent* event)
156 {
157   UserViewBase::mousePressEvent(event);
158 
159   if (event->button() == Qt::LeftButton)
160   {
161     if (!indexAt(event->pos()).isValid())
162     {
163       // Clicking outiside list will clear selection
164       selectionModel()->clearSelection();
165       setCurrentIndex(QModelIndex());
166     }
167   }
168 }
169 
contextMenuEvent(QContextMenuEvent * event)170 void MMUserView::contextMenuEvent(QContextMenuEvent* event)
171 {
172   myMenu->popup(viewport()->mapToGlobal(event->pos()));
173 }
174 
keyPressEvent(QKeyEvent * event)175 void MMUserView::keyPressEvent(QKeyEvent* event)
176 {
177   if (event->modifiers() & (Qt::ControlModifier | Qt::AltModifier))
178   {
179     event->ignore();
180     UserViewBase::keyPressEvent(event);
181     return;
182   }
183 
184   switch (event->key())
185   {
186     case Qt::Key_Space:
187       myMenu->popup(viewport()->mapToGlobal(QPoint(40, visualRect(currentIndex()).y())));
188       return;
189 
190     default:
191       UserViewBase::keyPressEvent(event);
192   }
193 }
194