Search code examples
c#recursionflickr

Load a Flickr tree as html recursive in C#


I'm currently trying to render a tree of Flickr Collections and Sets as HTML from C#. I'm using the Flickr.NET library to a list of all my collections with their childcollections and sets.

What I need to do is to render this tree as a HTML tree using nested unordered lists and I'm thinking of a recursive solution since a Collection can hold one or more sets and also hold child collections which again can hold sets and collections.

What I have right now is a list of all the root collections, their childcollections and their sets. So i.e. my Flickr tree looks like this:

  • Collection (this collection is in my list as an object itself)

    • Collection

      • Set
        • Photo1
        • Photo2
      • Set
        • Photo1
        • Photo2
    • Collection

      • Set
        • Photo1
        • Photo2
      • Set
        • Photo1
        • Photo2
  • Collection (this collection is in my list as an object itself)

    • Collection

      • Set
        • Photo1
        • Photo2
      • Set
        • Photo1
        • Photo2
    • Collection

      • Set
        • Photo1
        • Photo2
      • Set
        • Photo1
        • Photo2

And basically it could looks a hundred more ways since editors will eventually create a number more Collections within collections and sets within sets.

So, for every collection and set, I need a new nested unordered list.

I know this is quite complex, but nonetheless, it would be great to have an algorithm to render the tree as HTML. I've just become a tad too rusty when it comes to recursive algorithms :-/

I guess my basecase here is if the current collection doesn't have any childcollections and doesn't have any, then I can stop the recursive method?

Any help/hint on this is greatly appreciated!

Thanks a lot in advance.

All the best,

Bo

SOLUTION

I broke down the algorithms in four steps:

private void LoadFlickrTreeRecursive()
    {
        foreach (var collection in allCollections)
        {
            flickrTreeMarkup.Append("<ul class='collection'>");
            flickrTreeMarkup.Append("<li>" + collection.Title + "</li>");
            if (collection.Sets.Count > 0)
                RenderFlickPhotoSet(collection.Sets);

            if (collection.Collections.Count > 0)                
                RenderFlickrCollectionRecursive(collection.Collections);                    

            flickrTreeMarkup.Append("</ul>");
        }
    }

    private void RenderFlickPhotoSet(System.Collections.ObjectModel.Collection<CollectionSet> sets)
    {
        foreach (var set in sets)
        {
            flickrTreeMarkup.Append("<ul class='set'>");
            flickrTreeMarkup.Append("<li>" + set.Title + "</li>");
            var photos = flickr.PhotosetsGetPhotos(set.SetId);
            if (photos.Count > 0)
            {
                flickrTreeMarkup.Append("<ul class='photos'>");
                foreach (var photo in photos)
                {
                    flickrTreeMarkup.Append("<li>" + photo.Title + "</li>");
                }
                flickrTreeMarkup.Append("</ul>");
            }
            flickrTreeMarkup.Append("</ul>");                 
        }
    }

    private void RenderFlickrCollectionRecursive(System.Collections.ObjectModel.Collection<Collection> collections)
    {
        foreach (var collection in collections)
        {
            flickrTreeMarkup.Append("<ul class='collection'>");
            flickrTreeMarkup.Append("<li>" + collection.Title + "</li>");
            RenderFlickPhotoSet(collection.Sets);
            if (collection.Collections.Count > 0)
            {                    
                RenderFlickrCollectionRecursive(collection.Collections);                    
            }
            flickrTreeMarkup.Append("</ul>");                
        }            
    }

Works like a charm :-)

However, if anyone know of a better way than this, please let me know. Thanks!


Solution

  • This algorithm should work with a TreeView control:

    function rec(Collection c, TreeNode n)
    {
       TreeNode me = new TreeNode();
       n.ChildNodes.Add(me);
       for each collection v in c:
           rec(v, me)
       for each set s in c:
           AddSet(s, me)
    }