⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 filebrowserform.c

📁 palm编程
💻 C
📖 第 1 页 / 共 2 页
字号:
	Char *fileName2 = (Char*)MemPtrNew(MAX_FILENAME_LENGTH);
	
	fileInfo.nameP = fileName;
	fileInfo.nameBufLen = MAX_FILENAME_LENGTH;
	
	// Clean the database
	PrvEmptyDB();
	
	// If not the root, add UP directory
	if( StrCompare( "/", gCurrentPath) )
	{
		StrCopy( fileName, "..");
		fileInfo.attributes = vfsFileAttrDirectory;
		PrvAddRecord(&fileInfo, 0);
	}
	
	// Open at the current volume and path	
	err = VFSFileOpen(gCurrentVolume, gCurrentPath, vfsModeRead, &dirRef);
	if( err == errNone )
	{	
		fileIterator = vfsIteratorStart;
		while( fileIterator != vfsIteratorStop )
		{		
			err = VFSDirEntryEnumerate(dirRef, &fileIterator, &fileInfo);
			if( err == errNone )
			{
				if( ! (fileInfo.attributes & UNWANTED_FILES) )
				{
					if( fileInfo.attributes & vfsFileAttrDirectory ) {
						PrvAddRecord(&fileInfo, 0);
					} else {
						StrCopy(fileName2, gCurrentPath);
						StrCat(fileName2, fileInfo.nameP);
						err = VFSFileOpen(gCurrentVolume, fileName2, vfsModeRead, &fileRef);
						err = VFSFileSize(fileRef, &fileSize);
						PrvAddRecord(&fileInfo, fileSize);
						err = VFSFileClose(fileRef);
					}
				}
			}
		}
		
		VFSFileClose( dirRef );
	}
	
	MemPtrFree(fileName);
	MemPtrFree(fileName2);
	
	
	gFileCount = DmNumRecords(gDB);
	
	PrvDBSort();
	
	return err;
}

/***********************************************************************
 *
 * FUNCTION:    PrvDrawTableBorder
 *
 * DESCRIPTION: 
 *
 * PARAMETERS:  
 *
 * RETURNED:    N/A
 *
 ***********************************************************************/

static void PrvDrawTableBorder(FormType *frmP)
{
	RectangleType bounds;
	TablePtr tableP = FrmGetObjectPtr(frmP, FrmGetObjectIndex(frmP, FileBrowserFileTable));

	TblGetBounds(tableP, &bounds);
	WinDrawRectangleFrame(menuFrame, &bounds);
}

#pragma mark ---------- File Browser DB Functions ----------

/***********************************************************************
 *
 * FUNCTION:    FileBrowserDeleteDB
 *
 * DESCRIPTION: This routine should be called when the app stops.
 *				It deletes the temporary database.
 *
 * PARAMETERS:  None.
 *
 * RETURNED:    Error Code.
 *
 ***********************************************************************/

Err FileBrowserDeleteDB()
{
	LocalID dbID;
	UInt16 cardNo;

	Err err = errNone;
	
	if(!gDB)
	{
		// Open the database
		dbID = DmFindDatabase(fbCardNumber, fbDBName);
		if( dbID )
		{
			// If exists open it
			gDB = DmOpenDatabase(fbCardNumber, dbID, dmModeReadWrite);
			if(!gDB) {
				err = DmGetLastErr();
				return err;
			}
		}
		else
			return err;
	}
	
	err = DmOpenDatabaseInfo(gDB, &dbID, 0, 0, &cardNo, 0);
	err = DmCloseDatabase(gDB);
	err = DmDeleteDatabase(cardNo, dbID);		
	
	return err;
}

/***********************************************************************
 *
 * FUNCTION:    PrvEmptyDB
 *
 * DESCRIPTION: This routine deletes all the records of the temp database.
 *
 * PARAMETERS:  None.
 *
 * RETURNED:    Error Code.
 *
 ***********************************************************************/

static Err PrvEmptyDB()
{
	Err err = errNone;
	UInt16 index = DmNumRecords(gDB);
	
	while (index--)
	{
		err = DmRemoveRecord(gDB, index);
	}
	
	return err;
}

