WD:controller and context programming

每个web webdynpro controller都是定义在与Web Dynpro Component相关的全局abap class中的分离的本地abap class。当声明新的component或controller时这些classes都会自动生成。实施这些controllers的源代码自动生成。每个controller都提供许多预订义的methods,他们被web dynpro component以预订义的顺序调用。这些methods称为hook methods。创建controller时,这些methods都是空的,可以在里面加入自己想要的代码。除了这些hook methods,还可以定义额外的methods:ordinary methods,event handler methods或supply functions。

每当controller被激活时,controller class生成自所有的controller methods包括hook methods和用户定义的methods。ABAP workbench允许你在controller methods中输入源代码,而生成的controller class是不允许的。

HOOK METHODS

所有的controller types都有下面两种hook methods:

l         Wddoinit()

Wddoinit是在controller的生命周期中第一个处理的方法。在整个生命周期中只被处理一次。所有的初始化代码都应当写在这里,因为controller一旦被instantiated他就会被立即调用。

l         Wddoexit()

Wddoexit是在controller生命周期结束时最后调用的方法。所有的清理代码应当写在这里。

不同类型的controller还可以有其他不同的hook methods。对于component controller还有下面标准的hook methods:

l         Wddobeforenavigation()

无论何时触发一个客户端事件,view controller中对应的action method就会被处理。在action method处理之后,Web Dynpro Framework处理navigation queue中events之前,调用method wddobeforenavigation()。

在复杂的Web Dynpro Applications中,在进行下一步业务处理之前,验证来自不同components中的数据是十分必要的。这个方法就用来实现跨components的验证。

l         Wddopostprocessing()

在UI发送到客户端之前,最后调用的方法。

l         Wddoapplicationstatechange()

每当程序中止或继续时都会调用这个方法。如果触发window的suspend plug,web dynpro application就会被suspend。这可以用来启动一个新的application而没必要离开当前的Web Dynpro application。后启动的application结束后,被disable的web dynpro application就会自动继续执行。中止的web dynpro application通过resume plug继续执行。如果创建了至少一个suspend,就要建立一个resume plug。

对于view controller还有下面四个额外的标准hook methods:

l         Wddobeforeaction()

用户触发了绑定到action的客户端事件之后,web webdynpro application第一个调用的方法便是前一个显示的view assembley的所有view controllers的方法wddobeforeaction,这个调用甚至先于与client event相关的action handler method的调用。这个method经常包含与输入检查相关的代码。

l         Wddoafteraction()

Action handler methods被处理后,先前显示的view assembly的所有view controllers的方法wddoafteraction就会被处理。这个method一般放与action handling相关的代码。

l         Wddomodifyview()

唯一允许访问UI element hierarchy方法便是wddomodifyview。Interface parameter VIEW便是UI element hierarchy的reference。FIRST_TIME parameter用来标识在view controller的生命周期内被处理过。这个方法用来动态操作UI element hierarchy。

l         Wddocontextmenu()

在相应的view layout的UI element上点击鼠标右键时便会调用这个方法。从这个方法的源代码,静态定义的context menus可以被instantiated,新的context menus也可以被定义。这些context menus可以被分配给view hierarchy中定义的任何一个UI element。允许扩展标准的right-mouse menu。

对于window controllers还有两个特殊的hookmethods

l         Wddoonopen()

当window作为popup window时在window popup之前处理

l         Wddoonclose()

当window作为popup window时在window关闭之前处理

这两个方法中的源代码仅当window作为popup window时才会被处理。

额外的controller methods

对于所有的controllers,你可以在controller editor window中的methods tab创建自己的meithods,可以声明methods name,定义parameters。要定义普通的method把method type定义成method。如果method type选择event Handler,就会创建event handler method。它可以被静态注册到在properties tab中定义为used controller的任何fired event。最后,如果method type是supply function,methods就可以被绑定到context nodes。当node被访问并表示成invalid时,这些方法就会被Web dynpro framework自动调用。

Supply functions不能被controller method的源代码调用。只有web dynpro runtime才能调用这种类型的方法。

双击method name,就可以定义这个method的signature和source code。

所有的方法都是public的,可以被同一个component的任何其他controller调用。前提条件是调用这个方法的controller必须与拥有这些methods的controller建立usage relation。在used controller调用方法的ABAP代码可以通过web dynpro code wizard生成。

如果自定义的component method设置了interface flag,这个方法就会显示在component interface中。这个method对于其他component也是可以访问的。

Controller attributes

每个controller都是一个单独的ABAP class,具有用户定义的和自定义的methods,还包括attributes,可以被controller的methods访问。

Standard Attributes

