Issue 329: Add option to use custom icon classes
Status:  Done
Owner: ----
Closed:  Oct 2013
Reported by tarjei.h...@gmail.com, Jul 12, 2012
Hi, I would like the posibility to instead of defining an image for an icon to just suggest different classes for the icon span. 

This would make it easy to add custom icons from a separate sprite etc.
Jul 13, 2012
Project Member #1 moo...@wwwendt.de
This is already possible, see the 'theming' example:
  http://wwwendt.de/tech/dynatree/doc/sample-theming.html

add a custom class

  <li data="isFolder: true, addClass:'custom2'">Folder with custom class 2

and create a css rule

  span.custom2 span.dynatree-icon {
    background-position: 0 0;
    background-image: url("folder_page.gif");
  }

Status: Invalid
Labels: Milestone-Release1.2.2
Jul 15, 2012
#2 tarjei.h...@gmail.com
The problem with this solution is that it does not support using Bootstrap's generic icon css classes.
Jul 15, 2012
Project Member #3 moo...@wwwendt.de
I don't know about Bootstrap. Please give more Details on the requirements
Jul 15, 2012
#4 tarjei.h...@gmail.com
0 problem :)

Twitter bootstrap (http://twitter.github.com/bootstrap/) defines icons very easily using a inline item (like you do) and a class linked to that item. F.x.:

<i class="icon-folder"></i>Some text.

By being able to set the icon class it would be possible to use Bootstrap for themes directly.

Kind regards - and thanks for a nice product!

Tarjei
Jul 16, 2012
Project Member #5 moo...@wwwendt.de
See 
    http://twitter.github.com/bootstrap/base-css.html#icons

Maybe a new data option
    data={iconClass: 'icon-folder'}
would do it.

Another aproach could be that we still use 
    data={addClass: 'icon-folder'}
but extend the parser to handle class names starting with 'icon-' this way.
That would allow to pass it with <ul> initialization:
 <div id="tree">
    <ul id="treeData" style="display: none;">
      <li id="id1" class="icon-book">item1 with key and tooltip

jQuery themeroller also has predefined icon sets, that are used like so
    <span class="ui-icon ui-icon-suitcase"></span>
so the prefix 'ui-icon-' should also be considered.

Anyway this markup to be generated:

<span class="dynatree-node dynatree-has-children dynatree-lastsib dynatree-exp-cl dynatree-ico-c">
    <span class="dynatree-expander"></span>
    <span class="dynatree-checkbox"></span>
    <span class="dynatree-icon icon-folder"></span>   ***** class added here
    <a href="#" class="dynatree-title">Sub-item 4.2</a>
</span>

Status: New
Jul 16, 2012
#6 tarjei.h...@gmail.com
Looks good!
Jul 19, 2012
#7 tarjei.h...@gmail.com
Quick patch suggestion:

@@ -219,6 +219,8 @@ DynaTreeNode.prototype = {
                } else if ( data.icon === false ) {
                        // icon == false means 'no icon'
                        noop(); // keep JSLint happy
+        } else if ( data.iconClass ) {
+                       res +=  "<span class='" + " " + data.iconClass +  "'></span>";
                } else {
                        // icon == null means 'default icon'
                        res += cache.tagNodeIcon;
Oct 3, 2012
Project Member #8 moo...@wwwendt.de
(No comment was entered for this change.)
Status: Accepted
Oct 7, 2012
Project Member #9 moo...@wwwendt.de
(No comment was entered for this change.)
Labels: -Milestone-Release1.2.2 Milestone-Release1.2.x
Oct 6, 2013
Project Member #10 moo...@wwwendt.de
(No comment was entered for this change.)
Status: Done
Labels: -Milestone-Release1.2.x Milestone-Release2.0
Nov 26, 2013
#11 Werti...@gmail.com
As far as I can tell, the above change will not work, because the condition will allways fall into } else if ( data.icon === false ) { before the iconClass condition. 

Here is a suggested change, where I've moved the iconClass condition up: 
@@ -271,11 +271,11 @@
 				imageSrc = opts.imagePath + data.icon;
 			}
 			res += "<img src='" + imageSrc + "' alt='' />";
+		} else if ( data.iconClass ) {
+			res +=  "<span class='" + " " + data.iconClass +  "'></span>";
 		} else if ( data.icon === false ) {
 			// icon == false means 'no icon'
 //			noop(); // keep JSLint happy
-		} else if ( data.iconClass ) {
-			res +=  "<span class='" + " " + data.iconClass +  "'></span>";
 		} else {
 			// icon == null means 'default icon'
 			res += cache.tagNodeIcon;
Nov 26, 2013
Project Member #12 moo...@wwwendt.de
It's only a matter of precedence. 
Why do you want to set data.icon = false (which is defined as "hide the icon altogether") in addition to data.iconClass?
Dec 3, 2013
#13 Werti...@gmail.com
@12
My bad. I wasn't aware that data.icon is null until set explicitly to an icon or false, and therefore actually can enter the iconClass logic. 

I am using 
$.ui.dynatree.nodedatadefaults["icon"] = false; // Turn off icons by default
Because I only want to show an icon for nodes that actually has an icon associated with it. 
(Think file-type icons like pdf, word etc).

So instead of changing the code, you should use data.icon = null (or not change it) in conjunction with data.iconClass, if you want to use icons via classes.