mmi培训资料--自定义模板_第1页
mmi培训资料--自定义模板_第2页
mmi培训资料--自定义模板_第3页
已阅读5页,还剩10页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、mmi培训资料-自定义模板2008-06-06 21:48本文详细讲明了如何建设一个自定义列表窗体模板。原理部分请参见MTK平台(1)如何添加一个窗体模板。最终实现的是一个字典输入界面。布局为:该模板不包含业务逻辑,仅提供页面显示和 InputBox框输入事件后的ListBox的Redraw事件的注册,以及差不多的输入法设置、 清空后的返回函数。一、添加用户自定义列表模板的过程(一) 在 g_categories_controls_map中加入:,MMI_CATEGORY_CUSTOM_LIST,(U8*)custom_defi ne_list,(s16*)coordi nate_custom

2、_ list,NULLconst U8 custom_define_list=5,DM_BASE_LAYER_START,DM_SCR_BG,DM_BASE_CONTROL_SET1,DM_SINGLELINE_INPUTBOX1,DM_LIST1;const S16 coordinate_custom_list= 一 一DM_FULL_SCREEN_COORDINATE_FLAG, DM_CUSTOM_DEFINE_INPUTBOX, / 需要定义 DM_CUSTOM_DEFINE_LIST/ 需要定义;(二) 在 dm_get_coordinates ()函数中加入:/设定列表位置和大小(

3、不要不记得全局变量MMI_custom_Listbox_x等的定义)else if( *UICtrlAccessPtr_p = DM_CUSTOM_DEFINE_LIST )dm_coordi nate_i nfo->s16X = MMI_custom_Listbox_x;dm_coordi nate_i nfo->s16Y =MMI_custom_Listbox_y;dm_co ordin ate_i nfo->s16Width =MMI_custom_Listbox_width;dm_coordi nate_i nfo->s16Height =MMI_custom_

4、Listbox_height;dm_coordi nate_i nfo->Flags = DM_NO_FLAGS;UICtrlAccessPtr_p + ;设定输入框位置和大小else if( *UICtrlAccessPtr_p = DM_CUSTOM_DEFINE_INPUTBOX ) dm_coordi nate_i nfo->s16X = MMI_custo mn putbox_x ;dm_coordi nate_i nfo->s16Y = MMI_custo mn putbox_y;dm_coordi nate_i nfo->s16Width = MMI_cu

5、sto mn putbox_width ; dm_coordi nate_i nfo->s16Height =MMI_custom_i nputbox_height;dm_coord in ate_i nfo->Flags =DM_SINGLE_LINE_INPUTBOX_SPECIFIC_HEIGHT;UICtrlAccessPtr_p + ;(三) 在 Wgui_category.c中定义模板显示函数void ShowCategoryCustomListScree n(U8 *title,U16 title_ico n,U16 left_softkey,U16 left_sof

6、tkey_ic on,U16 right_softkey,U16 right_softkey_ic on,S32 nu mber_of_items,U8 *list_of_items,U16 *list_of_ico ns,S32 flags,S32 highlighted_item, U8 *history_buffer) _/* LocalVariables*/dm_data_struct dm_data;S32 i;U8 h_flag;/* CodeBody*/gdiayer_lock_frame_buffer();SetupCategoryKeyHa ndlers();MMI_titl

7、e_stri ng = (UI_stri ng_type) title;MMI title icon = (PU8) get image(title icon);cha nge_left_softkey(left_softkey, left_softkey_ico n);cha nge_right_softkey(right_softkey, right_softkey_ico n);/Create Listcreate_fixed_ic on text_me nu items(); associate_fixed_ic on text_list();ShowListCategoryScree

8、 n(Ul_stri ng_type) title, get_image(title_ico n), get_stri ng(left_softkey), get_image(left_softkey_ico n), get_stri ng(right_softkey), get_image(right_softkey_ico n), nu mber_of_items);for (i = 0; i < nu mber_of_items; i+) 一一add_fixedcon text_item(UI_stri ng_type) list_of_itemsi, wgui_get_list_