定义了controller之后,至少有两个attributes被预订以了。只有controller methods可以访问attributes。这两个标准的attributes是:

l         WD_THIS

WD_THIS是指向本地controller interface的self-reference。这个attribute必须与ABAP的selfreference ME区分开。后者不能够应用到任何controller的源代码中。WD_THIS是指向当前controller的interface的reference(IF_<CONTROLLER NAME>),代表着生成的class的所有功能。它也可以用来访问web dynpro的标准功能比如验证。

l         WD_CONTEXT

WD_CONTEXT是指向controller context root node的reference,进而可以访问整个context。对controller context的访问以这个reference开始。

如果其他的controller在properties tab中将component controller维护成used controller,额外的attributes便会被自动创建他便是:

l         WD_COMP_CONTROLLER

它是指向component controller的reference。通过这个reference,component controller的所有methods和public attributes都可以被访问(wd_comp_controller-><method>)。

对于所有其他的controlelrs,即使被声明为Used controllers,也不会有类似的reference被创建。不过这并不意味着用户定义的methods和public attributes不能被访问,不过reference首先要被evaluated。要声明指向used controller的reference必须使用下面的语句:

DATA:lo_ctrl TYPE REF TO ig_<ctrl>.

Lo_ctrl = wd_this->get_<ctrl>_ctr().

User Defined Attributes

在attributes tab,可以为controller定义额外的attributes。如果设置了public flag,这些attributes就可以被web dynpro component内的其他controllers访问。Attributes不能放于component interface。

如果要在controller methods中访问public controller attributes,必须使用reference variable WD_THIS.访问同一个component下的其他controllers定义的public attributes与访问其他controllers的methods方式一样。

对于出view controller之外的其他所有的controllers,attributes可以是privated的也可以是public的。

Accessing the context Nodes And Node elements at Runtime

Controller attributes可以为整个controller提供data objects。然而,不能够将UI elements properties绑定到这些attributes上。UI element properties只能绑定在controller context中定义的variables。如果数据需要在controllers间共享这种层级的数据存储是可取的。

在runtime访问controller context需要相应的web dynpro methods的知识。下面的部分将要阐述如何读取,修改,添加和删除存储在controller context中的信息。

Accessing a context Node

要访问context element或者context attribute,首先你需要一个相关context node的reference。

关于访问context node的两点:

l         对于每一个controller(<ctrl>),会生成一个名字为IF_<ctrl>的本地interface

l         对于controller context的每一个Node <node>,在这个interface中会生成一个常量WDCTX_<node>,它的value便是node name的大写。这个常量用来访问context node。

Context roolt node可以通过标准属性WD_CONTEXT来访问。Context root node的child nodes可以通过方法get_child_node()来识别。这个方法返回一个node instance类型为IF_WD_CONTEXT_NODE的reference。

Get_child_node()方法需要node的name还可以有要访问的node所属的parent node的element的index,如果不提供这个index,就会缺省使用lead selection index。

对于无关的nodes,index可以被忽略,因为context root node只有一个在lead selection中的element。

访问的pendent node的特殊方式可以通过方法path_get_node(path=<path>)。作为parameter,到desired node的完整path传给这个method。Path由node name和element indices组成(例如<node>.<el_index>.<sub_node>)。如果忽略了element index <el_index>,sub node instance <sub_node>由superordinate node在lead selection的element确定。

示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this-wdctx_flights ).

 

Accessing a Node Element

访问了context node,这个node在lead selection中的element的reference可以通过method get_element()得到。这个方法返回一个element的reference,类型为IF_WD_CONTEXT_ELEMENT。

Index为n的element可以通过method get_element(index)来访问。Collection中ellement的数量可以通过method get_element_count()来得到。

获得context node和node elements的reference的方法总结:

动作

方法

Context node <node>的reference

Lo_nd_<node> = wd_context->get_child_node( name = wd_this->wdctx_<node> )

Lead selection中element的reference

Lo_el_<node> = lo_nd_<node>->get_element( ).

Index为n的element的reference

Lo_el_<node> = lo_nd_<node>->get_element( index = n ).

Collection中elements的数量

N = lo_nd_<node>->get_element_count( ).

Reading and changing Attribute Values

Web dynpro framework提供了一系列的方法用来访问一个node element的attributes或者一个context node的所有elements的attributes。

Accessing Attributes of a Single Node Element

一旦你获得了一个node element的reference,有两种方法可以获得这个element的attribute values:

1.         node element的任何attribute都可以通过方法get_attribute()来获得。Attribute的name必须作为参数传入,而attribute的value将会作为参数传出。示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lo_el_flights TYPE REF TO if_wd_context_element.

DATA lv_connid   TYPE wd_this->element_flights-connid.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

