Custom Tree View

    Здравствуйте Хабралюди!

    Сейчас буду рассказывать об одном «дереве».

    Зачем и почему нужны «деревья» – Вы знаете лучше меня.

    Понадобилось для одного проекта «дерево» (tree view).
    Известные реализации в порядке важности\значимости для лично меня:

    Т.е., можно сказать, что я на них «засматривался».

    UPD:
    Во-первых хочу отметить, что очень сильно уважаю приведенные примеры.
    Во-вторых, данный компонент по очень многим параметрам сильно проигрывает.
    В третьих — чтобы получить хотя бы что-то схожее с jsTree, например, нужно будет много своего кода написать.

    Но, тем не менее решил запилить свой компонент.

    Для самых нетерпеливых: ссылка на пример в работе.




    Основные features:
    • Всё дерево запрашивается
    • Запрашивается частями
    • Подгружается в указанные узлы
    • Очень многое сильно настраивается
    • Практически «везде» есть поведение «по умолчанию»
    • Сохранение состояния через cookie
    • Независимость от backend
    • Think by Youself
    • etc.


    Основные anti-features:
    • Всё дерево запрашивается
    • Запрашивается частями
    • Подгружается в указанные узлы
    • Это «что-то новое»
    • Независимость от backend
    • Компоненту «без году неделя» – сыровато
    • В source нет comments
    • Think by Youself
    • etc.


    Есть какая-никакая документация там же.

    Частично приведу её здесь:

    $('#tree_content_div').treeControl( {
    	// как будет выглядеть запрос верхнего уровня
    	  root		: 'top'
    
    	// callback, который вернет "имя" листа
    	, name		: function( obj ){ return obj.name; }
    
    	// название темы в CSS
    	, theme		: 'custom'
    
    	// callback, где можно вывести некоторые messages
    	, info		: function( data ){ alert(data); }
    
    	// скорость анимации
    	, animate	: 1500
    
    	// лучше посмотреть доку
    	, preloader	: 2
    
    	// классы 
    	, classes	: {
    		  treeLeaf	: 'tree-leaf'
    		, heading	: 'heading'
    		, control	: 'control'
    		, status	: 'status'
    		, loader	: 'loader'
    		, selected	: 'selected'
    		, preloader	: 'preloader'
    		, hover		: 'hover'
    	}
    
    
    	// лучше посмотреть доку
    	, control		: { text : ['+', '–'], cls : 'open' }
    
    	// $.tmpl() шаблон узла
    	, template		: 
    		'<li><span class = "heading">${obj.name}</span>
    			<ul class = "tree-leaf"></ul></li>'
    			
    	// шаблон управляющего элемента +\- НЕ $.tmpl()
    	, ctrlTpl		: '<span class = "control"></span>'
    
    	// шаблон дополнительного элемента "статуса"    НЕ $.tmpl()
    	, statusTpl		: '<span class = "status"></span>'
    
    	// можно bind на управление, выделение, 
    	// потерю выделения, добавление узла
    	, handlers		: {
    		  control	: function( leaf ){ }
    		, select	: function( leaf ){ }
    		, blur		: function( leaf , result ){ 
    			if (something){
    				// Your Great Checking / Blocking code
    			}else{
    				result(); 
    			}
    		}
    		, leafsAdd	: function( leaf ,  controlObject ){ }
    	}
    
    	// можно bind на ... понятно
    	, callbacks		{
    		  click		: function( leaf ){ }
    		, mouseover	: function( leaf ){ }
    		, mouseout	: function( leaf ){ }
    	}
    	
    	// сохранять или нет состояние, зависит от наличия $.cookie
    	// если saveState не определен -- ничего не будет храниться
    	, saveState		: {
    		  name	: 'tree_control_cookie_name'
    		, opts	: { expires: 150 }
    	}
    	
    	// самая сложная часть -- то, что возвращает узлы, см пример:
    	, ws			: function( val, callback ){
    
    	try{
    		var val = ( typeof( val ) == 'string' ) ? 
    			{ 'leaf' : val , action : 'get' } : 
    				( ( typeof( val ) == 'object' ) ?
    					val : false );
    		if( val ){
    			$.ajax( {
    			
    			  type: "POST"
    			, async: true
    			, data : val
    			, dataType : 'text'
    			, url: './tree.php'
    			, success: 
    			function( data ){ 
    				if( data !== ''){ callback( data ); } 
    			}
    			, error: function(data){ alert(data); }
    			
    			} ) ;
    		}
    	}catch(e){ alert(e); }
    
    	}
    	
    	
    } );
    


    Что такое leaf:

    /*
    {
    	name 	: 'leaf.name from JSON received through 'ws', e.g. ID'
    	obj		: {
    		  name		: ' returned by x.name( leaf ) '
    		, children	: ' array of leafs that are children of this '
    		, parent	: 'link to parent'
    		, obj		: 'JSON that comes from ws'
    		, elem		: {
    			  li		: DOM of this leaf's LI 
    			, ul		: DOM of this leaf's UL 
    					(where children are)
    			, heading	: DOM of heading span
    			, control	: DOM of control span
    			, status	: DOM of status span
    		}
    	}
    }
    */
    


    Т.к. там всё, вроде бы – просто, то жду q & a в comment'ы.
    Share post
    AdBlock has stolen the banner, but banners are not teeth — they will be back

    More
    Ads

    Comments 10

      +3
      зачем [-] показывать, если нету чайлдов?
      имхо подсознательно воспринимается как — «свернуть», а сворачивать то — нечего
        0
        Это можно переопределить, если при декларации написать

            handlers.control( leaf )
        


        Нужно будет проверять, есть ли у узла чайлды, и переписывать

            // проверка чайлдов
            leaf.obj.children !== 0
        
            // запишем что-то новое в 
            leaf.elem.control.html(' *** ')
        


        И нужно так же на добавление листа подписаться

            handlers.leafsAdd( leaf, controlObject )
        


        А можно вообще

            x,control		: { text : ['', ''], cls : 'open' }
        


        И тогда в

        .tree-leaf { наша одна картинка }
        .tree-leaf.open { наша другая картинка }
        
        +1
        А я че-т так и не понял чем вас не устраивали приведенные вами же примеры.
        Я использую jsTree с grid плагином: jstree-grid
        Давайте подробнее… что конкретно вам не хватало? Потому как все ваши плюсы есть в уже готовых реализациях
          0
          :)

          Cделал в начале UPD c кратким ответом.

          >> Потому как все ваши плюсы есть в уже готовых реализациях >>

          Спорить не буду, есть.

          >> что конкретно вам не хватало? >>

          • Своего собственного маленького удобного мне компонента
          • ЧСВ от того, что я могу сделать нечто подобное
          • Некоторой свободы, т.к. код того же jsTree мне в той ситуации показался немного больше необходимого минимума


          Сделал UPD в начало.
          +1
          if( data !== ''){ callback( data ); }
          можно заменить на
          data && callback( data );
            0
            Да, там не везде эта конструкция.
            С другой стороны — неофиту проще если IF виден.
            :)
            0
            Форматирование кода какое-то диковатое, лично для меня.
              0
              Дело вкуса )
              –1
              использовали jstree для отображения дерева продукции:
              vitrage-mebel.com.ua/
                +1
                У меня тоже всё началось с jstree.
                Его было «слишком много».

                Хотя компонент, конечно — чумовой :)

              Only users with full accounts can post comments. Log in, please.