/***********************************************************************
 *
 * FUNCTION:    PrvAddRecord
 *
 * DESCRIPTION: This routine adds a record to the temp database
 *
 * PARAMETERS:  fileInfoP 		- Pointer to a FileInfo Structure
 *
 * RETURNED:    Error Code
 *
 ***********************************************************************/

static Err PrvAddRecord(FileInfoType* fileInfoP, UInt32 fileSize)
{

	Err			err = errNone;
	void*		memLockP = NULL;
	MemHandle	recordHandle = NULL;
	UInt32		recordSize = 0;
	UInt16		recordIndex = dmMaxRecordIndex;
	UInt32		offset = 0;
	FileBrowserFileInfo fbFileInfo;
	
	// Local store
	fbFileInfo.selected = false;
	fbFileInfo.attribute = fileInfoP->attributes;
	fbFileInfo.fileName = fileInfoP->nameP;
	fbFileInfo.fileSize = fileSize;

	recordSize = (StrLen(fbFileInfo.fileName)+1);

	recordHandle = DmNewRecord(gDB, &recordIndex, recordSize + sizeof(UInt32) + sizeof(UInt16) + sizeof(Boolean));
	if( !recordHandle )
	{
		err = DmGetLastErr();
		return err;
	}
	
	memLockP = MemHandleLock(recordHandle);
	
	// Write selection
	offset = 0;
	err = DmWrite( memLockP, offset, &fbFileInfo.selected, sizeof(Boolean));
	if(err) goto Done;
	
	offset += sizeof(Boolean);
	err = DmWrite( memLockP, offset, &fbFileInfo.attribute, sizeof(UInt16));
	if(err) goto Done;
	
	offset += sizeof(UInt16);
	err = DmWrite( memLockP, offset, &fbFileInfo.fileSize, sizeof(UInt32));
	if(err) goto Done;
	
	offset += sizeof(UInt32);
	err = DmWrite( memLockP, offset, fbFileInfo.fileName, recordSize);
	if(err) goto Done;

Done:	
	MemHandleUnlock(recordHandle);
	err = DmReleaseRecord(gDB, recordIndex, true);
	
	if( err )
	{
		DmRemoveRecord(gDB, recordIndex);
	}
	
	return err;
}

/***********************************************************************
 *
 * FUNCTION:    PrvGetRecord
 *
 * DESCRIPTION: This routine returns the file info for the given index
 *
 * PARAMETERS:  index		- File index in the database
 *				fileInfoP	- File info Ptr
 *
 * RETURNED:    
 *
 ***********************************************************************/

static Err PrvGetRecord(UInt16 index, FileBrowserFileInfo* fileInfoP, MemHandle* hP)
{
	Err err = errNone;
	UInt8 *recP = NULL;
	
	*hP = DmQueryRecord(gDB, index);
	if (hP == NULL)
	{
		err = DmGetLastErr();
		goto Done;
	}
	
	recP = (UInt8 *)MemHandleLock(*hP);
	if (recP == NULL)
	{
		err = memErrChunkNotLocked;
		goto Done;
	}
	
	fileInfoP->selected = (Boolean)*recP;
	recP += sizeof(Boolean);
	fileInfoP->attribute = MisalignedReadBEUInt16(recP, 0);
	recP += sizeof(UInt16);
	fileInfoP->fileSize = MisalignedReadBEUInt32(recP, 0);
	recP += sizeof(UInt32);
	fileInfoP->fileName = (Char*)recP;
	
Done:
	return err;
}

/***********************************************************************
 *
 * FUNCTION:    PrvReleaseRecord
 *
 * DESCRIPTION: 
 *
 * PARAMETERS:  
 *
 * RETURNED:    
 *
 ***********************************************************************/
 
static void PrvReleaseRecord(UInt16 index, MemHandle h)
{
	MemHandleUnlock(h);
}

/***********************************************************************
 *
 * FUNCTION:    
 *
 * DESCRIPTION: 
 *
 * PARAMETERS:  
 *
 * RETURNED:    
 *
 ***********************************************************************/