Lo_el_flights = lo_nd_flights->get_element( ).

 

Lo_el_flights->get_attribute(

       EXPORTING

              Name = ‘CONNID’

       IMPORTING

              Value = lv_connid ).

2.         静态定义的attributes可以通过调用method get_static_attributes()来获得。一个structure将作为参数被传出。Target structure可以与node structure不同。这种情况是可能的是因为structure elements被单独得copy到target structure。

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lo_el_flights TYPE REF TO if_wd_context_element.

DATA ls_flights   TYPE wd_this->element_flights-connid.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

Lo_el_flights = lo_nd_flights->get_element( ).

 

Lo_el_flights->get_static_attributes(

       IMPORTING

              Static_attributes = ls_flights

).

下面两点非常重要:

l         对于一个controller context的每一个node <node>,structure type element_node在interface IF_<ctrl>中会被自动生成。Node的类型与element_node的类型一样。如果node没有类型,structure fields便是组成node element的attributes。这个constant可以用来定义一个变量,可以通过上面例子中的方法填充。

l         另外,对于一个controller context的每一个node <node>,一个标准的table type elements_<node>也会在interface IF_<ctrl>中自动生成。这个table的line type便是element_<node>。这个constant可以用来定义一个internal table用来存放多个node elements的attributes。获得所有node elements的attributes的示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lt_flights TYPE wd_this->elements_flights.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this-wdctx_flights ).

 

Lo_nd_flights->get_static_attributes_table(

     IMPORTING

           Table = lt_flights

).

通过method get_static_attributs_table(),所有elements的attributes都可以返回到internal table中。

要想获得用户选择的多个行项目的数据,就需要调用方法get_selected_elements()。这个方法将所有选中的elements放到一个internal table中(type为WDR_CONTEXT_ELEMENT_SET)。这个internal table的每一行都是一个selected element的reference。

为了选择一个context element,用户就需要在相应的table line上做标记,尽管lead selection的element都是dark orange的,相关的context element并不会自动被选择。

因此,当调用method get_selected_elements()时,application必须指明lead selection的element是否被返回即使并没有显式选择它。这通过parameter INCLUDING_LEAD_SELECTION来确定。

Changing the attribute values of a node element

一旦有了到一个node element的reference,你不仅可以使用相应的getter方法读取attribute values,你还可以通过相应的setter方法修改attribute values。

方法set_attribute()可以用来修改node element的任何attribute value。可以通过set_static_attributes()修改静态定义的多个attributes。

修改单个attribute value的示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lo_el_flights TYPE REF TO if_wd_context_element.

DATA lv_connid TYPE wd_this->element_flights-connid.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

Lo_el_flights = lo_nd_flights->get_element().

 

Lo_el_flights->set_attribute(

       EXPORTING

              Name = ‘CONNID’

              Value = ‘0405’

)

修改element的多个属性的示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lo_el_flights TYPE REF TO if_wd_context_element.

DATA ls_flights TYPE wd_this->element_flights.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

Lo_el_flights = lo_nd_flights->get_element().

Ls_flights-carrid = ‘AE’.

Ls_flights-connid = ‘0123’.

 

Lo_el_flights->set_static_attributes(

       EXPORTING

              Static_attributes = ls_flights ).

获得和修改一个controller <ctrl>的node <node>的atrributs的代码总结如下:

动作

方法

读取attribute <attr>的value

DATA: lv_<attr> TYPE wd_this->element_<node>-<attr>.

Lo_el_<node>->get_attribute(

EXPORTING

          Name = ‘<attr>’

        IMPORTING

          Value = lv_<attr> ).

读取多个静态attribute的value

DATA:ls_<node> TYPE wd_this->element_<node>.

Lo_el_<node>->get_static_attributes(

       IMPORTING

            Static_attributes = ls_<node> ).

读取所有node elements的静态attributes的value

DATA: lt_node TYPE wd_this->elements_<node>.

Lo_nd_<node>->get_static_attributes_table(

        IMPROTING

               Table = lt_<node> ).

修改单个attribute <attr>的value

DATA: lv_<attr> TYPE wd_this->element_<node>-<attr>.

Lv_<attr> = …

Lo_el_<node>->set_attribute(

         EXPORITNG

             Name = ‘<attr>”

             Value = lv_<attr> ).

 

修改一个node element的多个attributes

DATA: ls_<node> TYPE wd_this->element_<node>.

Ls_<node>-<attr> = ….

Lo_el_<node>->set_static_attributes(

EXPORTING

        Static_attributes = ls_<node> ).

Adding new elements to a context node

