转:http://www.blogjava.net/Scott/archive/2007/07/11/129644.html
SearchContainer的用法说明
在Liferay中,列表通常是使用SearchContainer来实现的,如BBS的栏目列表等。在Liferay的源代码中,JSP夹杂了大量的本应在Action中实现的代码,因此导致很难看懂。我尝试写一个Portlet,结果就在JSP处耗费了很长时间。
在此简单总结一下SearchContainer的用法,内容有些不恰当。具体可参考message_boards/view.jsp中的代码。
1.1 概述
作为一个条目的列表,应该包括几个方面的内容:
l Table的标题行
l Table的内容
l 每一个条目允许的操作
l 分页
1.2 Table的标题行(不同的liferay版本可能有所不同,但实质是一样的)
标题行相对比较简单,核心代码如下:
List headerNames = new ArrayList();
headerNames.add("news.column");
headerNames.add("news.columndescript");
headerNames.add("news.childcolumns");
headerNames.add(StringPool.BLANK);
其中注意两点:
1、 每个标题,应该是i18n的资源,需要在资源文件language.properties中添加内容。
2、 最后一行,是用来显示可能的操作按钮的,不需要标题行。
1.3 创建SearchContainer
根据这个headerNames来创建SearchContainer。
首先需要生成一个PortletURL对象,并包括必要的参数
PortletURL portletURL = res.createRenderURL();
portletURL.setParameter("struts_action", "/ext/news/columnadmin/view");
portletURL.setParameter("columnId", columnId);
如果页面是分为多个Tab的,还需要将Tab也添加进去。
然后就可以创建SearchContainer
SearchContainer searchContainer = new SearchContainer(req, null, null,"column",
SearchContainer.DEFAULT_DELTA, portletURL,headerNames, null);
检查源代码,SearchContainer函数的定义为
SearchContainer(
RenderRequest req, //javax.portlet.RenderRequest
DisplayTerms displayTerms, //具体意义还不是很清楚,一般设置为null
DisplayTerms searchTerms, //具体意义还不是很清楚,一般设置为null
String curParam, //当前操作的列表,如果某个JSP页面中有两个列表需要分页,则此参数可以分别设置为“cur1”和“cur2”,暂时没发现有什么影响
int delta, //设置每页显示的记录数,默认的是20,可以修改此设置
PortletURL iteratorURL, //设置被循环的每条记录的操作URL
List headerNames, //设置表头信息
String emptyResultsMessage //当查询结果为空时,即数据库中无数据供列表显示时所显示的内容,如果设置为null,则列表表头也不显示出来,也可以设置为“暂无数据”等
)
这一步同创建headerNames应该是可以互换的,用searchContainer.setHeaderNames()即可。
1.4 Table的内容
主要由几个小步骤完成
1.4.1 设置总条数
searchContainer.setTotal(total);
1.4.2 直接设置查询结果
searchContainer.setResults(results)
变量是一个List,其中的每一个对象将会被用到下一个设置可执行操作的JSP中。
1.4.3 设置Table的显示条目
List resultRows = searchContainer.getResultRows();
for (int i = 0; i < results.size(); i++) {
NewsColumn cutColumn = (NewsColumn) results.get(i);
// 生成新的一个显示行
ResultRow row = new ResultRow(cutColumn, cutColumn.getPrimaryKey() .toString(), i);
// 设置URL
PortletURL rowURL = res.createRenderURL();
rowURL.setWindowState(WindowState.MAXIMIZED);
rowURL.setParameter("struts_action", "/ext/news/columnadmin/view");
rowURL.setParameter("columnId", cutColumn.getColumnId());
// 设置每一列的显示内容
row.addText(cutColumn.getName(), rowURL);
row.addText(cutColumn.getDescription(), rowURL);
row.addText(childCount), rowURL);
// 设置每一个条目的可用操作
row.addJSP("right", SearchEntry.DEFAULT_VALIGN, "*.jsp");
resultRows.add(row);
}
1.5 每一个条目允许的操作
通过row.addJSP("right", SearchEntry.DEFAULT_VALIGN, "column_action.jsp")来调用JSP显示相应的操作。
在JSP中,通过下面的语句能够获取当前条目的 model 对象
ResultRow row = (ResultRow)request.getAttribute(WebKeys.SEARCH_CONTAINER_RESULT_ROW);
MBCategory category = (MBCategory)row.getObject();
拿到model之后,通过<c:if test="<%= MBCategoryPermission.contains 方式判断权限,如果允许操作,则首先生成相应的portletURL,然后显示icon图标。
<c:if test="<%= MBCategoryPermission.contains(permissionChecker, category, ActionKeys.UPDATE) %>">
<portlet:renderURL windowState="<%= WindowState.MAXIMIZED.toString() %>" var="portletURL">
<portlet:param name="struts_action" value="/message_boards/edit_category" />
<portlet:param name="redirect" value="<%= currentURL %>" />
<portlet:param name="categoryId" value="<%= category.getCategoryId() %>" />
</portlet:renderURL>
<liferay-ui:icon image="edit" url="<%= portletURL %>" />
</c:if>
这部分代码涉及到Liferay的权限机制。
1.6 显示table和分页
显示table很简单,在JSP中
<liferay-ui:search-iterator searchContainer="<%= searchContainer %>" />
SearchContainer自身支持分页。以下几步
l 创建SearchContainer时设置每页显示的条数
构造函数SearchContainer的第四个参数int delta就是每页显示的条数,缺省使用SearchContainer.DEFAULT_DELTA,表示每页显示20条。我们可以用其他任何我们喜欢的数值。
l 从逻辑层取数据时提供begin和end参数
searchContainer.getStart() 和searchContainer.getEnd()
l 显示分页信息
<liferay-ui:search-paginator searchContainer="<%= searchContainer %>" />
注意:如果因为URL缺其他参数设置而导致分页后的页面不能正常显示,则可以在
<liferay-ui:search-iterator searchContainer="<%= searchContainer %>" />
<liferay-ui:search-paginator searchContainer="<%= searchContainer %>" />标签之间定义URL,并将需要的参数设置进去;
例如:
<liferay-ui:search-iterator searchContainer="<%= searchContainer %>" />
<%
//解决分页时点击下一页或是最后一页时显示的问题
PortletURL pUrl=renderResponse.createRenderURL();
pUrl=searchContainer.getIteratorURL();
pUrl.setParameter("curAction","viewMagazineEntry");
pUrl.setParameter("magazineTitleId",String.valueOf(magazineTitle.getMagazineTitleId()));
searchContainer.setIteratorURL(pUrl);
%>
<liferay-ui:search-paginator searchContainer="<%= searchContainer %>" />
说明:分页的那些标签(如:上一页,下一页,最后等等)只有当列表记录数达到或超过前面设置的每页显示最大记录条数时才被显示出来,否则隐藏。
分享到:
相关推荐
通过 `searchContainer.setTotal(total)` 方法来设定表格的总记录数,`total` 是一个整数值。 1.4.2 直接设置查询结果 使用 `searchContainer.setResults(results)` 来设置查询结果,`results` 是一个 List,包含了...
SearchContainer是Liferay Portal框架中用于构建数据...理解并熟练掌握SearchContainer的用法,对于开发高效、易维护的Liferay应用至关重要。在实际开发过程中,应结合Liferay文档和示例代码进行学习,以提高开发效率。
`README.md`是项目文档,通常包含项目简介、安装指南、使用方法等信息。对于这个Demo,它会解释如何运行和测试这个导航示例。 总的来说,这个Demo展示了如何在React Native中使用`navigator`进行基本的导航功能实现...
举例来说,一个简单的使用LIFERAY-UI:SEARCHCONTAINER的场景可能是创建一个用户友好的搜索界面,用户可以输入关键词并立即看到匹配的结果。通过配置搜索容器,可以定义搜索字段、过滤器、排序方式以及结果的展示样式...
例如,您可以使用`<liferay-ui:tabs>` 创建一个多部分的表单,每个部分都包含一个`<liferay-ui:section>`,并且在每个部分下方使用`<liferay-ui:pageIterator>` 显示搜索结果。在提交表单时,使用`...
JSPPortlet标签库提供了处理portlet交互的方法,比如处理portlet的渲染和动作请求。`<liferay-portlet:renderURL>`用于创建portlet渲染URL,而`<liferay-portlet:actionURL>`则用于生成portlet的动作URL,这两个标签...
使用 SearchContainer 设置条件并按列搜索/排序。 它不是Hibernate全文搜索,而是从前端通过延迟初始化按域模型进行搜索的真正有用的实用程序。 如何使用: 1. Create example of class SearchPaginatorHelper...
通过让React仅在使用该值的特定组件之间进行协调,可以实现快速更新。 受的想法启发-状态订阅(原子)减去所有其余部分。 只需一个状态值就可以共享并让组件挂接到其中,而无需更新整个子树。例子import { ...
function SEARCH_ENGINE(searchContainer, inputBox, resultBox, listItemClass) { // 初始化,绑定事件等操作 const searchEngine = new function() { // 数据处理,转换汉字为拼音等 // ... // 监听input...