home *** CD-ROM | disk | FTP | other *** search
- /*
- * ActionBack.c - Copyright © 1991 by S.R. & P.C.
- *
- * Created: 21 Apr 1991 16:09:52
- * Modified: 12 Jul 1991 20:43:07
- *
- * Make>> make
- */
-
-
- #include "Global.h"
- #include "FileList.h"
- #include "ActionBack.h"
- #include "Process.h"
- #include "proto/ActionBack.h"
- #include "proto/Process.h"
- #include "proto/Windows.h"
- #include "proto/Mouse.h"
- #include "proto/Scan.h"
- #include "proto/Sort.h"
- #include "proto/Draw.h"
- #include "proto/String.h"
- #include "proto/File.h"
- #include "proto/FileList.h"
-
- extern struct ExecBase *SysBase;
- extern struct MinList WindowList;
- extern struct Config Config;
- extern struct MsgPort *ProcessPort;
-
-
- #define AB_DELETE (AB_DELETE_DEST|AB_DELETE_SOURCE)
-
-
- /* Search by name a ScrollEntry in a window */
-
- static struct ScrollEntry *FindEntry(struct BrowserWindow *Win, char *Name)
- {
- struct ScrollEntry *S;
- short i;
-
- /* No list for main window, only an array */
- if (Win->bw_Type == BW_MAIN) {
- for( i=0 ; i < Win->bw_ShownEntries ; i++ ) {
- S = Win->bw_EntryArray[i];
- if (!Strcmp(S->se_FileInfo.fi_Name, Name))
- return (S->se_State & STATE_DELETED) ? NULL : S;
- }
- }
- else {
- S = (struct ScrollEntry *)Win->bw_EntryList.mlh_Head;
- while(S->se_Node.mln_Succ) {
- if (!Strcmp(S->se_FileInfo.fi_Name, Name))
- return (S->se_State & STATE_DELETED) ? NULL : S;
- S = (struct ScrollEntry *)S->se_Node.mln_Succ;
- }
- }
- return NULL;
- }
-
-
- /* Search by name a ScrollEntry in NewEntryList of a window */
-
- static struct ScrollEntry *FindNewEntry(struct BrowserWindow *Win, char *Name)
- {
- struct ScrollEntry *S;
-
- S = (struct ScrollEntry *)Win->bw_NewEntryList.mlh_Head;
- while(S->se_Node.mln_Succ) {
- if (!Strcmp(S->se_FileInfo.fi_Name, Name))
- return S;
- S = (struct ScrollEntry *)S->se_Node.mln_Succ;
- }
- return NULL;
- }
-
-
- static void ActionBack(struct SuperFileInfo *sfi, BPTR DirLock, short Action)
- {
- struct BrowserWindow *Win;
- struct ScrollEntry *S = NULL;
- struct Point Position;
- BOOL PrintString = FALSE;
- short len;
-
- if (!Action)
- return;
- if (Action & AB_SCANDEVS) {
- ScanDevs();
- return;
- }
- switch(sfi->FileInfo.fi_Type) {
- case DLX_FILE:
- case DLX_DIR:
- Win = FindDir(DirLock);
- break;
- default: /* device, volume, assign */
- Win = (struct BrowserWindow *)WindowList.mlh_Head;
- }
- if (Win) {
- if (Action & AB_NEW_ENTRY) {
- if (S = FindEntry(Win, sfi->FileInfo.fi_Name)) {
- /* size of new entry may be different, so... */
- Win->bw_NumBytes -= S->se_FileInfo.fi_Size;
- Win->bw_NumBlocks -= S->se_FileInfo.fi_NumBlocks;
- Win->bw_NumBytes += sfi->FileInfo.fi_Size;
- Win->bw_NumBlocks += sfi->FileInfo.fi_NumBlocks;
- if (S->se_Print) {
- Win->bw_ShownBytes -= S->se_FileInfo.fi_Size;
- Win->bw_ShownBlocks -= S->se_FileInfo.fi_NumBlocks;
- Win->bw_ShownBytes += sfi->FileInfo.fi_Size;
- Win->bw_ShownBlocks += sfi->FileInfo.fi_NumBlocks;
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- if ((len = strlen(S->se_FileInfo.fi_Name)) > Win->bw_MaxFilenameLen) {
- Win->bw_Flags |= BWF_REBUILD_STRINGS;
- Win->bw_NewMaxFilenameLen = MAX(len, Win->bw_NewMaxFilenameLen);
- }
- else {
- BuildPrintString(Win, S);
- PrintString = TRUE;
- }
- }
- else
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- MakeBottomInfoString(Win);
- RefreshBottomInfo(Win);
- }
- else if (S = FindNewEntry(Win, sfi->FileInfo.fi_Name)) {
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- }
- else if (S = AllocMem(sizeof(struct ScrollEntry), MEMF_PUBLIC|MEMF_CLEAR)) {
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- /* entry can only be a file or dir here, so set pen to 1 or 3 */
- S->se_Pen = (S->se_FileInfo.fi_Type == DLX_FILE) ? 1 : 3;
- AddTail((struct List *)&Win->bw_NewEntryList, (struct Node *)S);
- Win->bw_NumNewEntries++;
- Win->bw_Flags |= BWF_REBUILD_ARRAY;
- if ((len = strlen(S->se_FileInfo.fi_Name)) > Win->bw_MaxFilenameLen) {
- Win->bw_Flags |= BWF_REBUILD_STRINGS;
- Win->bw_NewMaxFilenameLen = MAX(len, Win->bw_NewMaxFilenameLen);
- }
- }
- }
- else if (S = FindEntry(Win, sfi->OldName)) {
- if (Action & AB_DELETE) {
- if (S->se_State & STATE_SELECTED)
- DoSelect(Win, S, OPT_TOGGLESELECT); /* deselect entry */
- S->se_State = STATE_DELETED;
- Win->bw_NumDeleted++;
- Win->bw_Flags |= BWF_REBUILD_ARRAY;
- /* if this file had the longest filename, tell DoUpdateDir() to check if
- * strings could be made smaller */
- if (strlen(sfi->OldName) == Win->bw_MaxFilenameLen)
- Win->bw_Flags |= BWF_CHECK_MAXLEN;
- PrintString = TRUE;
- }
- if (S->se_State & STATE_GHOSTED) { /* change state only if ghosted */
- S->se_State &= ~STATE_GHOSTED;
- if (S->se_Print) {
- if (Action & AB_SELECT)
- DoSelect(Win, S, 0);
- PrintString = TRUE;
- }
- }
- if (S->se_Print) {
- if (Action & AB_UPDATE_STRING) {
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- BuildPrintString(Win, S);
- PrintString = TRUE;
- }
- if (Action & AB_RENAME_ENTRY) {
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- Win->bw_Flags |= BWF_SORT;
- if ((len = strlen(S->se_FileInfo.fi_Name)) > Win->bw_MaxFilenameLen) {
- Win->bw_Flags |= BWF_REBUILD_STRINGS;
- Win->bw_NewMaxFilenameLen = MAX(len, Win->bw_NewMaxFilenameLen);
- }
- else {
- /* if this file had the longest filename, tell DoUpdateDir() to check if
- * strings could be made smaller */
- if (strlen(sfi->OldName) == Win->bw_MaxFilenameLen && len <Win->bw_MaxFilenameLen)
- Win->bw_Flags |= BWF_CHECK_MAXLEN;
- BuildPrintString(Win, S);
- PrintString = TRUE;
- }
- }
- /* Modified entry may no more pass through filters so check it */
- if (!MatchFilters(&S->se_FileInfo, &Win->bw_FiltersInfo))
- Win->bw_Flags |= BWF_REBUILD_ARRAY|BWF_REBUILD_STRINGS;
- }
- }
- else if (S = FindNewEntry(Win, sfi->OldName)) {
- if (Action & AB_DELETE) {
- Remove((struct Node *)S);
- Win->bw_NumNewEntries--;
- }
- else
- CopyFileInfo(&S->se_FileInfo, &sfi->FileInfo);
- }
- if (PrintString && GetSePosition(Win, S, &Position))
- Print(Win, S, Position.X, Position.Y);
- }
- }
-
-
- void DoActionBack(struct SuperFileInfo *sfi, BPTR SrcDir, BPTR DestDir)
- {
- if (sfi->ActionBack == AB_NONE)
- return;
- if (DestDir)
- ActionBack(sfi, DestDir, sfi->ActionBack & AB_DEST_FLAGS);
- /* Don't check SrcDir, it may be the main window */
- ActionBack(sfi, SrcDir, sfi->ActionBack & AB_SOURCE_FLAGS);
- }
-
-
- void SendActionBack(struct SuperFileInfo *sfi, BPTR SrcDir, BPTR DestDir)
- {
- struct TaskData *TaskData;
- struct BrowserMsg *Msg;
-
- if (sfi->ActionBack == AB_NONE)
- return;
- if (Config.Options & OPT_ASYNCHRONOUS) {
- TaskData = (struct TaskData *)SysBase->ThisTask->tc_UserData;
- FreeProcessRepliedMsg(TaskData);
- if (!(Msg = AllocBrowserMsg()))
- return;
- Msg->bm_ExecMessage.mn_ReplyPort = TaskData->td_ReplyPort;
- Msg->bm_Type = BM_ACTIONBACK;
- Msg->bm_Info.ActionBack.SrcDir = SrcDir;
- Msg->bm_Info.ActionBack.DestDir = DestDir;
- /* Copy SuperFileInfo */
- Msg->bm_Info.ActionBack.sfi = *sfi;
- if (sfi->FileInfo.fi_Comment)
- Msg->bm_Info.ActionBack.sfi.FileInfo.fi_Comment = CopyStr(sfi->FileInfo.fi_Comment);
- PutMsg(ProcessPort, (struct Message *)Msg);
- TaskData->td_MsgCount++;
- }
- else
- DoActionBack(sfi, SrcDir, DestDir);
- sfi->ActionBack = AB_NONE;
- }
-
-
- void DoUpdateDir(BPTR Dir)
- {
- struct BrowserWindow *Win;
- struct ScrollEntry *S, *Next;
- short len=0, i;
- BOOL Ok = TRUE;
- UBYTE Flags;
-
- if (Win = FindDir(Dir)) {
- if (Flags = Win->bw_Flags) {
- /* if strings have to be rebuilt, they must be longer, so don't check if
- * they can be made smaller !! */
- if ((Flags & BWF_CHECK_MAXLEN) && !(Flags & BWF_REBUILD_STRINGS)) {
- for( i=0 ; i<Win->bw_ShownEntries ; i++ ) {
- S = Win->bw_EntryArray[i];
- if (!(S->se_State & STATE_DELETED))
- len = MAX(len, strlen(S->se_FileInfo.fi_Name));
- }
- if (len < Win->bw_MaxFilenameLen) {
- Win->bw_MaxFilenameLen = len;
- Flags |= BWF_REBUILD_STRINGS;
- }
- }
- if ((Flags & BWF_SORT) && !(Flags & BWF_REBUILD_ARRAY) && (Win->bw_Sort & 0x0F) == NAME_SORT)
- Sort(Win);
- if ((Flags & BWF_REBUILD_STRINGS) && !(Flags & BWF_REBUILD_ARRAY)) {
- Ok = BuildPrintStrings(Win);
- }
- else if ((Flags & BWF_REBUILD_ARRAY) && !(Flags & BWF_REBUILD_STRINGS)) {
- if (Ok = UpdateEntryList(Win, TRUE)) {
- Win->bw_ShownFiles = Win->bw_ShownDirs = Win->bw_ShownEntries = 0;
- Win->bw_ShownBytes = Win->bw_ShownBlocks = 0;
- S = (struct ScrollEntry *)Win->bw_EntryList.mlh_Head;
- i = 0;
- while(Next = (struct ScrollEntry *)S->se_Node.mln_Succ) {
- if (S->se_Print) {
- Win->bw_EntryArray[i++] = S;
- if (S->se_FileInfo.fi_Type == DLX_FILE)
- Win->bw_ShownFiles++;
- else
- Win->bw_ShownDirs++;
- Win->bw_ShownBytes += S->se_FileInfo.fi_Size;
- Win->bw_ShownBlocks += S->se_FileInfo.fi_NumBlocks;
- }
- S = Next;
- }
- Win->bw_ShownEntries = i;
- Sort(Win);
- MakeBottomInfoString(Win);
- }
- }
- else { /* both flags BWF_REBUILD_ARRAY and BWF_REBUILD_STRINGS are set */
- if (Ok = List2Array(Win))
- MakeBottomInfoString(Win);
- }
- Win->bw_Flags = 0;
- if (Ok)
- RefreshWindow(Win);
- else
- CloseBrowserWindow(Win);
- }
- else { /* some entries may have been reselected, so update bottom info */
- MakeBottomInfoString(Win);
- RefreshBottomInfo(Win);
- }
- }
- }
-
-
- void SendUpdateDir(BPTR Dir)
- {
- struct TaskData *TaskData;
- struct BrowserMsg *Msg;
-
- if (!Dir)
- return;
- if (Config.Options & OPT_ASYNCHRONOUS) {
- TaskData = (struct TaskData *)SysBase->ThisTask->tc_UserData;
- if (!(Msg = AllocBrowserMsg()))
- return;
- Msg->bm_ExecMessage.mn_ReplyPort = TaskData->td_ReplyPort;
- Msg->bm_Type = BM_UPDATEDIR;
- Msg->bm_Info.Dir = Dir;
- PutMsg(ProcessPort, (struct Message *)Msg);
- TaskData->td_MsgCount++;
- /* Wait for all pending messages before unlocking Dir, or locks given to
- * actionback messages won't be valid anymore */
- WaitAllMsg(TaskData);
- }
- else
- DoUpdateDir(Dir);
- }
-
-
-