PALM开发教程-第八章 表和滚动条 |
| 作者:palmheart 来源:palmheart.net 发布时间:2005-12-21 3:35:05 |
|
7.定义Column Widths。设Column Width从1到40。选中Column Width 1,按CTRL-K创建一个新的列。设置此列宽度从2到40。选中Column Width 2,按CTRL-K创建第三列。设置Column Width从3到73; 8.Contact List窗体看起来如图8-2所示。 在表中显示记录 我们将添加表的两个基本函数:drawTable()和drawCell()。drawTable()在光标的当前状态绘制表。函数drawCell()是定制的单元输入函数,当Palm OS要向表中输入一个条目时,就会执行这个函数。我们先加入这些函数的原型: static void drawTable( void ); static void drawCell( VoidPtr table, Word row, Word column, RectanglePtr bounds ); drawCell()的函数原型必须和订制字单元输入的回馈函数原型相匹配。在Palm OS文献的TblSetCustomDrawProcedure()中有这个原型的定义。 为了整洁起见,最好在文件的开头定义常量: // CH.8 Table constants #define TABLE_NUM_COLUMNS 3 #define TABLE_NUM_ROWS 11 #define TABLE_COLUMN_DATE 0 #define TABLE_COLUMN_TIME 1 #define TABLE_COLUMN_NAME 2 #define BLACK_UP_ARROW "\x01" #define BLACK_DOWN_ARROW "\x02" #define GRAY_UP_ARROW "\x03" #define GRAY_DOWN_ARROW "\x04" 常量TABLE_NUM_COLUMNS和TABLE_NUM_ROWS定义了窗体中表显示的大小,这与以后的很多运算与迭代有关。接下去的三个常量TABLE_COLUMN_DATE、TABLE_COLUMN_TIME和TABLE_COLUMN_NAME定义了每列所填写的信息。最后的四个常量BLACK_UP_ARROW,BLACK_DOWN_ARROW,GRAY_UP_ARROW和GRAY_DOWN_ARROW是Palm Os中Symol 7字体中代表这些图的ASCII值。当滚动条到达顶部或底部,我们使用这些常量给箭头加上灰晕。值得注意的是,在Palm Os中,只有这个控件可以添加灰晕。 函数contactListHandleEvent()的修改 找到Contact List窗体的事件处理函数contactListHandleEvent(),在这里需要添加drawTable()函数调用: // CH.7 Form open event case frmOpenEvent: { // CH.7 Draw the form FrmDrawForm( form ); // CH.8 Populate and draw the table drawTable(); } break; 接着,处理表中记录被选中后的操作,在选中一条记录后应该调用Contact Detail窗体来显示其详细信息。请注意这些代码与处理列表框记录选中后的代码很相似。为使Contact Detail窗体显示相应的记录,我们设置了游标(Cursor)变量。 // CH.7 Respond to a list selection case tblSelectEvent: { // CH.7 Set the database cursor to the selected contact cursor += event->data.tblSelect.row; // CH.7 Go to contact details FrmGotoForm( ContactDetailForm ); } break; 因为数据库要根据了不同的标准排序,所以每次排序后都要重新画表来显示新的记录顺序。为此,在DmQuickSort()后加入drawTable()函数来响应popSelectEvent事件。 // CH.7 Sort the contact database by the new criteria DmQuickSort( contactsDB, (DmComparF*)sortFunc, sortBy ); // CH.8 Rebuild the table drawTable(); } break; 这样对这个函数的修改就完成了。 添加drawTable()函数 下面添加drawTable()函数。先定义一些变量,并获取表的指针。 // CH.8 Draw our list of choices using a table object static void drawTable( void ) { FormPtr form; TablePtr table; Int column; Int count; ControlPtr upArrow; ControlPtr downArrow; // CH.8 Get the form pointer form = FrmGetActiveForm(); // CH.8 Get the table pointer table = getObject( form, ContactListTableTable ); 我们将对表中的列做两件事情。首先,每一列都要有一个定制的规则(Routine)。虽然条目类型是基于单元的,但如果单元是定制的,每一单元在特定的列上都要使用相同的规则。在例子中,我们将创建一个定制规则——drawCell(),在表的每个单元中都将使用这个规则。 另外一个要做的事情是使列为可见。列的缺省值是不可见的,为了显示需要将其设置为可见。 // CH.8 For all columns for( column = 0; column < TABLE_NUM_COLUMNS; column++ ) { // CH.8 Set the draw routine TblSetCustomDrawProcedure( table, column, drawCell ); // CH.8 Make the column visible TblSetColumnUsable( table, column, true ); } 下面,再来讲述表的行。由于表中的每一单元都需要定义一个类型,所以我们对列进行了操作。对于表中的不用(Unused)的行来说,就不需这样做。如果数据库包含的记录少于可见的行数,就需把表中不用的行关闭。这是很重要的,如果不关掉这些不用的行,当写代码时,我们就会试图向行中写不存在的记录,说不定会使系统崩溃的。既然表中的记录数是在变化的,我们就要保证在有记录时,标记行为可用,在没有记录时,标记行为不可用。 // CH.8 Initialize the table styles for( count = 0; count < TABLE_NUM_ROWS; count++ ) { // CH.8 If there is data if( count < numRecords ) { // CH.8 Show the row TblSetRowUsable( table, count, true ); // CH.8 Set the cell styles for( column = 0; column < TABLE_NUM_COLUMNS; column++ ) TblSetItemStyle( table, count, column, customTableItem ); } else // CH.8 Hide unused rows if any TblSetRowUsable( table, count, false ); } // CH.8 Draw the table TblDrawTable( table ); 一旦表的类型确定,通过命令TblDrawTable()将表画出来。 值得注意的是,使用TblSetRowUsable()函数可以在浏览表时,只显示所览数据库的一列,这种方法的缺点是它比我们后面章节使用的方法要耗费更多的内存。 添加drawCell()函数 通过前面的准备,现在终于可以调用我们定制函数drawCell()了,每次它都会在表中绘制一条目(Item)。下面是函数的开始部分: // CH.8 The custom drawing routine for a table cell static void drawCell( VoidPtr table, Word row, Word column, RectanglePtr bounds ) { Int record; CharPtr precord; Char string[DB_FIRST_NAME_SIZE + DB_LAST_NAME_SIZE]; SWord width; SWord len; Boolean noFit; 由于这个函数是通过调用TblSetCustomDrawProcedure()设置的回 |
| [] [返回上一页] [打 印] |
|
文章评论 |
