/* ****************************************************************************
* FUNCTION
* aud_vr_sd_scan_tags_in_group_folder
* DESCRIPTION
* vr sd scan all tags in a group folder
* PARAMETERS
* group_id [IN]
* path [?]
* RETURNS
* void
**************************************************************************** */
void aud_vr_sd_scan_tags_in_group_folder(kal_uint16 group_id, kal_uint16 * path)
{
/* ---------------------------------------------------------------- */
/* Local Variables */
/* ---------------------------------------------------------------- */
kal_uint16 filename[VR_MAX_DB_PATH_LEN + 1 ];
kal_uint16 filename_expr[VR_MAX_DB_PATH_LEN + 1 ];
kal_int32 word_id;
FS_HANDLE fd_cursor;
FS_DOSDirEntry file_info;
/* ---------------------------------------------------------------- */
/* Code Body */
/* ---------------------------------------------------------------- */
vr_sd_ctx.id_length[group_id] = 0 ;
kal_wsprintf(filename_expr, " %wMTKVR_????.vrd " , path);
if ((fd_cursor = FS_FindFirst(filename_expr, 0 , 0 , & file_info, filename, (VR_MAX_DB_PATH_LEN + 1 ) << 1 )) >= 0 )
{
/* loop through all vrd files in a group folder */
do
{
/* filter out folder results */
if ( ! (file_info.Attributes & FS_ATTR_DIR))
{
/* parse word id and add to id array and increment id length */
if ((word_id = aud_vr_sd_extract_word_id(filename)) >= 0 )
{
vr_sd_ctx.id_array[group_id][vr_sd_ctx.id_length[group_id] ++ ] = word_id;
}
}
} while (FS_FindNext(fd_cursor, & file_info, filename, (VR_MAX_DB_PATH_LEN + 1 ) << 1 ) == FS_NO_ERROR);
FS_FindClose(fd_cursor);
}
}
下面讲一讲匹配,这里所说的匹配主要是将文件格式(即后缀名)的匹配,在获取到文件名以后进行。
思路也都是相同的,那就是从文件名末端开始搜索到第一个".",然后截取"."后面这一段作为拓展名,然后把这个拓展名拿到自己的需要的格式列表中对比即可。
MTK中有两种方式实现了这个需求,
方式1(来自FileManagerSrc.c):
/*****************************************************************************
* mmi_fmgr_get_file_group
* DESCRIPTION
* check file type belongs to which file group
* PARAMETERS
* path [?]
* RETURNS
* void
**************************************************************************** */
U8 mmi_fmgr_get_file_group(S8 * path)
{
/* ---------------------------------------------------------------- */
/* Local Variables */
/* ---------------------------------------------------------------- */
FMGR_FILTER file_type;
S32 result;
/* ---------------------------------------------------------------- */
/* Code Body */
/* ---------------------------------------------------------------- */
result = mmi_fmgr_get_file_type(path, & file_type);
if (result == FS_FILE_NOT_FOUND)
{
return FMGR_GROUP_UNKNOWN;
}
if (FMGR_FILTER_IS_SET_AUDIO( & file_type))
{
return FMGR_GROUP_AUDIO;
}
else if (FMGR_FILTER_IS_SET_IMAGE( & file_type))
{
return FMGR_GROUP_IMAGE;
}
else if (FMGR_FILTER_IS_SET_VIDEO( & file_type))
{
return FMGR_GROUP_VIDEO;
}
else if (FMGR_FILTER_IS_SET_SWFLASH( & file_type))
{
return FMGR_GROUP_SWFLASH;
}
else
{
return FMGR_GROUP_UNKNOWN;
}
}
在mmi_fmgr_get_file_type函数内实现了相应的逻辑,这个流程依赖于FileMgr.c中
const fmgr_filter_struct fmgr_filter[FMGR_MAX_FILTER_COUNT];
方式2: 依赖于系统的全局变量的东西有时并不能满足我们应用的需求,这个时候我们需要自己定义一个私有的fmgr_filter,来实现拓展名的判断。
这个流程的实现可以参照09A代码AudioPlayerPlayList.c中mmi_audply_playlist_generate_search函数。
下面来对比两个获取后缀名的函数:
/*****************************************************************************
* mmi_fmgr_extract_ext_file_name
* DESCRIPTION
* get pointer to the extension file name in the file path
* PARAMETERS
* path [?]
* RETURNS
* void
**************************************************************************** */
PS8 mmi_fmgr_extract_ext_file_name(S8 * path)
{
/* ---------------------------------------------------------------- */
/* Local Variables */
/* ---------------------------------------------------------------- */
S16 i, length;
/* ---------------------------------------------------------------- */
/* Code Body */
/* ---------------------------------------------------------------- */
length = (S16) mmi_ucs2strlen(path);
i = length - 1 ;
while (i >= 0 )
{
if (path[i << 1 ] == ' \\ ' && path[(i << 1 ) + 1 ] == 0 )
{
return NULL;
}
if (path[i << 1 ] == ' . ' && path[(i << 1 ) + 1 ] == 0 && (i != length - 1 ))
{
break ;
}
i -- ;
}
if (i < 0 )
{
return NULL;
}
return & path[(i + 1 ) << 1 ];
}
另一种系统string处理的接口:
* FUNCTION
* app_ucs2_strrchr
* DESCRIPTION
* Scan a UCS2 encoded string for the last occurrence of a character.
* PARAMETERS
* string [IN] UCS2 encoded string to search in.
* ch [IN] UCS2 encoded wide-character to search for.
* RETURNS
* returns pointer to the last occurrence of ch in string
* returns NULL if ch does not occur in string
**************************************************************************** */
kal_int8 * app_ucs2_strrchr( const kal_int8 * string , kal_wchar ch)
{
/* ---------------------------------------------------------------- */
/* Local Variables */
/* ---------------------------------------------------------------- */
kal_int8 * cursor = (kal_int8 * ) string ;
/* ---------------------------------------------------------------- */
/* Code Body */
/* ---------------------------------------------------------------- */
while ( * cursor || * (cursor + 1 )) /* find end of string */
{
cursor += 2 ;
}
/* search towards front */
while ((kal_int8 * ) string != cursor &&
( * (cursor + 1 ) << 8 | (kal_uint8)( * cursor)) != ch)
{
cursor -= 2 ;
}
if (( * (cursor + 1 ) << 8 | (kal_uint8)( * cursor)) == ch) /* found ? */
{
return cursor;
}
return NULL;
}
PS8 test( const UI_string_type ext)
{
/* ---------------------------------------------------------------- */
/* Local Variables */
/* ---------------------------------------------------------------- */
U8 i = 0 ;
U32 ext_len = 0 ;
UI_character_type file_ext[FMGR_MAX_EXT_LEN + 1 ];
/* ---------------------------------------------------------------- */
/* Code Body */
/* ---------------------------------------------------------------- */
/* skip ".". */
{
PS8 dot = (PS8)app_ucs2_strrchr(( const PS8)ext, (U16)L ' . ' );
if (dot)
{
dot += 2 ;
}
else
{
dot = (PS8)ext;
}
mmi_ucs2ncpy((PS8)file_ext, ( const PS8)dot, FMGR_MAX_EXT_LEN);
ext_len = mmi_ucs2strlen(( const PS8)dot);
return dot;
}
}