代码之家  ›  专栏  ›  技术社区  ›  Daniel Sloof

安卓TreeView

  •  40
  • Daniel Sloof  · 技术社区  · 15 年前

    我知道有 ExpandableListView 但它最多只能支持两个级别。我需要一个真正的TreeView垂直列表,至少有5个级别(越多越好)。

    有什么建议吗?

    编辑:

    我看到了关于使用自定义适配器和基于项级别设置填充的讨论。

    我有一个具有ID和父ID的未排序的对象数组列表,我还动态地向这个数组添加项。

    有人能给我举几个例子说明我该怎么做吗?

    10 回复  |  直到 7 年前
        1
  •  16
  •   bmelnychuk    11 年前

    我也有同样的问题。您可以查看我的实现 androidtreeview

    .

    • 它的n级树。

    • 节点的自定义样式

    • 旋转后保存状态

    AndroidTreeView

        2
  •  14
  •   Jarek Potiuk    14 年前

    我们公司也为此开放了一个解决方案。它作为库提供,因此非常容易使用: http://code.google.com/p/tree-view-list-android/

    是的,非常容易使用: http://code.google.com/p/tree-view-list-android/

    enter image description here

        3
  •  10
  •   Community Mohan Dere    8 年前

    我为自己解决了这个问题,在一个类似的主题中发布: 其他线程

    enter image description here

        4
  •  6
  •   yakhtarali Daniel Sloof    10 年前

    回答我自己的问题,因为我们几个月前实施了这个。

    Our implementation 在开源项目中。

        5
  •  4
  •   Aaron Gillion    11 年前

    我找到了一个 更容易的 解决这个问题的方法,因为我自己在编码技能方面有点中级。在我的情况下,我需要一个 窗口主题 树视图,经过头脑风暴的想法,我能够实现几乎没有任何编码!

    诀窍是:使用 WebVIEW 以及一个嵌入的HTML页面,用于显示自定义树视图,并使用Android的超级便捷的javascript通信界面接收选择和单击: Proof of Concept Example on Android-er Blog

    有了这种能力,我们就可以利用Web上大量的JS/CSS控制片段。 Themeable Windows7-Style jQuery TreeView control -- jsTree

    有了Android,很多的可能性和力量,快乐的编码!

        6
  •  3
  •   dbm    15 年前

    我发现下面的链接非常非常有用。它描述了将树结构存储在二维数据结构(通常是数据库表)中的替代方法。

    我认为你会发现这个范例很容易理解和实现。

    http://mikehillyer.com/articles/managing-hierarchical-data-in-mysql/

    至于如何在Android中可视化这是另一个问题。如果“填充”列表项解决方案不够,我可能会从头开始编写自己的小部件。

        7
  •  3
  •   dotsa    13 年前

    我认为,如果多级可扩展列表做得好,它实际上是有效的,看起来很棒。 以下是 http://code.google.com/p/tree-view-list-android的另一个示例/

    看起来很棒。 下面是另一个例子 http://code.google.com/p/tree-view-list-android/

    enter image description here

        8
  •  2
  •   Ted Hopp    15 年前

    我同意PJV,至少对于手机大小的设备。最好组织小部件在ListView中一次显示一组兄弟姐妹。这可以在跟踪树中位置的单个活动中完成。它可以显示一个标题,其中面包屑显示当前显示项的父级路径。

    多层次树视图可能适合平板电脑设备,但手机没有足够的房地产来支持建议的5个层次(所有的东西都必须足够大才能容纳手指)。

    不过,如果您是在树视图上设置的,则不要查看子类化的ExpandableListView。它通过将父索引和子索引(每一个int)打包为单个long进行内部操作。这种内部表示实际上不可能扩展到2个级别以上。

        9
  •  2
  •   abatishchev Karl Johan    15 年前
    package com.expand.search;
    
    import android.app.ExpandableListActivity;
    import android.os.Bundle;
    import android.view.ContextMenu;
    import android.view.Gravity;
    import android.view.MenuItem;
    import android.view.View;
    import android.view.ViewGroup;
    import android.view.ContextMenu.ContextMenuInfo;
    import android.widget.AbsListView;
    import android.widget.BaseExpandableListAdapter;
    import android.widget.ExpandableListAdapter;
    import android.widget.ExpandableListView;
    import android.widget.TextView;
    import android.widget.Toast;
    import android.widget.ExpandableListView.ExpandableListContextMenuInfo;
    
       /** Demonstrates expandable lists using a custom {@link ExpandableListAdapter}
        * from {@link BaseExpandableListAdapter}.
       */
    public class expands extends ExpandableListActivity {
    
    ExpandableListAdapter mAdapter;
    
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    
        // Set up our adapter
        mAdapter = new MyExpandableListAdapter();
        setListAdapter(mAdapter);
        registerForContextMenu(getExpandableListView());
    }
    
    @Override
    public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
        menu.setHeaderTitle("Sample menu");
        menu.add(0, 0, 0, R.string.expandable_list_sample_action);
    }
    
    @Override
    public boolean onContextItemSelected(MenuItem item) {
        ExpandableListContextMenuInfo info = (ExpandableListContextMenuInfo) item.getMenuInfo();
    
        String title = ((TextView) info.targetView).getText().toString();
    
        int type = ExpandableListView.getPackedPositionType(info.packedPosition);
        if (type == ExpandableListView.PACKED_POSITION_TYPE_CHILD) {
            int groupPos = ExpandableListView.getPackedPositionGroup(info.packedPosition); 
            int childPos = ExpandableListView.getPackedPositionChild(info.packedPosition); 
            Toast.makeText(this, title + ": Child " + childPos + " clicked in group " + groupPos,   
                    Toast.LENGTH_SHORT).show();
            return true;
        } else if (type == ExpandableListView.PACKED_POSITION_TYPE_GROUP) {
            int groupPos = ExpandableListView.getPackedPositionGroup(info.packedPosition); 
            Toast.makeText(this, title + ": Group " + groupPos + " clicked", Toast.LENGTH_SHORT).show();
            return true;
        }
    
        return false;
    }
    
    /** A simple adapter which maintains an ArrayList of photo resource Ids. 
     * Each photo is displayed as an image. This adapter supports clearing the
     * list of photos and adding a new photo.
     */
    public class MyExpandableListAdapter extends BaseExpandableListAdapter {
        // Sample data set.  children[i] contains the children (String[]) for groups[i].
        private String[] groups = { "Category1", "Category2", "Category3", "Category4" };
        private String[][] children = {
                { "Charity1", "Charity2", "Charity3", "Charity4" },
                { "Charity5", "Charity6", "Charity7", "Charity8" },
                { "Charity9", "Charity10" },
                { "Charity11", "Charity12" }
        };
    
        public Object getChild(int groupPosition, int childPosition) {
            return children[groupPosition][childPosition];
        }
    
        public long getChildId(int groupPosition, int childPosition) {
            return childPosition;
        }
    
        public int getChildrenCount(int groupPosition) {
            return children[groupPosition].length;
        }
    
        public TextView getGenericView() {
            // Layout parameters for the ExpandableListView
            AbsListView.LayoutParams lp = new AbsListView.LayoutParams(
                    ViewGroup.LayoutParams.MATCH_PARENT, 64);
    
            TextView textView = new TextView(expands.this);
            textView.setLayoutParams(lp);
            // Center the text vertically
            textView.setGravity(Gravity.CENTER_VERTICAL | Gravity.LEFT);
            // Set the text starting position
            textView.setPadding(36, 0, 0, 0);
            return textView;
        }
    
        public View getChildView(int groupPosition, int childPosition, boolean isLastChild,
                View convertView, ViewGroup parent) {
            TextView textView = getGenericView();
            textView.setText(getChild(groupPosition, childPosition).toString());
            return textView;
        }
    
        public Object getGroup(int groupPosition) {
            return groups[groupPosition];
        }
    
        public int getGroupCount() {
            return groups.length;
        }
    
        public long getGroupId(int groupPosition) {
            return groupPosition;
        }
    
        public View getGroupView(int groupPosition, boolean isExpanded, View convertView,
                ViewGroup parent) {
            TextView textView = getGenericView();
            textView.setText(getGroup(groupPosition).toString());
            return textView;
        }
    
        public boolean isChildSelectable(int groupPosition, int childPosition) {
            return true;
        }
    
        public boolean hasStableIds() {
            return true;
        }
    }
    

    }

        10
  •  1
  •   Ginger McMurray    15 年前

    我首先要让数据结构更能代表它所包含的内容。因为您有一个项目数组,每个子项都可以有自己的项目数组,每个子项都有自己的数组等等。我考虑使用一个包含两个成员的类:一个表示此特定项目的数据的对象和一个包含该项目子项的数组。每个孩子本身就是类的一个实例,这样它也可以有孩子。

    私人班级家长和孩子{ 对象父; 阵列儿童; }

    然后,适配器将有一个代表顶层的parentandkids对象数组。您将添加和删除基于展开父项的列表项。