9、me nu_icon (i, list_of_ic on si);一 _ 一 一 -h_flag = set_list_me nu_category_history(MMI_CATEGORY_CUSTOM_LIST, history_buffer);if (h_flag)fixedist_goto_item _n o_redraw(MMI_fixedist_me nu.highlight edtem);_ elsefixedist_goto_item _n o_redraw(highlighted_i tem);/Create In putboxmemset(custom_si ngle_i

10、nput_buffer,0,100);pfnU nicodeStrcpy(custom_si ngle_i nput_buffer,L"Custom Category");wgui_setup_s in gleli ne_in putbox(0,0,240,320,custom_s in gle_i nput_buffer,pfnUni codeStrle n( custom_s in gle_i nput_buffer),MMI_CATEGORY_CUSTOM_LIST,get stri ng(right softkey),get_image(right_softkey_

11、ico n),INPUT_TYPE_ALPHANUMERIC_LOWERCASE| INPUT_TYPE_USE_ONLY_ENGLISH_MODES,history_buffer,0);register_hide_multitap(wgui_hide_multitap);gdiayer_ un lock_frame_buffer();ExitCategory Function = ExitCategoryCustomListScree n; dm_setup_category_fu nctio ns(dm_redraw_category_scree n, dm_get_category_hi

12、story, dm_get_category_history_size);dm_data.s32Scrld = (S32) GetActiveScree nld(); dm_data.s32Catld = MMI_CATEGORY_CUSTOM_LIST;/不要不记得该常量 MMI_CATEGORY_CUSTOM_6定义dm_data.s32flags |= DM_CLEAR_SCREEN_BACKGROUND;dm_data.s32flags |= DM_SHOW_VKPAD;dm_register_vkpad_callback(CustomList_virtual_keypad_callb

13、ack); dm_setup_data(&dm_data); dm_redraw_category_scree n();/* end of ShowCategory353Screen */void CustomList_virtual_keypad_callback(void) #if defi ned(_MMI_TOUCH_SCREEN_)mmi_pe n_editor_clear_a nd_show_virtual_keyboard_area();#en difgui_show_tra nspare nt_image(0,200,Getlmage(IMG_H_SELECT_LEFT

