Tracker: Fix pose locations when moving/copying to a folder

... in different view mode or icon size. Fixes #19698.

Change-Id: I386fc5acc0f97c24d6554c5220aebf20d58cbd83
Reviewed-on: https://review.haiku-os.org/c/haiku/+/10863
Tested-by: Commit checker robot <[email protected]>
Reviewed-by: John Scipione <[email protected]>
Haiku-Format: Haiku-format Bot <[email protected]>
This commit is contained in:
John Scipione
2026-05-04 00:59:04 +00:00
parent 706fc8e3c6
commit 4856376f00
2 changed files with 51 additions and 39 deletions
+50 -38
View File
@@ -5043,17 +5043,20 @@ BPoseView::MoveSelectionInto(Model* destFolder, BContainerWindow* srcWindow,
BContainerWindow* destWindow, uint32 buttons, BPoint dropPoint, bool forceCopy, BContainerWindow* destWindow, uint32 buttons, BPoint dropPoint, bool forceCopy,
bool forceMove, bool createLink, bool createRelativeLink, BPoint dragStart, bool pinToGrid) bool forceMove, bool createLink, bool createRelativeLink, BPoint dragStart, bool pinToGrid)
{ {
ASSERT(srcWindow != NULL);
ASSERT(srcWindow->PoseView() != NULL);
ASSERT(srcWindow->PoseView()->TargetModel() != NULL);
AutoLock<BWindow> lock(srcWindow); AutoLock<BWindow> lock(srcWindow);
if (!lock) if (!lock)
return; return;
ASSERT(srcWindow->PoseView()->TargetModel() != NULL); BPoseView* sourceView = srcWindow->PoseView();
if (sourceView->CountSelected() == 0)
if (srcWindow->PoseView()->CountSelected() == 0)
return; return;
if (destWindow != NULL && SecondaryMouseButtonDown(modifiers(), buttons)) { if (destWindow != NULL && SecondaryMouseButtonDown(modifiers(), buttons)) {
BPoseView* poseView = (srcWindow != NULL ? srcWindow->PoseView() : NULL); BPoseView* poseView = (srcWindow != NULL ? sourceView : NULL);
switch (destWindow->ShowDropContextMenu(dropPoint, poseView)) { switch (destWindow->ShowDropContextMenu(dropPoint, poseView)) {
case kCreateRelativeLink: case kCreateRelativeLink:
createRelativeLink = true; createRelativeLink = true;
@@ -5078,44 +5081,43 @@ BPoseView::MoveSelectionInto(Model* destFolder, BContainerWindow* srcWindow,
} }
} }
// make sure source and destination folders are different // same folder and not creating a link
if (*srcWindow->PoseView()->TargetModel()->NodeRef() == *destFolder->NodeRef() if (*sourceView->TargetModel()->NodeRef() == *destFolder->NodeRef()
&& !(createLink || createRelativeLink)) { && !(createLink || createRelativeLink)) {
BPoseView* targetView = srcWindow->PoseView();
if (forceCopy) { if (forceCopy) {
targetView->DuplicateSelection(&dragStart, &dropPoint); sourceView->DuplicateSelection(&dragStart, &dropPoint);
return; return;
} }
if (targetView->ViewMode() == kListMode) { if (sourceView->ViewMode() == kListMode) {
// can't move in list view // can't move in list view
return; return;
} }
BPoint delta = dropPoint - dragStart; BPoint delta = dropPoint - dragStart;
int32 selectCount = targetView->CountSelected(); int32 selectCount = sourceView->CountSelected();
for (int32 index = 0; index < selectCount; index++) { for (int32 index = 0; index < selectCount; index++) {
BPose* pose = targetView->SelectionList()->ItemAt(index); BPose* pose = sourceView->SelectionList()->ItemAt(index);
// remove pose from VSlist before changing location // remove pose from VSlist before changing location
// so that we "find" the correct pose to remove // so that we "find" the correct pose to remove
// need to do this because bsearch uses top of pose // need to do this because bsearch uses top of pose
// to locate pose to remove // to locate pose to remove
targetView->RemoveFromVSList(pose); sourceView->RemoveFromVSList(pose);
BPoint loc(pose->Location(targetView) + delta); BPoint loc(pose->Location(sourceView) + delta);
BRect oldBounds(pose->CalcRect(targetView)); BRect oldBounds(pose->CalcRect(sourceView));
if (pinToGrid) if (pinToGrid)
loc = targetView->PinToGrid(loc, targetView->fGrid, targetView->fOffset); loc = sourceView->PinToGrid(loc, sourceView->fGrid, sourceView->fOffset);
// TODO: don't drop poses under desktop elements // TODO: don't drop poses under desktop elements
// ie: replicants, deskbar // ie: replicants, deskbar
pose->MoveTo(loc, targetView); pose->MoveTo(loc, sourceView);
targetView->RemoveFromExtent(oldBounds); sourceView->RemoveFromExtent(oldBounds);
targetView->AddToExtent(pose->CalcRect(targetView)); sourceView->AddToExtent(pose->CalcRect(sourceView));
// remove and reinsert pose to keep VSlist sorted // remove and reinsert pose to keep VSlist sorted
targetView->AddToVSList(pose); sourceView->AddToVSList(pose);
} }
return; return;
@@ -5175,7 +5177,7 @@ BPoseView::MoveSelectionInto(Model* destFolder, BContainerWindow* srcWindow,
if (okToMove) { if (okToMove) {
PoseList* selectionList = srcWindow->PoseView()->SelectionList(); PoseList* selectionList = srcWindow->PoseView()->SelectionList();
BList* pointList = destWindow->PoseView()->GetDropPointList(dragStart, dropPoint, BList* pointList = destWindow->PoseView()->GetDropPointList(dragStart, dropPoint,
selectionList, srcWindow->PoseView()->ViewMode() == kListMode, pinToGrid); selectionList, srcWindow->PoseView(), pinToGrid);
int32 selectionSize = srcWindow->PoseView()->CountSelected(); int32 selectionSize = srcWindow->PoseView()->CountSelected();
BObjectList<entry_ref, true>* srcList = new BObjectList<entry_ref, true>(selectionSize); BObjectList<entry_ref, true>* srcList = new BObjectList<entry_ref, true>(selectionSize);
@@ -6099,24 +6101,36 @@ BPoseView::ConvertZombieToPose(Model* zombie, int32 index)
BList* BList*
BPoseView::GetDropPointList(BPoint dropStart, BPoint dropEnd, const PoseList* poses, BPoseView::GetDropPointList(BPoint dropStart, BPoint dropEnd, const PoseList* poseList,
bool sourceInListMode, bool pinToGrid) const BPoseView* sourcePoseView, bool pinToGrid) const
{ {
if (ViewMode() == kListMode) ASSERT(poseList != NULL);
return NULL; ASSERT(sourcePoseView != NULL);
int32 poseCount = poses->CountItems(); int32 poseCount = poseList->CountItems();
BList* pointList = new BList(poseCount); BList* pointList = new BList(poseCount);
for (int32 index = 0; index < poseCount; index++) { for (int32 index = 0; index < poseCount; index++) {
BPose* pose = poses->ItemAt(index); BPose* pose = poseList->ItemAt(index);
BPoint poseLoc; if (pose == NULL)
if (sourceInListMode) break;
poseLoc = dropEnd + BPoint(0, index * (IconPoseHeight() + 3));
else
poseLoc = dropEnd + (pose->Location(this) - dropStart);
if (pinToGrid) BPoint poseLoc;
poseLoc = PinToGrid(poseLoc, fGrid, fOffset); if (ViewMode() == kListMode) {
// drop poses at the end of the list
poseLoc = dropEnd + BPoint(0, index * fListElemHeight);
} else {
if (pose->HasLocation()) {
// copy the source location
poseLoc = dropEnd + (pose->Location(sourcePoseView) - dropStart);
} else {
// no source location, auto-place the pose in the destination
BRect destViewBounds(Bounds());
const_cast<BPoseView*>(this)->PlacePose(pose, destViewBounds);
poseLoc = dropEnd + (pose->Location(this) - dropStart);
}
if (pinToGrid)
poseLoc = PinToGrid(poseLoc, fGrid, fOffset);
}
pointList->AddItem(new BPoint(poseLoc)); pointList->AddItem(new BPoint(poseLoc));
} }
@@ -6155,13 +6169,11 @@ BPoseView::DuplicateSelection(BPoint* dropStart, BPoint* dropEnd)
BObjectList<entry_ref, true>* srcList = new BObjectList<entry_ref, true>(CountSelected()); BObjectList<entry_ref, true>* srcList = new BObjectList<entry_ref, true>(CountSelected());
CopySelectionListToEntryRefList(fSelectionList, srcList); CopySelectionListToEntryRefList(fSelectionList, srcList);
BList* dropPoints; BList* dropPoints = NULL;
if (dropStart) { if (dropStart) {
bool pinToGrid = (modifiers() & B_COMMAND_KEY) != 0; bool pinToGrid = (modifiers() & B_COMMAND_KEY) != 0;
dropPoints = GetDropPointList(*dropStart, *dropEnd, fSelectionList, dropPoints = GetDropPointList(*dropStart, *dropEnd, fSelectionList, this, pinToGrid);
ViewMode() == kListMode, pinToGrid); }
} else
dropPoints = NULL;
// perform asynchronous duplicate // perform asynchronous duplicate
FSDuplicate(srcList, dropPoints); FSDuplicate(srcList, dropPoints);
+1 -1
View File
@@ -660,7 +660,7 @@ protected:
// misc // misc
BList* GetDropPointList(BPoint dropPoint, BPoint startPoint, BList* GetDropPointList(BPoint dropPoint, BPoint startPoint,
const PoseList*, bool sourceInListMode, bool pinToGrid) const; const PoseList*, BPoseView*, bool pinToGrid) const;
void SendSelectionAsRefs(uint32 what, bool onlyQueries = false); void SendSelectionAsRefs(uint32 what, bool onlyQueries = false);
void MoveListToTrash(BObjectList<entry_ref, true>*, bool selectNext, void MoveListToTrash(BObjectList<entry_ref, true>*, bool selectNext,
bool deleteDirectly); bool deleteDirectly);