xref: /haiku/src/apps/mediaplayer/playlist/CopyPLItemsCommand.cpp (revision 2222d0559df303a9846a2fad53741f8b20b14d7c)
1 /*
2  * Copyright © 2007-2009 Stephan Aßmus <superstippi@gmx.de>.
3  * All rights reserved. Distributed under the terms of the MIT License.
4  */
5 #include "CopyPLItemsCommand.h"
6 
7 #include <new>
8 #include <stdio.h>
9 
10 #include <Autolock.h>
11 
12 #include "Playlist.h"
13 
14 
15 using std::nothrow;
16 
17 
18 CopyPLItemsCommand::CopyPLItemsCommand(Playlist* playlist,
19 		 const int32* indices, int32 count, int32 toIndex)
20 	:
21 	PLItemsCommand(),
22 	fPlaylist(playlist),
23 	fItems(count > 0 ? new (nothrow) PlaylistItem*[count] : NULL),
24 	fToIndex(toIndex),
25 	fCount(count),
26 	fItemsCopied(false)
27 {
28 	if (!indices || !fPlaylist || !fItems) {
29 		// indicate a bad object state
30 		delete[] fItems;
31 		fItems = NULL;
32 		return;
33 	}
34 
35 	memset(fItems, 0, sizeof(PlaylistItem*) * fCount);
36 
37 	// init original entries and
38 	for (int32 i = 0; i < fCount; i++) {
39 		PlaylistItem* item = fPlaylist->ItemAt(indices[i]);
40 		if (item != NULL)
41 			fItems[i] = item->Clone();
42 		if (fItems[i] == NULL) {
43 			// indicate a bad object state
44 			_CleanUp(fItems, fCount, true);
45 			return;
46 		}
47 	}
48 }
49 
50 
51 CopyPLItemsCommand::~CopyPLItemsCommand()
52 {
53 	_CleanUp(fItems, fCount, !fItemsCopied);
54 }
55 
56 
57 status_t
58 CopyPLItemsCommand::InitCheck()
59 {
60 	if (!fPlaylist || !fItems)
61 		return B_NO_INIT;
62 	return B_OK;
63 }
64 
65 
66 status_t
67 CopyPLItemsCommand::Perform()
68 {
69 	BAutolock _(fPlaylist);
70 
71 	status_t ret = B_OK;
72 
73 	fItemsCopied = true;
74 
75 	// add refs to playlist at the insertion index
76 	int32 index = fToIndex;
77 	for (int32 i = 0; i < fCount; i++) {
78 		if (!fPlaylist->AddItem(fItems[i], index++)) {
79 			ret = B_NO_MEMORY;
80 			break;
81 		}
82 	}
83 	return ret;
84 }
85 
86 
87 status_t
88 CopyPLItemsCommand::Undo()
89 {
90 	BAutolock _(fPlaylist);
91 
92 	fItemsCopied = false;
93 	// remember currently playling item in case we copy items over it
94 	PlaylistItem* current = fPlaylist->ItemAt(fPlaylist->CurrentItemIndex());
95 
96 	// remove refs from playlist
97 	int32 index = fToIndex;
98 	for (int32 i = 0; i < fCount; i++) {
99 		fPlaylist->RemoveItem(index++, false);
100 	}
101 
102 	// take care about currently played item
103 	if (current != NULL)
104 		fPlaylist->SetCurrentItemIndex(fPlaylist->IndexOf(current));
105 
106 	return B_OK;
107 }
108 
109 
110 void
111 CopyPLItemsCommand::GetName(BString& name)
112 {
113 	if (fCount > 1)
114 		name << "Copy Entries";
115 	else
116 		name << "Copy Entry";
117 }
118