static Int16 PrvDBCompareRecords( Char* r1P, Char* r2P, 
	Int16 UNUSED_PARAM(param), SortRecordInfoType* UNUSED_PARAM(info1), 
	SortRecordInfoType* UNUSED_PARAM(info2), MemHandle UNUSED_PARAM(appInfoH))
{
	Int16 result;
	FileBrowserFileInfo rec1, rec2;
	
	rec1.selected = (Boolean)*r1P;
	r1P += sizeof(Boolean);
	rec1.attribute = MisalignedReadBEUInt16(r1P, 0);
	r1P += sizeof(UInt16) + sizeof(UInt32);
	rec1.fileName = (Char*)r1P;
	
	rec2.selected = (Boolean)*r2P;
	r2P += sizeof(Boolean);
	rec2.attribute = MisalignedReadBEUInt16(r2P, 0);
	r2P += sizeof(UInt16) + sizeof(UInt32);
	rec2.fileName = (Char*)r2P;


	// First check to display the folder first
	if (rec1.attribute & vfsFileAttrDirectory)
	{
		if (!(rec2.attribute & vfsFileAttrDirectory))
			return -1;
	}
	else if (rec2.attribute & vfsFileAttrDirectory)
			return 1;
			
	// Alphabetize;
	result = TxtCompare(	rec1.fileName,	// const Char *s1
							0xFFFF,			// UInt16 s1Len,
							NULL,			// UInt16 *s1MatchLen,
							rec2.fileName,	// const Char *s2,
							0xFFFF,			// UInt16 s2Len,
							NULL);			// UInt16 *s2MatchLen
	return result;
}
/************************************************************
 *
 * FUNCTION:
 *
 * DESCRIPTION:
 *
 * PARAMETERS:
 * 
 * RETURNS:
 *
 *************************************************************/
 
static void PrvDBSort()
{
	DmInsertionSort(gDB, (DmComparF *)&PrvDBCompareRecords, 0);
}

#pragma mark ---------- File Browser List View ----------

/***********************************************************************
 *
 * FUNCTION:    PrvListViewInit
 *
 * DESCRIPTION: This routine initializes the table
 *
 * PARAMETERS:  frmP 		- Pointer to a form
 *
 * RETURNED:    N/A
 *
 ***********************************************************************/

static void PrvListViewInit(FormType *frmP)
{
	UInt16 rowCount;
	TablePtr tableP = FrmGetObjectPtr(frmP, FrmGetObjectIndex(frmP, FileBrowserFileTable));
	
	gRowCount = rowCount = TblGetNumberOfRows(tableP);
	
	// Init the row elements
	while( rowCount-- )
	{
		TblSetRowUsable(tableP, rowCount, false);
		TblSetItemStyle(tableP, rowCount, FILE_COLUMN, customTableItem);
	}
	
	TblHasScrollBar(tableP, true);
	TblSetColumnUsable(tableP, FILE_COLUMN, true);
	TblSetCustomDrawProcedure(tableP, FILE_COLUMN, PrvListViewDrawFile);
	
	// Load the table
	PrvListViewLoadTable(frmP, false);
}

/***********************************************************************
 *
 * FUNCTION:    PrvListViewDrawFile
 *
 * DESCRIPTION: This routine draws a file in the table
 *
 * PARAMETERS:  tableP 		- Pointer to the table
 *				row			- The row to draw
 *				column		- The column to draw
 *				boundsP		- Pointer to the element bound
 *
 * RETURNED:    N/A
 *
 ***********************************************************************/