将新的element加入到context node需要分两步走,第一步是要创建可以添加到指定context node的element。定义了attributes value之后,新的element就可以被加入到context node中。这就像在internal table中插入一行一样。第一步是创建正确line type的work area的cell values。第二步是将work area插入到internal table。

Creating a new node element

为了创建添加到指定context node的node element,首先要确定这个context node的reference。可以通过标准attribute context_node的方法get_child_node()来获得。示例代码如下:

DATA:lo_nd_flights TYPE REF TO if_wd_context_node.

Lo_nd_flihgts = wd_context->get_child_node( name = wd_this->wdctx_flights ).

一旦得到这个reference,方法create_element()用来创建新的element。Static attributes的初始值可以通过参数static_attributes_values或者setter方法set_attribute或set_static_attributes()来设置。不过现在这个element还不是context node的一部分。

示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lo_el_flights TYPE REF TO if_wd_context_element.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

Lo_el_flights = lo_nd_flights->create_element().

 

Lo_el_flights->set_attribute( name = ‘CARRID’ value = ‘ZH’ ).

Lo_el_flights->set_attribute( name = ‘CONNID’ value = ‘0400’).

 

Adding elements to a context node

最后这个element就可以通过node的method bind_element()加入进来。这个method有两个参数:

l         Element reference传给参数new_item

l         参数set_intial_elements用来确定elemen是简单的添加到element collection中(value = abap_false)还是替换所有的在collection已经存在的elements(value = abap_true)

示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA lo_el_flights TYPE REF TO if_wd_context_element.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

Lo_el_flights = lo_nd_flights->create_element().

 

Lo_el_flights->set_attribute( name = ‘CARRID’ value = ‘ZH’ ).

Lo_el_flights->set_attribute( name = ‘CONNID’ value = ‘0400’).

 

Lo_nd_flights->bind_element(

       New_item = lo_el_flights

       Set_intial_elements = abap_false

)

Binding a structure to a context node

在ABAP程序中,datasets是通过structures来实现的。然而,为了在UI上显示structure elements,structure content必须copy到一个context element。这意味着new element必须被定义,attribute values必须被设置并被绑定到相应的context node上。

有更简便的方法将structure comtent copy到context node的new element上。不是使用bind_eleemt()并传送element reference而是通过方法bind_structure()通过参数new_item来传送structure。对bind_structure()方法已经存在的可以被扩展或替代,通过参数set_intial_elements来控制。

示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA ls_flights TYPE wd_this->element_flights.t.

 

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

 

Ls_flights-carrid = ‘AA’.

Ls_filgts-connid = ‘0017’.

 

 

Lo_nd_flights->bind_structure(

       New_item = ls_flights

       Set_intial_elements = abap_false

)

Binding an internal table to a context node

有相同结构的多个datasets在ABAP中是通过internal table来处理的。为了在UI中显示datasets,internal table的内容需要被copy到相应数目的context elements中。

最好的方法是通过method bind_table()来实现。Internal table被传送给参数new_items,已经存在的collection可以被扩展或者替代,通过参数set_intial_elements来控制。

示例代码如下:

DATA lo_nd_flights TYPE REF TO if_wd_context_node.

DATA ls_flights TYPE wd_this->element_flights..

DATA lt_flights TYPE wd_this->elements_flights

.

Lo_nd_flights = wd_context->get_child_node( name = wd_this->wdctx_flights ).

 

Ls_flights-carrid = ‘AA’.

Ls_filgts-connid = ‘0017’.

APPEND ls_flights TO lt_flights.

 

Ls_flights-carrid = ‘AA’.

Ls_filgts-connid = ‘0401’.

APPEND ls_flights TO lt_flights.

 

Lo_nd_flgihts->bind_table( new_items = lt_flights

                       Set_intital_elements = abap_true ).

Deleting elements from a context node

要在collection中删除elements,需要调用方法remove_element()。Element的reference必须传递给参数element。

总结:

动作

方法

创建一个新的element

Lo_el_<node> = lo_nd_<node>->create_element()

将element添加到collection

Lo_nd_<node>->bind_element(

     New_item = lo_el_<node>

     Set_intitial_elements = abap_false

)

将structure ls_<node>绑定到collection

DATA: ls_<node> TYPE wd_this->element_<node>.

….

Lo_nd_<node>->bind_structure(

   New_item = ls_<node>

   Set_initial_parameter = abap_false

)

将internal table lt_<node>绑定到collection

DATA:lt_<node> TYPE wd_this->elements_<node>.

…..

Lo_nd_<node>->bind_table(

New_items = lt_<node>

Set_intial_elements = abap_false

)

在collection中删除element

Ls_nd_<node>->remove_element(

        Element = lo_el_<node>

)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值