14、),0); 一一 一 "" -void ExitCategoryCustomListScree n()wgui_close_si ngleli ne_in putbox(); 一一 一(四) 在 singleline_inputbox_multitap_input()函数中添加用户处理 key_0key_9的按键事件的函数:void (*singleline_inputbox_customnput_callback)(void) = UI_dummy_function;void si ngleli ne_in putbox_multitap_i nput(UI_charac

15、ter_type c) /* LocalVariables*/* CodeBody*/if (MMI_si ngleli ne_in putbox.flags & UI_SINGLE_LINE_INPUT_BOX_PLUS_CHARACTER_HANDLING)if (MMI_si ngleli ne_in putbox.text0 = '+') &&(MMI_si ngleli ne_in putbox.curre nt_text_p =MMI_si ngleli ne_in putbox.text) &&(MMI_si ngleli

16、ne_in putbox.text_le ngth >=(MMI_si ngleli ne_in putbox.available_le ngth - ENCODING_LENGTH)return;gui_si ngle_li ne_in put_box_i nsert_multitap_character(&MM I_si ngleli ne_in putbox, c);redraw_si ngleli ne_in putbox();sin gleli ne_in putbox_i nput_callback();sin gleli ne_in putbox_customn p

17、ut_callback(); (五) Wgui_Category.c中添加用户事件定义接口/右键事件注册void SetCategoryCustomListRightSoftkeyFu nctio n(void (*f) (void)wgui_s in gleli ne_in putbox_RSK_f unction = f;key_0到key_9按下时的事件注册exter n void (*si ngleli ne_in putbox_custo mn put_callback) (void);void SetCategoryCustomListNumKeyFu nctio n(void (

18、*f) (void)sin gleli ne_in putbox_custom_i nput_callback = f ; 一 /设置InputBox大小void SetCustomListnputbox_Size(S32p_x , S32 p_y , S32 p_width , S32 p_height ) 一 MMI_custo mn putbox_x = p_x ;MMI_custo mn putbox_y = p_y ;MMI custo mn putbox width = p width ;MMI_custo mn putbox_height = p_height ; 一/设置Lis

19、tBox大小void SetCustomList_Listbox_Size(S32 p_x , S32 p_y , S32 p_width , S32 p_height ) 一 MMI_custom_Listbox_x = p_x ;MMI_custom_Listbox_y = p_y ;MMI_custom_Listbox_width = p_width ;MMI_custom_Listbox_height = p_height ;二、自定义列表模板的使用方法1、 调用 SetCustomListnputbox_Size和 SetCustomList_Listbox_Size设置列表框和输入

20、框的大小。2、调用显示窗体的接口 ShowCategoryCustomListScreen 。3、调用右键事件注册函数,注册文本框被清空后的事件(如返回等)SetCategoryCustomListRightSoftkey Fun ctio n 。4、调用 key_0 至 key_9 的事件注册函数,SetCategoryCustomListNumKeyFunction()。三、参数详细讲明 void SetCustomListnputbox_Size(S32 p_x , S32 p_y , S32 p_width , S32 p_height ) 与void SetCustomList_Li

21、stbox_Size(S32 p_x , S32 p_y , S32 p_width , S32 p_height ) p_x , p_y:起始位置p_width , p_height :大小。 void SetCategoryCustomListRightSoftkeyFu nctio n(void (*f) (void)void SetCategoryCustomListNumKeyFunction(void (*f) (void) f(void):函数地址。/标题文本指针/标题图标ID/左键文本ID/左键图标ID/右键文本ID/ 右键图标ID buffer, / Input输入 Buff

22、er/列表条目数/列表项文本指针数组/ 列表项Icon/当前咼亮显示的列表条目 void ShowCategoryCustomListScree n(U8 *title,U16 title_ico n,U16 left_softkey,U16 left_softkey_ic on,U16 right_softkey,U16 right_softkey_ico n, U8* custom_s in gle_i nputS32 nu mber_of_items, U8 *list_of_items,U16 *list_of_ico ns,S32 highlighted item,U8 *histo

23、ry_buffer)/ 历史记录Buffer附:所需更换的文件wgui.c wgui_categories.c wgui_draw_ma nager.c wgui_i nputs.cwgui.h wgui_categories_defs.h wgui_draw_ma nager.h CustCoord in ate.c一、什么是History治理关于我们上层用户而言,经常接触到的History治理是如此的:void EntryFun c()U8 *guiBuffer;En tryNewScree n( ScreenD , Exit_Fu nc , En try_Fu nc , NULL );

24、guiBuffer = GetCurrGuiBuffer( SCR_ID_WORDMAIN_LIST );ShowCategroyXXScree n( Title_ID ,,guiBuffer); _然而,不管是EntryNewScreen的调用,依旧guiBuffer的传入,我们都专门少考虑过 对这些指针和函数在GUI的治理起到了什么样的作用。下面我们就要了解,以上的代码 与History治理之间存在的关系。在MTK环境中,每当我们进入一个窗口,系统将先提取前一个窗口需保留的数 据。这些数据包括:1. 窗口 ID ;2. 进入窗口时调用的函数和退出调用的函数-Exit_Fu nc 和En t

25、ry_Fu nc ;3. 组成窗体的控件的属性(如,列表控件当前高亮显示的条目、当前屏的首末条 目等)。举例讲明这些数据在实际中是如何被使用的。假设存在AB两个窗口,A窗口需要保留的数据为data_A。我们先从A窗口进入到B窗 口。data_A将在B窗口调用EntryNewScreen()的时候,被压入一个结构类似于栈的数 据储备区域;当从B调用GoBackHistory()返回A时,data_A从栈顶被弹出,然后A利 用data_A将自身还原到其进入B之前的状态。这确实是History治理的作用。简言之,确实是要保持窗口的外观状态。、History治理的机制现在,我们来了解一下前面所讲的da

26、ta_A的数据结构是什么样的。typedef struct _history _U16 scrnlD;/(l)Screen ID ( 窗口号)FuncPtr entryFuncPtr;EntryNewScreen时要进入的 Entry_FuncU8 in putBufferMAX_INPUT_BUFFER;/(3)没遇到过其使用,差不多上NULLU8 guiBufferMAX_GUI_BUFFER;/(4)窗体中控件的一些需储存的信息的 Buffer,通常/在使用时被转化成各控件自定义的结构体如:list_me nu_category_history 。 history;而存放data_A的类

27、似于堆栈的数据区则以全局变量的形式定义在系统中:historyNode historyDataMAX_HISTORY; (MAX_HISTORY = 50):设当前窗口 A所对应的数据是historyData EntryScreenNum- 1 ,那么它是何时、是如何被赋值的?又是何时、如何被使用的?通过跟踪调试,我们差不多明白,在由窗口 A进入到窗口 B (调用EntryNewScreen)的 时候,我们将data_A记录到了 historyNode 的结构体变量中。然而,在EntryNewScreen 的时候传入的,却是data_B,data_A是如何被记录和使用的呢?我们摘选EntryN

28、ewScreen的子函数中所包含的较核心的代码来讲明那个咨询题。这三 段代码是按照现在的排放顺序来执行的。第一段(history h 可懂得为data_A):h.scrnID = scrnID;/ scrnID = currExitScrnIDh.e ntryFun cPtr = en tryF un cPtr; / entryFun cPtr = currE ntryF un cPtrpfnU ni codeStrcpy(S8*) h.i nputBuffer, (S8*) & n History);/ n History = NULL ;GetCategoryHistory(h.g

29、uiBuffer);/GetCategoryHistory是指向猎取/guiBuffer的函数的指针AddHistory(h);/ 数据入栈第二段:if(currExitFu ncPtr)(*currExitFuncPtr) ();/ 执行 Exit_Func _第三段(记录 ScreenD,Exit_Func 和 EntryFunc):currExitScrnID = scrnID;currExitF un cPtr = exitF un cPtr;currE ntryF un cPtr = entryFun cPtr;如此,我们就能够看出,EntryNewScreen函数先将上次执行Ent

30、ryNewScreen时所记录 的 currExitScrnID, currEntryFuncPtr以 history 结构为载体记录入栈; 然后执行了 记录中的 currExitFuncPtr ;最后将本窗口的 scrnlD、exitFuncPtr、entryFuncPtr 分 别记录入全局变量 currExitScrnlD 、currExitFuncPtr 和 currEntryFuncPtr ,留待下次 调用EntryNewScreen时使用。下面有数据出入栈流程,有爱好的话能够跟踪一下。以先后顺序代表包含关系,如下:1. 入栈(EntryNewScreen):(1) U8 En try

31、NewScree n( U16 newscrnID, Fun cPtr newExitHa ndler, Fu ncPtrn ewE ntryHa ndler, void *peerBuf)(2) static void ExecuteCurrExitHa ndler(void);(3) void ExecuteCurrExitHa ndler_Ext(void);(4) void GenericExitScreen( U16 scrnID , FuncPtr entryFuncPtr);(5) void AddHistoryReference(history *addHistory); /处

32、理 historyData(6) S16 in creme nt();/ 更换栈指针2. 出栈(GoBackHistory):(1) void GoBackHistory(void);(2) static void ExecutePopHistory(void);/ 处理 historyData(3) static U8 decreme nt(void);/更换栈指针现在我们差不多明白了 history的三个结构体成员是如何记录的了,最后来重点看一下history.guiBuffer是如何被记录和使用的。三、GUI Buffer对控件属性的记录由上2节我们明白,guiBuffer是窗体中某些控

33、件的需储存的属性的Buffer,通常在使用时被转化成各控件自定义的结构体。如:list_me nu_category_history。现在有几个咨询题需要我们解答:1. guiBuffer 指向的Buffer是如何被分配的?该块数据是动态的依旧静态的?2. 这块Buffer是何时被写入数据的?3. 如何开释(动态分配时)或清空(固定地址时)该块Buffer ?让我们逐一解答上面的三个咨询题,以清晰我们对guiBuffer的认识。1. 答:在 void AddHistoryReference(history *addHistory)中,调用OslMalloc(MAX_GUI_BUFFEF动态申请

34、了一块内存,用来储存在 GenericExitScreen中猎取的history.guiBuffer 。参见出入栈流程2. 如何开释(动态分配时)或清空(固定地址时)该块Buffer ?答:在 static void decreme nt (void) 函数中,该 buffer 被开释: OslMfree(historyDatacurrHistoryIndex.guiBuffer);。参见出入栈流程3. 答:只要一个窗体模板有需要储存状态的控件,它们都调用了那个函数dm_setup_category_f unction s()。函数定义如下:void dm_setup_category_fu

35、nctions(Fun cPtr redraw_fu nction,U8 *(*get history function) (U8 *buffer),S32(*get_history_size_fu nctio n) (void)/指向窗体重画函数的函数指针RedrawCategoryF un ctio n = redraw_fu nctio n;/指向猎取窗体guiBuffer的函数指针GetCategoryHistory = get_history_f un cti on;/指向猎取窗体guiBuffer大小的函数指针GetCategoryHistorySize = get_history

36、_size_f un cti on;在只有一个控件的状态需要储存的窗体中,会如此传参给那个函数: dm_setup_category_fu nctio ns(dm_redraw_category_scree n, dm_get_category_history, dm_get_category_history_size);GenericExitScreen()函数中,将使用 GetCategoryHistory()猎取某个控件的 GuiBuffer参见出入栈流程。如果按照上面的设置,GetCategoryHistory 指向了 dm_get_category_history那个函数。看看那个函

37、数做了什么:con trol_set_ptr = dm_search_co ntrol_set(U16) p_dm_data->s32Catld,& coordi nate_set_p); /猎取窗体模板内的控件类型数组 co ntrol_set_ptru8NoOfUICtrls = con trol_set_ptrO; /猎取数组内变量个数,即控件的个数/*按照控件类型,猎取控件的guiBuffer.值得注意的是,1.那个地点的histroy_Buffer 的名称起的不行,应该起名为 guiBuffer,不应混淆视听;2.最终history_buffer 将 指向模板中定义的最

38、后一个控件的guiBuffer*/for (u8CtrlCt = 1; u8CtrlCt <= u8NoOfUICtrls; u8CtrlCt+)switch (co ntrol_set_ptru8CtrlCt) 一 一case DM_CIRCULAR_MENU1:get_circular_me nu _category_history(U16) p_dm_data->s32Catld, history_buffer);break;case DM_LIST1:get_list_me nu _category_history(U16) p_dm_data->s32Catld,

39、history_buffer);break;case DM_DYNAMIC_LIST1:get_list_me nu _category_history(U16) p_dm_data->s32Catld, history_buffer);break;case DM_ASYNCDYNAMIC_LIST1:get_list_me nu _category_history(U16) p_dm_data->s32Catld,history_buffer);break;/./.而在模版显示函数(ShowCategroyXXScreen)中,则按照guibuffer 的情形设置控件的 属性。如

40、果guibuffer 不为空,则讲明该模板的显示函数是在 GoBackHistory()的时候 被调用的,而不是进入新窗口时被调用的。那么控件必定有一些保留的属性需要被还原。以6号窗口的List为例。在ShowCategory6Screen()中,调用下面的函数来复原 List 设置:h_flag = set_list_me nu_category_history(MMI_CATEGORY6_ID, history_buffer); 如此guiBuffer 的Get和Set就统一起来了。现在,我们差不多明白了 guiBuffer所起到的作用。然而,如果一个窗体模板内有两个 或两个以上需要记录状

41、态的控件,又该如何办呢?ps:该死的字数限制,只能把剩下的放到MTK平台History治理下了。四、灵活使用guiBuffer在我们自己设计窗体模板时,经常会显现一个窗体中有多个控件的情形。然而,如果一 个窗体中有两个控件、却依旧调用 dm_get_category_history()猎取控件的GuiBuffer的话,就会显现咨询题。例如,我们在制作CustomList窗体时,初期使用了如此的代码:(1) 模板中的组件设置:const U8 custom_define_list=5,DM_BASE_LAYER_START,DM_SCR_BG,DM_BASE_CONTROL_SET1, DM_S

42、INGLELINE_INPUTBOX1, / 单行输入控件DM_LIST1/列表控件;窗体显示函数ShowCategoryCustomListScreen 部分源码:void ShowCategoryCustomListScree n(.,U8 * guiBuffer)/./ 按照 MMI CATEGORY CUSTOM I的STuiBuffer,为全局结构体变量MMI_fixed_list_me nu赋值.h_flag = set_list_me nu_category_history(MMI_CATEGORY_CUSTOM_LIST,guiBuffer);/而后利用MMI_fixed_li

43、st_menu,设置list的属性if (h_flag)fixedist_goto_item _n o_redraw(MMI_fixedist_me nu.highlightedtem);elsefixedist_goto_item _n o_redraw(highlightedtem); - -/再设置单行输入框的属性wgui_setup_s in gleli ne_in putbox(0,0,240,320,custom_s in gle_i nput_buffer,50,MMI_CATEGORY_CUSTOM_LIST,get_stri ng(right_softkey),get_ima

44、ge(right_softkey_ico n),INPUT_TYPE_ALPHANUMERIC_LOWERCASE| INPUT_TYPE_USE_ONLY_ENGLISH_MODES, guiBuffer,0);/ 其中 wgui_setup_singleline_inputbox函数中调用了/set_singleline_inputbox_category_history()来解析 guiBufferdm_setup_category_fu nctio ns(dm_redraw_category_scree n, dm_get_category_history, dm_get_catego

45、ry_history_size);连续使用前3节的假设。窗口 A使用了 CustomList窗体模板。从A进入到B时,EntryNewScreen函数调用了我们设置的猎取 guiBuffer函数dm_get_category_history,它先储存了 A中InputBox的属性,再储存 A中List的属性现在它将把输入框的属性覆盖掉。当从B窗口返回到A窗口时,ShowCategoryCustomListScreen()函数先把 history_buffer 传给了set_list_menu_category_history , 由于 guiBuffer 中储备的是 List 的数据,因此在

46、交付fixed_list_goto_item_no_redraw进行设置属性的时候,可不能显现咨询题。但wgui_setup_singleline_inputbox()就会因为guiBuffer中储备的不是输入框储备的数据而显现错误。因此,权宜之计是,将更换传给 wgui setup singleline inputbox 的入参:wgui_setup_s in gleli ne_in putbox(0,0,240,320,custom_s in gle_i nput_buffer,50,MMI_CATEGORY_CUSTOM_LIST,get_stri ng(right_softkey),

47、get_image(right_softkey_ico n),INPUT_TYPE_ALPHANUMERIC_LOWERCASE | INPUT_TYPE_USE_ONLY_ENGLISH_MODES, NULL,0);如此,尽管死机bug幸免了 ,然而特定情形下InputBox需要储存的属性,将 全部丢失掉.因此,更加合适的做法是,提取dm_setup_category_functions() 中使用的 函数接口 :get_si ngleli ne_in putbox_category_history get_list_me nu _category_history如此能够分别猎取input

48、box 和list 的属性,然后将得到的两个属性的数据 连续存放在一块动态分配的 Buffer中.如200号窗口的GetCategroyHistory 函数所示: U8 *GetCategory200History(U8 *history_buffer) _S32 s;get_list_me nu_category_history(MMI_CATEGORY2OO_ID, history_buffer);s = sizeof(list_me nu _category_history);s = (s + 3) / 4;s *= 4;get_si ngleli ne_in putbox_catego

49、ry_history(MMI_CATEGORY200_ID, (U8*)(history_buffer + s), MMI_curre nt_in put_type);return (history_buffer); _要注意的咨询题是,系统为guiBuffer分配空间时,依据的是MAX_GUI_BUFFE而不是 dm_setup_category_functions()所指定的猎取 guiBuffer 大小的函数GetCategoryHistorySize.而且系统中从未使用过该函数指针所指向的函数。惊奇的是 所有窗体模板的制作者都兢兢业业地制作了那个猎取guiBuffer大小的函数。在20

50、0号窗口里,猎取guiBuffer大小的函数如下:S32 GetCategory200HistorySize(void)return (sizeof(list_me nu _category_history) + 3) / 4) * 4 + sizeof(si ngleli ne_in putbox_category_history); 如果怕出错且不怕苦恼的话,也能够未雨绸缪的写一个如此的函数,但可能多半是用不上的。最后的任务确实是在显示窗体时分别猎取各控件的guiBuffer,然后将这些GUI_Buffer分别传给各个控件的Set函数.仍旧参看200号窗体的代码实现:h_flag = set_list_me nu_category_history(MMI_CATEGORY200_ID,history_buffer);/ 第一个控件的 Gui_Bufferif (h_flag)S32 s = sizeof(list_me nu _categor

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论