我的Rails应用程序中有以下记录:
id: 1
name: 'About'
slug: 'about'
permalink: '/about'
parent_id: null
id: 2
name: 'Team'
slug: 'team'
permalink: '/about/team'
parent_id: 1
id: 3
name: 'Cameron'
slug: 'cameron'
permalink: '/about/team/cameron'
parent_id: 2
我将它们显示在这样的列表中:
<ul>
<% @pages.each do |page| %>
<li>
<%= page.parent.title rescue '' %><br>
<%= page.permalink %>
</li>
<% end %>
</ul>
这会创建一个列表:
<ul>
<li>About<br>/about</li>
<li>Team<br>/about/team</li>
<li>Cameron<br>/about/team/cameron</li>
</ul>
但是我想创建一个如下所示的嵌套列表,它使用parent_id对它们进行分组。
<ul>
<li>About<br>/about</li>
<li>-- Team<br>/about/team</li>
<li>---- Cameron<br>/about/team/cameron</li>
</ul>
是否有一种快速简便的方法可以将它们分组到控制器中?
我想出的最好的想法是在控制器中执行此操作:
@pages = Page.where(parent_id: nil)
然后在视图中:
<% @pages.each do |page| %>
<%= render 'page_row', :page => page, :sub => 0 %>
<% page.pages.each do |page| %>
<%= render 'page_row', :page => page, :sub => 1 %>
<% page.pages.each do |page| %>
<%= render 'page_row', :page => page, :sub => 2 %>
<% page.pages.each do |page| %>
<%= render 'page_row', :page => page, :sub => 3 %>
<% end %>
<% end %>
<% end %>
<% end %>
使用partial来创建嵌套:
<%
$i = 0
$num = sub
prefix = ''
while $i < $num do
prefix += '---'
$i +=1
end
%>
<li>
<%= prefix %> <%= page.parent.title rescue '' %><br>
<%= page.permalink %>
</li>
但是通过像我一直在做的那样手动循环,它将嵌套限制为只有4级深度并且代码不是很好。
如何才能实现相同的结果,但没有手动循环来创建页面的嵌套视图?
答案 0 :(得分:3)
我要做的是在模型中为同一个模型创建一个引用,也就是说:
has_many :pages, foreign_key: 'parent_id'
然后得到所有顶级父母:
@parents = Page.where(parent_id: nil)
然后在视图中加载每个父项的所有子项:
@parents.each { |p| p.pages.each { |c| ... } }
这种结构也在this SO thread中解释。
答案 1 :(得分:2)
我认为你是在正确的轨道上,但不是循环固定的次数,整个视图应该是递归的。
在控制器中:@top_level_pages = Page.where(parent_id: nil)
在视图中
<%= render 'pages', pages: @top_level_pages, level: 0 %>
在页面部分
中<% pages.each do |page| %>
<li>
<%= '-' * level %><%= page.name %><br>
<%= page.permalink %>
</li>
<%= render 'pages', pages: pages.pages, level: level + 1 %>
<% end %>
答案 2 :(得分:0)
在我看来,您应该创建一个新类,负责构建一个树结构(JSON或哈希),以减少视图层所需逻辑的方式封装数据。
new Thread(new Runnable() {
@Override
public void run() {
boolean downloading = true;
while (downloading) {
DownloadManager.Query q = new DownloadManager.Query();
q.setFilterById(downloadId);
Cursor cursor = downloadManager.query(q);
cursor.moveToFirst();
int bytes_downloaded = cursor.getInt(cursor
.getColumnIndex(DownloadManager.COLUMN_BYTES_DOWNLOADED_SO_FAR));
int bytes_total = cursor.getInt(cursor.getColumnIndex(DownloadManager.COLUMN_TOTAL_SIZE_BYTES));
if (cursor.getInt(cursor.getColumnIndex(DownloadManager.COLUMN_STATUS)) == DownloadManager.STATUS_SUCCESSFUL) {
downloading = false;
}
final int dl_progress = (int) ((bytes_downloaded * 100l) / bytes_total);
((Activity) mContext).runOnUiThread(new Runnable() {
@Override
public void run() {
holder.mTextView.setText(String.valueOf(dl_progress) + "%");
}
});
cursor.close();
}
}
}).start();
在视图中,我将使用partial来定义每个级别的表示 - 生成下一个较低级别,再次调用partial并传入:children。让部分处理迭代遍历该级别的元素,以及其中:children存在,再次将它们传递给partial。