static void PrvListViewDrawFile(void *tableP, Int16 row, Int16 column, RectangleType *boundsP)
{
	UInt16 index;
	MemHandle h;
	FileBrowserFileInfo fileInfo;
	WinHandle winH;
	Char * ptr;
	UInt16 titleLen;
	Char text[32];
	UInt32 fileSizeWidth = 0;
	Err err = errNone;
	
	index = TblGetRowID(tableP, row);
	
	err = PrvGetRecord( index, &fileInfo, &h);
	if( err ) goto Done;
	
	// Draw icon
	ptr = StrChr (fileInfo.fileName, linefeedChr);
	titleLen = (ptr == NULL ? StrLen (fileInfo.fileName) : (UInt16) (ptr - fileInfo.fileName));
	
	if( fileInfo.attribute & vfsFileAttrDirectory )
	{
		RectangleType rct;
		
		winH = gFolderWinH;
				
		WinGetWindowFrameRect(winH, &rct);			
		WinCopyRectangle(winH, 0, &rct, boundsP->topLeft.x, boundsP->topLeft.y + 1, winPaint);
	}
	else
	{
		RectangleType rct;
		
		winH = gDocumentWinH;
				
		WinGetWindowFrameRect(winH, &rct);			
		WinCopyRectangle(winH, 0, &rct, boundsP->topLeft.x, boundsP->topLeft.y + 1, winPaint);

	}
	
	if( !(fileInfo.attribute & vfsFileAttrDirectory) )
	{
		// Display the file size
		if(fileInfo.fileSize > 1048576)
		{
			// Use the KB style (123.4 MB)
			UInt32 mantissa = fileInfo.fileSize / 1048576;
			UInt32 fraction = ( fileInfo.fileSize - mantissa * 1048576 ) / 104858;
			
			StrPrintF(text, "%ld.%ld M", mantissa, fraction);			
		}
		else if(fileInfo.fileSize > 1024)
		{
			// Use the KB style (123.4 KB)
			UInt32 mantissa = fileInfo.fileSize / 1024;
			UInt32 fraction = ( fileInfo.fileSize - mantissa * 1024 ) / 103;
			
			StrPrintF(text, "%ld.%ld K", mantissa, fraction);
		}
		else
		{
			// Use the B style (24 B)
			StrPrintF(text, "%ld B", fileInfo.fileSize);
		}
	
		// Get the length
		fileSizeWidth = FntCharsWidth(text, StrLen(text));
		WinDrawChars(text, StrLen(text), boundsP->topLeft.x + boundsP->extent.x - fileSizeWidth, boundsP->topLeft.y);
		fileSizeWidth + 4; // Give me some space
	}
	
	// Draw File Name
	if( FntWidthToOffset (fileInfo.fileName, titleLen, boundsP->extent.x - 15 - fileSizeWidth, NULL, NULL) == titleLen)
	{
		WinDrawChars (fileInfo.fileName, titleLen, boundsP->topLeft.x + 15, boundsP->topLeft.y);
	}
	else
	{
		Int16 titleWidth;
		titleLen = FntWidthToOffset (fileInfo.fileName, titleLen, boundsP->extent.x - 15 - fileSizeWidth - FntCharWidth (chrEllipsis), NULL, &titleWidth);
		WinDrawChars (fileInfo.fileName, titleLen, boundsP->topLeft.x + 15, boundsP->topLeft.y);
		WinDrawChar (chrEllipsis, boundsP->topLeft.x + 15 + titleWidth, boundsP->topLeft.y);
	}
	
	// Release the record
	PrvReleaseRecord(index, h);
	
Done:
	return;
}

/***********************************************************************
 *
 * FUNCTION:    PrvListViewLoadTable
 *
 * DESCRIPTION: This routine loads the table.
 *
 * PARAMETERS:  frmP		- Pointer to a form.
 *
 * RETURNED:    N/A
 *
 ***********************************************************************/

static void PrvListViewLoadTable(FormType *frmP, Boolean redraw)
{
	UInt16 row;
	UInt16 rowCount;
	UInt16 displayCount;
	TablePtr tableP = FrmGetObjectPtr(frmP, FrmGetObjectIndex(frmP, FileBrowserFileTable));
	ScrollBarPtr barP = FrmGetObjectPtr(frmP, FrmGetObjectIndex(frmP, FileBrowserFileScrollBar));
	
	rowCount = TblGetNumberOfRows(tableP);
	displayCount = gFileCount - gTopIndex;
	
	for(row = 0; row < gRowCount; row++)
	{
		if( row < displayCount )
		{
			TblSetRowID(tableP, row, row + gTopIndex);
			TblSetRowUsable(tableP, row, true);
			TblSetRowSelectable(tableP, row, true);
		}
		else
		{
			TblSetRowUsable(tableP, row, false);
			TblSetRowSelectable(tableP, row, false);
		}
	}
	
	if( redraw )
	{
		TblEraseTable(tableP);
		TblDrawTable(tableP);
	}
	
	if( gFileCount <= gRowCount )
	{
		SclSetScrollBar(barP, 0, 0, 0, gRowCount);
	}
	else
	{
		SclSetScrollBar(barP, gTopIndex, 0, gFileCount - gRowCount, gRowCount);
	}
}











⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -