00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "taskgroupitem.h"
00023 #include "layoutwidget.h"
00024 #include "windowtaskitem.h"
00025 #include "tasksmenu.h"
00026
00027
00028 #include <QGraphicsSceneContextMenuEvent>
00029 #include <QStyleOptionGraphicsItem>
00030 #include <QGraphicsView>
00031 #include <QTimer>
00032 #include <QApplication>
00033 #include <QGraphicsLinearLayout>
00034 #include <QInputDialog>
00035
00036
00037 #include <KAuthorized>
00038 #include <KDebug>
00039 #include <KIcon>
00040 #include <KLocalizedString>
00041 #include <KGlobalSettings>
00042 #include <KIconLoader>
00043
00044 #include <taskmanager/taskactions.h>
00045 #include <taskmanager/taskmanager.h>
00046 #include <taskmanager/taskgroup.h>
00047 #include <taskmanager/abstractgroupingstrategy.h>
00048
00049 #include <Plasma/Theme>
00050 #include <Plasma/FrameSvg>
00051 #include <Plasma/ToolTipManager>
00052 #include <Plasma/Corona>
00053 #include <Plasma/Containment>
00054
00055 #include "tasks.h"
00056 #include "layoutwidget.h"
00057
00058 TaskGroupItem::TaskGroupItem(QGraphicsWidget *parent, Tasks *applet, const bool showTooltip)
00059 : AbstractTaskItem(parent, applet, showTooltip),
00060 m_group(0),
00061 m_expandedLayout(0),
00062 m_popupMenuTimer(0),
00063 m_lastActivated(-1),
00064 m_activeTaskIndex(0),
00065 m_maximumRows(1),
00066 m_forceRows(false),
00067 m_splitPosition(0),
00068 m_parentSplitGroup(0),
00069 m_childSplitGroup(0)
00070 {
00071 setAcceptDrops(true);
00072 }
00073
00074
00075 bool TaskGroupItem::isSplit()
00076 {
00077 return m_childSplitGroup != 0;
00078 }
00079
00080 void TaskGroupItem::setSplitGroup(TaskGroup *group)
00081 {
00082 m_group = group;
00083 m_parentSplitGroup = dynamic_cast<TaskGroupItem*>(parentWidget());
00084 if (!m_parentSplitGroup) {
00085 kDebug() << "no parentSplit Group";
00086 return;
00087 }
00088 expand();
00089 }
00090
00091
00092 void TaskGroupItem::unsplitGroup()
00093 {
00094
00095 if (!m_childSplitGroup) {
00096 return;
00097 }
00098 m_childSplitGroup->deleteLater();
00099 m_childSplitGroup = 0;
00100 m_splitPosition = 0;
00101 reload();
00102 }
00103
00104
00105 TaskGroupItem * TaskGroupItem::splitGroup()
00106 {
00107 return m_childSplitGroup;
00108 }
00109
00110 void TaskGroupItem::setSplitIndex(int position)
00111 {
00112
00113 Q_ASSERT(m_expandedLayout);
00114 Q_ASSERT(m_parentSplitGroup);
00115
00116 for (int i = position ; i < m_parentSplitGroup->group()->members().size() ; i++) {
00117
00118 AbstractGroupableItem *item = m_parentSplitGroup->group()->members().at(i);
00119 if (!m_groupMembers.contains(item)) {
00120 m_groupMembers.insert(item, m_parentSplitGroup->abstractItem(item));
00121 }
00122 m_expandedLayout->addTaskItem(abstractItem(item));
00123 }
00124 m_splitPosition = position;
00125 }
00126
00127 TaskGroupItem * TaskGroupItem::splitGroup(int newSplitPosition)
00128 {
00129
00130 Q_ASSERT(m_expandedLayout);
00131
00132
00133 for (int i = newSplitPosition ; i < m_groupMembers.size() ; i++) {
00134 AbstractGroupableItem *item = group()->members().at(i);
00135 m_expandedLayout->removeTaskItem(abstractItem(item));
00136
00137 }
00138
00139 if (m_splitPosition) {
00140 for (int i = m_splitPosition ; i < newSplitPosition ; i++) {
00141 AbstractGroupableItem *item = group()->members().at(i);
00142 m_expandedLayout->addTaskItem(abstractItem(item));
00143
00144 }
00145 }
00146
00147 if (!m_childSplitGroup) {
00148
00149 m_childSplitGroup = new TaskGroupItem(this, m_applet, true);
00150 m_childSplitGroup->setSplitGroup(m_group);
00151 }
00152
00153 m_childSplitGroup->setSplitIndex(newSplitPosition);
00154 m_splitPosition = newSplitPosition;
00155 return m_childSplitGroup;
00156 }
00157
00158
00159 void TaskGroupItem::activate()
00160 {
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173 }
00174
00175 void TaskGroupItem::close()
00176 {
00177
00178 m_group = 0;
00179 }
00180
00181
00182 void TaskGroupItem::updateTask(::TaskManager::TaskChanges changes)
00183 {
00184 Q_ASSERT(m_group);
00185
00186 bool needsUpdate = false;
00187
00188 TaskFlags flags = m_flags;
00189 if (m_group->isActive()) {
00190 flags |= TaskHasFocus;
00191 emit activated(this);
00192 } else {
00193 flags &= ~TaskHasFocus;
00194 }
00195
00196 if (m_group->demandsAttention()) {
00197 flags |= TaskWantsAttention;
00198 } else {
00199 flags &= ~TaskWantsAttention;
00200 }
00201
00202 if (m_group->isMinimized()) {
00203 flags |= TaskIsMinimized;
00204 } else {
00205 flags &= ~TaskIsMinimized;
00206 }
00207
00208 if (flags != m_flags) {
00209 needsUpdate = true;
00210 setTaskFlags(flags);
00211 }
00212
00213
00214 if (changes & TaskManager::IconChanged) {
00215 needsUpdate = true;
00216 setIcon(m_group->icon());
00217 }
00218
00219 if (changes & TaskManager::NameChanged) {
00220 needsUpdate = true;
00221 setText(m_group->name());
00222 }
00223
00224 if (m_showingTooltip &&
00225 (changes & TaskManager::IconChanged ||
00226 changes & TaskManager::NameChanged ||
00227 changes & TaskManager::DesktopChanged)) {
00228 updateToolTip();
00229 }
00230
00231 if (needsUpdate) {
00232
00233 queueUpdate();
00234 }
00235 }
00236
00237 void TaskGroupItem::updateToolTip()
00238 {
00239 if (!m_group) {
00240 return;
00241 }
00242
00243 Plasma::ToolTipContent data(m_group->name(),
00244 i18nc("Which virtual desktop a window is currently on", "On %1",
00245 KWindowSystem::desktopName(m_group->desktop())));
00246
00247
00248
00249 Plasma::ToolTipManager::self()->setContent(this, data);
00250 }
00251
00252
00253 void TaskGroupItem::reload()
00254 {
00255 kDebug();
00256 QList <AbstractItemPtr> itemsToRemove = m_groupMembers.keys();
00257
00258 foreach (AbstractItemPtr item, group()->members()) {
00259 if (!item) {
00260 kDebug() << "invalid Item";
00261 continue;
00262 }
00263 itemsToRemove.removeAll(item);
00264 itemAdded(item);
00265
00266 if (item->isGroupItem()) {
00267 TaskGroupItem *group = qobject_cast<TaskGroupItem *>(abstractItem(item));
00268 if (group) {
00269 group->reload();
00270 }
00271 }
00272 }
00273 foreach (AbstractItemPtr item, itemsToRemove) {
00274 if (!item) {
00275 kDebug() << "invalid Item";
00276 continue;
00277 }
00278 itemRemoved(item);
00279 }
00280 }
00281
00282 void TaskGroupItem::setGroup(TaskManager::GroupPtr group)
00283 {
00284
00285 m_group = group;
00286 m_abstractItem = qobject_cast<AbstractItemPtr>(group);
00287 if (!m_abstractItem) {
00288 kDebug() << "error";
00289 }
00290
00291 connect(m_group, SIGNAL(itemRemoved(AbstractItemPtr)), this, SLOT(itemRemoved(AbstractItemPtr)));
00292 connect(m_group, SIGNAL(itemAdded(AbstractItemPtr)), this, SLOT(itemAdded(AbstractItemPtr)));
00293
00294
00295
00296 connect(m_group, SIGNAL(changed(::TaskManager::TaskChanges)),
00297 this, SLOT(updateTask(::TaskManager::TaskChanges)));
00298
00299 connect(m_group, SIGNAL(itemPositionChanged(AbstractItemPtr)), this, SLOT(itemPositionChanged(AbstractItemPtr)));
00300 connect(m_group, SIGNAL(groupEditRequest()), this, SLOT(editGroup()));
00301
00302
00303 reload();
00304 updateTask(::TaskManager::EverythingChanged);
00305
00306
00307 }
00308
00309 TaskManager::GroupPtr TaskGroupItem::group() const
00310 {
00311 return m_group;
00312 }
00313
00314 void TaskGroupItem::contextMenuEvent(QGraphicsSceneContextMenuEvent *e)
00315 {
00316
00317 if (!KAuthorized::authorizeKAction("kwin_rmb") || !m_group) {
00318 QGraphicsWidget::contextMenuEvent(e);
00319 return;
00320 }
00321 Q_ASSERT(m_applet);
00322
00323 if (m_applet == parentWidget()) {
00324 e->ignore();
00325 return;
00326 }
00327
00328 QAction *a;
00329
00330 if (m_expandedLayout) {
00331 a = new QAction(i18n("Collapse Group"), this);
00332 connect(a, SIGNAL(triggered()), this, SLOT(collapse()));
00333 } else {
00334 a = new QAction(i18n("Expand Group"), this);
00335 connect(a, SIGNAL(triggered()), this, SLOT(expand()));
00336 }
00337
00338 QList <QAction*> actionList;
00339 actionList.append(a);
00340
00341 TaskManager::BasicMenu menu(qobject_cast<QWidget*>(this), m_group, &m_applet->groupManager(), actionList);
00342 menu.adjustSize();
00343
00344 Q_ASSERT(m_applet->containment());
00345 Q_ASSERT(m_applet->containment()->corona());
00346 menu.exec(m_applet->containment()->corona()->popupPosition(this, menu.size()));
00347 }
00348
00349 QList<AbstractTaskItem*> TaskGroupItem::memberList() const
00350 {
00351 return m_groupMembers.values();
00352 }
00353
00354 AbstractTaskItem *TaskGroupItem::createAbstractItem(TaskManager::AbstractItemPtr groupableItem)
00355 {
00356
00357 AbstractTaskItem *item = 0;
00358
00359 if (m_groupMembers.contains(groupableItem)) {
00360
00361 return m_groupMembers.value(groupableItem);
00362 }
00363
00364 if (groupableItem->isGroupItem()) {
00365 TaskGroupItem *groupItem = new TaskGroupItem(this, m_applet, m_applet->showTooltip());
00366 groupItem->setGroup(static_cast<TaskManager::TaskGroup*>(groupableItem));
00367 item = groupItem;
00368 } else {
00369 WindowTaskItem *windowItem = new WindowTaskItem(this, m_applet, m_applet->showTooltip());
00370 windowItem->setTask(static_cast<TaskManager::TaskItem*>(groupableItem));
00371 item = windowItem;
00372 }
00373
00374 if (!item) {
00375 kDebug() << "invalid Item";
00376 return 0;
00377 }
00378
00379 return item;
00380 }
00381
00382
00383
00384 void TaskGroupItem::itemAdded(TaskManager::AbstractItemPtr groupableItem)
00385 {
00386
00387 if (!m_applet) {
00388 kDebug() << "No applet";
00389 return;
00390 }
00391
00392
00393 AbstractTaskItem *item = createAbstractItem(groupableItem);
00394
00395 if (!item) {
00396 kDebug() << "invalid Item";
00397 return;
00398 }
00399
00400 m_groupMembers[groupableItem] = item;
00401 item->setParentItem(this);
00402
00403 if (collapsed()) {
00404 item->hide();
00405 QRect rect = iconGeometry();
00406 item->publishIconGeometry(rect);
00407 } else if (isSplit()) {
00408 splitGroup(m_splitPosition);
00409
00410
00411 } else {
00412 m_expandedLayout->addTaskItem(item);
00413 }
00414
00415 if (item->isActive()) {
00416
00417 m_activeTaskIndex = indexOf(item);
00418 } else if (m_group->members().size() == 1) {
00419 m_activeTaskIndex = 0;
00420 }
00421
00422 connect(item, SIGNAL(activated(AbstractTaskItem*)),
00423 this, SLOT(updateActive(AbstractTaskItem*)));
00424
00425 }
00426
00427 void TaskGroupItem::itemRemoved(TaskManager::AbstractItemPtr groupableItem)
00428 {
00429
00430 if (!m_applet) {
00431 kDebug() << "No Applet";
00432 return;
00433 }
00434 AbstractTaskItem *item = m_groupMembers.take(groupableItem);;
00435
00436 if (!item) {
00437 kDebug() << "Item not found";
00438 return;
00439 }
00440
00441 disconnect(item, 0, 0, 0);
00442
00443 if (m_expandedLayout) {
00444 m_expandedLayout->removeTaskItem(item);
00445 }
00446
00447 item->close();
00448 item->deleteLater();
00449 }
00450
00451
00452 bool TaskGroupItem::isWindowItem() const
00453 {
00454 return false;
00455 }
00456
00457 bool TaskGroupItem::isActive() const
00458 {
00459 kDebug() << "Not Implemented";
00460 return false;
00461 }
00462
00463 void TaskGroupItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
00464 {
00465 if (event->buttons() & Qt::LeftButton) {
00466 if (m_applet->groupManager().sortingStrategy() == TaskManager::GroupManager::ManualSorting ||
00467 m_applet->groupManager().groupingStrategy() == TaskManager::GroupManager::ManualGrouping) {
00468 if (!m_popupMenuTimer) {
00469 m_popupMenuTimer = new QTimer(this);
00470 m_popupMenuTimer->setSingleShot(true);
00471 m_popupMenuTimer->setInterval(300);
00472 connect(m_popupMenuTimer, SIGNAL(timeout()), this, SLOT(popupMenu()));
00473 }
00474 m_popupMenuTimer->start(300);
00475 } else {
00476 popupMenu();
00477 }
00478 }
00479
00480 event->accept();
00481 }
00482
00483 void TaskGroupItem::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
00484 {
00485 if (event->button() == Qt::MidButton) {
00486 expand();
00487 }
00488
00489 if (m_popupMenuTimer) {
00490 if (m_popupMenuTimer->isActive()) {
00491
00492 popupMenu();
00493 }
00494 m_popupMenuTimer->stop();
00495 }
00496
00497 AbstractTaskItem::mouseReleaseEvent(event);
00498 }
00499
00500 void TaskGroupItem::popupMenu()
00501 {
00502 if (!m_expandedLayout) {
00503 TaskManager::TasksMenu menu(qobject_cast<QWidget*>(this), m_group, &m_applet->groupManager(), m_applet);
00504 menu.adjustSize();
00505 Q_ASSERT(m_applet->containment());
00506 Q_ASSERT(m_applet->containment()->corona());
00507 menu.exec(m_applet->containment()->corona()->popupPosition(this, menu.size()));
00508 }
00509 }
00510
00511 void TaskGroupItem::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
00512 {
00513 if (QPoint(event->screenPos() - event->buttonDownScreenPos(Qt::LeftButton)).manhattanLength() < QApplication::startDragDistance()) {
00514 return;
00515 }
00516
00517
00518 if (m_popupMenuTimer) {
00519 m_popupMenuTimer->stop();
00520 }
00521 AbstractTaskItem::mouseMoveEvent(event);
00522 }
00523
00524 void TaskGroupItem::expand()
00525 {
00526 if (m_expandedLayout) {
00527
00528 return;
00529 }
00530
00531
00532 m_expandedLayout = new LayoutWidget(this, m_applet);
00533 m_expandedLayout->setMaximumRows(m_maximumRows);
00534 m_expandedLayout->setForceRows(m_forceRows);
00535
00536
00537
00538 connect(m_applet, SIGNAL(constraintsChanged(Plasma::Constraints)), m_expandedLayout, SLOT(constraintsChanged(Plasma::Constraints)));
00539 connect(m_expandedLayout, SIGNAL(sizeHintChanged(Qt::SizeHint)), this, SLOT(updatePreferredSize()));
00540 updatePreferredSize();
00541 emit changed();
00542 checkSettings();
00543
00544
00545 }
00546
00547 LayoutWidget *TaskGroupItem::layoutWidget()
00548 {
00549 return m_expandedLayout;
00550 }
00551
00552 void TaskGroupItem::collapse()
00553 {
00554
00555 if (!m_expandedLayout) {
00556
00557 return;
00558 }
00559
00560 if (m_parentSplitGroup) {
00561 m_parentSplitGroup->collapse();
00562 }
00563
00564
00565 unsplitGroup();
00566 foreach (AbstractTaskItem *member, m_groupMembers) {
00567 m_expandedLayout->removeTaskItem(member);
00568 }
00569 setLayout(0);
00570
00571
00572 m_expandedLayout = 0;
00573 updatePreferredSize();
00574
00575 emit changed();
00576 checkSettings();
00577 }
00578
00579 bool TaskGroupItem::collapsed() const
00580 {
00581 return m_expandedLayout == 0;
00582 }
00583
00584 void TaskGroupItem::updatePreferredSize()
00585 {
00586 if (layout()) {
00587 setPreferredSize(layout()->preferredSize());
00588 layout()->invalidate();
00589
00590 } else {
00591
00592 setPreferredSize(basicPreferredSize());
00593 }
00594
00595 emit sizeHintChanged(Qt::PreferredSize);
00596 }
00597
00598
00599
00600 AbstractTaskItem *TaskGroupItem::directMember(AbstractTaskItem *item)
00601 {
00602 Q_ASSERT(item);
00603 Q_ASSERT(m_group);
00604 TaskManager::AbstractItemPtr directMember = m_group->directMember(item->abstractItem());
00605 if (!directMember) {
00606 kDebug() << "Error" << item->abstractItem();
00607 }
00608 return abstractItem(directMember);
00609 }
00610
00611 void TaskGroupItem::paint(QPainter *painter,
00612 const QStyleOptionGraphicsItem *option,
00613 QWidget *widget)
00614 {
00615 if (!m_expandedLayout) {
00616 AbstractTaskItem::paint(painter,option,widget);
00617 }
00618
00619
00620
00621
00622
00623
00624
00625 }
00626
00627
00628
00629 void TaskGroupItem::editGroup()
00630 {
00631
00632
00633 Q_ASSERT(m_group);
00634 Q_ASSERT(m_applet);
00635 if (m_applet->groupManager().taskGrouper()->editableGroupProperties() & TaskManager::AbstractGroupingStrategy::Name) {
00636 bool ok;
00637 QString text = QInputDialog::getText(qobject_cast<QWidget*>(this), tr("Edit Group"),
00638 tr("New Group Name: "), QLineEdit::Normal,
00639 m_group->name(), &ok);
00640 if (ok && !text.isEmpty()) {
00641 m_group->setName(text);
00642 }
00643 }
00644 }
00645
00646
00647 void TaskGroupItem::itemPositionChanged(AbstractItemPtr item)
00648 {
00649
00650 if (!m_expandedLayout) {
00651 return;
00652 }
00653
00654 Q_ASSERT(item);
00655
00656 if (item->isGroupItem()) {
00657 TaskGroupItem *groupItem = static_cast<TaskGroupItem*>(abstractItem(item));
00658 if (groupItem) {
00659 groupItem->unsplitGroup();
00660 }
00661 }
00662
00663 AbstractTaskItem *taskItem = abstractItem(item);
00664
00665 m_expandedLayout->removeTaskItem(taskItem);
00666 m_expandedLayout->insert(m_group->members().indexOf(item), taskItem);
00667 }
00668
00669
00670 void TaskGroupItem::dragEnterEvent(QGraphicsSceneDragDropEvent *event)
00671 {
00672
00673 if (!m_expandedLayout &&
00674 (event->mimeData()->hasFormat(TaskManager::Task::mimetype()) ||
00675 event->mimeData()->hasFormat(TaskManager::Task::groupMimetype()))) {
00676 event->acceptProposedAction();
00677
00678 } else {
00679 event->accept();
00680 if (!m_popupMenuTimer) {
00681 m_popupMenuTimer = new QTimer(this);
00682 m_popupMenuTimer->setSingleShot(true);
00683 m_popupMenuTimer->setInterval(300);
00684 connect(m_popupMenuTimer, SIGNAL(timeout()), this, SLOT(popupMenu()));
00685 }
00686 m_popupMenuTimer->start(300);
00687 }
00688 }
00689
00690 AbstractTaskItem *TaskGroupItem::taskItemForWId(WId id)
00691 {
00692 QHashIterator<AbstractItemPtr, AbstractTaskItem*> it(m_groupMembers);
00693
00694 while (it.hasNext()) {
00695 it.next();
00696 AbstractTaskItem *item = it.value();
00697 TaskGroupItem *group = qobject_cast<TaskGroupItem*>(item);
00698
00699 if (group) {
00700 item = group->taskItemForWId(id);
00701 if (item) {
00702 return item;
00703 }
00704 } else {
00705 TaskManager::TaskItem *task = qobject_cast<TaskManager::TaskItem*>(it.key());
00706 if (task && task->task() && task->task()->window() == id) {
00707 return item;
00708 }
00709 }
00710 }
00711
00712 return 0;
00713 }
00714
00715 void TaskGroupItem::dropEvent(QGraphicsSceneDragDropEvent *event)
00716 {
00717
00718 if (event->mimeData()->hasFormat(TaskManager::Task::mimetype()) ||
00719 event->mimeData()->hasFormat(TaskManager::Task::groupMimetype())) {
00720 bool ok;
00721 QList<WId> ids = TaskManager::Task::idsFromMimeData(event->mimeData(), &ok);
00722
00723 if (!ok) {
00724
00725 event->ignore();
00726 return;
00727 }
00728
00729 AbstractTaskItem *targetTask = dynamic_cast<AbstractTaskItem *>(scene()->itemAt(mapToScene(event->pos())));
00730
00731
00732
00733 foreach (WId id, ids) {
00734 handleDroppedId(id, targetTask, event);
00735 }
00736
00737
00738 event->acceptProposedAction();
00739 } else {
00740 event->ignore();
00741 }
00742 }
00743
00744 void TaskGroupItem::handleDroppedId(WId id, AbstractTaskItem *targetTask, QGraphicsSceneDragDropEvent *event)
00745 {
00746 AbstractTaskItem *taskItem = m_applet->rootGroupItem()->taskItemForWId(id);
00747
00748 if (!taskItem) {
00749
00750 return;
00751 }
00752
00753 if (!taskItem->parentGroup()) {
00754
00755 return;
00756 }
00757
00758 TaskManager::GroupPtr group = taskItem->parentGroup()->group();
00759
00760
00761
00762
00763
00764 if ((event->modifiers() == m_applet->groupModifierKey()) &&
00765 m_applet->groupManager().groupingStrategy() == TaskManager::GroupManager::ManualGrouping) {
00766
00767
00768 if (!targetTask) {
00769
00770 m_applet->groupManager().manualGroupingRequest(taskItem->abstractItem(), m_group);
00771 } else if (targetTask->isWindowItem() && (group == m_group)) {
00772
00773 int targetIndex = m_group->members().indexOf(targetTask->abstractItem());
00774 int sourceIndex = m_group->members().indexOf(taskItem->abstractItem());
00775 TaskManager::ItemList members;
00776 members.append(targetTask->abstractItem());
00777 members.append(taskItem->abstractItem());
00778
00779 if (m_applet->groupManager().manualGroupingRequest(members)) {
00780 if (sourceIndex < targetIndex) {
00781
00782 targetIndex--;
00783 }
00784
00785
00786 m_applet->groupManager().manualSortingRequest(taskItem->abstractItem()->parentGroup(), targetIndex);
00787
00788 } else {
00789
00790 }
00791 } else if (!targetTask->isWindowItem()) {
00792
00793
00794 m_applet->groupManager().manualGroupingRequest(taskItem->abstractItem(), dynamic_cast<TaskManager::GroupPtr>(targetTask->abstractItem()));
00795 }
00796 } else if (m_applet->groupManager().sortingStrategy() == TaskManager::GroupManager::ManualSorting) {
00797
00798 if (group == m_group) {
00799
00800 layoutTaskItem(taskItem, event->pos());
00801 } else {
00802 AbstractTaskItem *directMember = abstractItem(m_group->directMember(group));
00803 if (directMember) {
00804 layoutTaskItem(directMember, event->pos());
00805 }
00806 }
00807 }
00808 }
00809
00810 void TaskGroupItem::layoutTaskItem(AbstractTaskItem* item, const QPointF &pos)
00811 {
00812 if (!m_expandedLayout) {
00813 return;
00814 }
00815
00816 int insertIndex = m_expandedLayout->insertionIndexAt(pos);
00817
00818 if (insertIndex == -1) {
00819 m_applet->groupManager().manualSortingRequest(item->abstractItem(), -1);
00820 } else {
00821 if (!m_parentSplitGroup) {
00822 m_applet->groupManager().manualSortingRequest(item->abstractItem(), insertIndex);
00823 } else {
00824 m_applet->groupManager().manualSortingRequest(item->abstractItem(), insertIndex +
00825 m_parentSplitGroup->m_groupMembers.size());
00826 }
00827 }
00828 }
00829
00830
00831 void TaskGroupItem::updateActive(AbstractTaskItem *task)
00832 {
00833 if (!m_expandedLayout) {
00834 return;
00835 }
00836
00837 m_activeTaskIndex = indexOf(task);
00838 }
00839
00840 int TaskGroupItem::indexOf(AbstractTaskItem *task)
00841 {
00842 if (!m_group || !task) {
00843
00844 return -1;
00845 }
00846
00847 int index = 0;
00848
00849 foreach (AbstractGroupableItem *item, group()->members()) {
00850 AbstractTaskItem *taskItem = abstractItem(item);
00851 if (taskItem) {
00852 if (task == taskItem) {
00853 TaskGroupItem *groupItem = qobject_cast<TaskGroupItem *>(taskItem);
00854 if (groupItem) {
00855 return index + groupItem->indexOf(groupItem->activeSubTask());
00856 }
00857
00858 return index;
00859 }
00860
00861 TaskGroupItem *groupItem = qobject_cast<TaskGroupItem *>(taskItem);
00862 if (groupItem) {
00863 int subIndex = groupItem->indexOf(task);
00864 if(subIndex == -1) {
00865 index += groupItem->memberList().count();
00866 } else {
00867 return index+subIndex;
00868 }
00869 } else {
00870 index++;
00871 }
00872 }
00873 }
00874 return -1;
00875 }
00876
00877 AbstractTaskItem * TaskGroupItem::activeSubTask()
00878 {
00879 foreach(AbstractGroupableItem *item, group()->members()) {
00880 AbstractTaskItem *taskItem = abstractItem(item);
00881 if (taskItem) {
00882 if(taskItem->isActive()) {
00883 TaskGroupItem *groupItem = qobject_cast<TaskGroupItem *>(taskItem);
00884 if (groupItem) {
00885 return groupItem->activeSubTask();
00886 }
00887 return taskItem;
00888 }
00889 }
00890 }
00891 return NULL;
00892 }
00893
00894 int TaskGroupItem::totalSubTasks()
00895 {
00896 int count = 0;
00897
00898 foreach(AbstractGroupableItem *item, group()->members()) {
00899 AbstractTaskItem *taskItem = abstractItem(item);
00900 if (taskItem) {
00901 TaskGroupItem *groupItem = qobject_cast<TaskGroupItem *>(taskItem);
00902 if (groupItem) {
00903 count += groupItem->memberList().count();
00904 } else {
00905 count++;
00906 }
00907 }
00908 }
00909 return count;
00910 }
00911
00912
00913 AbstractTaskItem * TaskGroupItem::selectSubTask(int index)
00914 {
00915 foreach(AbstractGroupableItem *item, group()->members()) {
00916 AbstractTaskItem *taskItem = abstractItem(item);
00917 if (taskItem) {
00918 TaskGroupItem *groupItem = qobject_cast<TaskGroupItem *>(taskItem);
00919 if (groupItem) {
00920 if (index < groupItem->memberList().count()) {
00921 return groupItem->abstractItem(groupItem->group()->members().at(index));
00922 } else {
00923 index -= groupItem->memberList().count();
00924 }
00925 } else if (index == 0) {
00926 return taskItem;
00927 } else {
00928 --index;
00929 }
00930 }
00931 }
00932 return NULL;
00933 }
00934
00935 void TaskGroupItem::wheelEvent(QGraphicsSceneWheelEvent *event)
00936 {
00937 int subTasks = totalSubTasks();
00938
00939 if (subTasks < 1) {
00940 return;
00941 }
00942
00943
00944 if (event->delta() < 0) {
00945 m_activeTaskIndex++;
00946 if (m_activeTaskIndex >= subTasks) {
00947 m_activeTaskIndex = 0;
00948 }
00949
00950 } else {
00951 m_activeTaskIndex--;
00952 if (m_activeTaskIndex < 0) {
00953 m_activeTaskIndex = subTasks - 1;
00954 }
00955 }
00956
00957
00958 AbstractTaskItem *taskItem = selectSubTask(m_activeTaskIndex);
00959 if (taskItem) {
00960 taskItem->activate();
00961 }
00962 }
00963
00964 int TaskGroupItem::maxRows()
00965 {
00966 return m_maximumRows;
00967 }
00968
00969 void TaskGroupItem::setMaxRows(int rows)
00970 {
00971 m_maximumRows = rows;
00972 if (m_expandedLayout) {
00973 m_expandedLayout->setMaximumRows(m_maximumRows);
00974 }
00975 }
00976
00977 bool TaskGroupItem::forceRows()
00978 {
00979 return m_forceRows;
00980 }
00981
00982 void TaskGroupItem::setForceRows(bool forceRows)
00983 {
00984 m_forceRows = forceRows;
00985 if (m_expandedLayout) {
00986 m_expandedLayout->setForceRows(m_forceRows);
00987 }
00988 }
00989
00990 int TaskGroupItem::optimumCapacity()
00991 {
00992 if (m_expandedLayout) {
00993 return m_expandedLayout->maximumRows() * m_expandedLayout->preferredColumns();
00994 }
00995
00996 return 1;
00997 }
00998
00999 AbstractTaskItem* TaskGroupItem::abstractItem(AbstractItemPtr item)
01000 {
01001 if (m_groupMembers.contains(item)) {
01002 return m_groupMembers.value(item);
01003 }
01004
01005 return 0;
01006 }
01007
01008 void TaskGroupItem::setAdditionalMimeData(QMimeData* mimeData)
01009 {
01010 if (m_group) {
01011 m_group->addMimeData(mimeData);
01012 }
01013 }
01014
01015 void TaskGroupItem::publishIconGeometry() const
01016 {
01017
01018 if (m_expandedLayout || !m_group || m_groupMembers.isEmpty()) {
01019 return;
01020 }
01021
01022 QRect rect = iconGeometry();
01023 publishIconGeometry(rect);
01024 }
01025
01026 void TaskGroupItem::publishIconGeometry(const QRect &rect) const
01027 {
01028 foreach (AbstractTaskItem *item, m_groupMembers) {
01029 WindowTaskItem *windowItem = qobject_cast<WindowTaskItem *>(item);
01030 if (windowItem) {
01031 windowItem->publishIconGeometry(rect);
01032 continue;
01033 }
01034
01035 TaskGroupItem *groupItem = qobject_cast<TaskGroupItem *>(item);
01036 if (groupItem) {
01037 groupItem->publishIconGeometry(rect);
01038 }
01039 }
01040 }
01041
01042 #include "taskgroupitem.moc"
01043