dropsite 0.2.1 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/Rakefile +12 -3
- data/bin/dropsite +1 -34
- data/dropsite.gemspec +1 -1
- data/lib/dropsite/application.rb +93 -0
- data/lib/dropsite/dir_renderer.rb +23 -25
- data/lib/dropsite/plugins/image_thumbnails/assets/css/image_thumbnails.css +87 -0
- data/lib/dropsite/plugins/image_thumbnails/assets/css/reset.css +30 -0
- data/lib/dropsite/plugins/image_thumbnails/assets/images/icons/directory-large.png +0 -0
- data/lib/dropsite/plugins/image_thumbnails/assets/images/icons/directory.png +0 -0
- data/lib/dropsite/plugins/image_thumbnails/assets/images/row-bg.png +0 -0
- data/lib/dropsite/plugins/image_thumbnails/image_thumbnails.erb +49 -0
- data/lib/dropsite/plugins/image_thumbnails/image_thumbnails.rb +65 -0
- data/lib/dropsite/plugins/simple_index/simple_index.erb +1 -1
- data/lib/dropsite/plugins/simple_index/simple_index.rb +1 -1
- data/lib/dropsite/render_helper.rb +60 -22
- data/lib/dropsite/site.rb +30 -28
- data/lib/dropsite/site_dir.rb +84 -32
- data/lib/dropsite/site_file.rb +12 -11
- data/lib/dropsite.rb +34 -9
- data/test/fixtures/many_folders_public/one/two/three/four/five/six/seven/eight/file.txt +1 -0
- data/test/helper.rb +17 -4
- data/test/{test_write_site.rb → integration/test_process_site.rb} +31 -44
- data/test/integration/test_process_site_many_folders.rb +18 -0
- data/test/integration/test_process_site_with_thumbnails.rb +40 -0
- data/test/unit/test_application.rb +19 -0
- data/test/unit/test_config_file.rb +34 -0
- data/test/{test_render_helper.rb → unit/test_render_helper.rb} +13 -13
- data/test/{test_site.rb → unit/test_site.rb} +19 -3
- data/test/unit/test_site_dir.rb +31 -0
- data/test/{test_site_file.rb → unit/test_site_file.rb} +9 -9
- metadata +27 -19
- data/lib/dropsite/plugins/simple_index/assets/simple_index.js +0 -3
- data/test/test_site_dir.rb +0 -20
    
        data/Rakefile
    CHANGED
    
    | @@ -2,12 +2,21 @@ require 'rake' | |
| 2 2 | 
             
            require 'rake/testtask'
         | 
| 3 3 | 
             
            require 'rake/rdoctask'
         | 
| 4 4 |  | 
| 5 | 
            -
            Rake::TestTask.new do |t|
         | 
| 5 | 
            +
            Rake::TestTask.new("test:units") do |t|
         | 
| 6 6 | 
             
              t.libs << 'lib'
         | 
| 7 | 
            -
              t. | 
| 7 | 
            +
              t.libs << '.'
         | 
| 8 | 
            +
              t.pattern = 'test/unit/**/test_*.rb'
         | 
| 8 9 | 
             
            end
         | 
| 9 10 |  | 
| 10 | 
            -
             | 
| 11 | 
            +
            Rake::TestTask.new("test:integration") do |t|
         | 
| 12 | 
            +
              t.libs << 'lib'
         | 
| 13 | 
            +
              t.libs << '.'
         | 
| 14 | 
            +
              t.pattern = 'test/integration/**/test_*.rb'
         | 
| 15 | 
            +
            end
         | 
| 16 | 
            +
             | 
| 17 | 
            +
            task :test => ['test:units', 'test:integration']
         | 
| 18 | 
            +
             | 
| 19 | 
            +
            task :default => 'test:units'
         | 
| 11 20 |  | 
| 12 21 | 
             
            begin
         | 
| 13 22 | 
             
              require 'rcov/rcovtask'
         | 
    
        data/bin/dropsite
    CHANGED
    
    | @@ -1,38 +1,5 @@ | |
| 1 1 | 
             
            #!/usr/bin/env ruby
         | 
| 2 | 
            -
             | 
| 3 | 
            -
            require 'optparse'
         | 
| 4 | 
            -
             | 
| 5 | 
            -
            # TODO: take this out later
         | 
| 6 2 | 
             
            $:.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
         | 
| 7 3 | 
             
            require 'dropsite'
         | 
| 8 | 
            -
            include Dropsite
         | 
| 9 | 
            -
             | 
| 10 | 
            -
            options = {
         | 
| 11 | 
            -
              :quiet => false
         | 
| 12 | 
            -
            }
         | 
| 13 | 
            -
             | 
| 14 | 
            -
            OptionParser.new do |opts|
         | 
| 15 | 
            -
              opts.on('-d', '--dropbox-home [PATH]', 'Specify Dropbox directory') {|path| options[:dropbox_home] = path }
         | 
| 16 | 
            -
              opts.on('-q', '--quiet', 'Suppress site processing output') {|| options[:quiet] = true }
         | 
| 17 | 
            -
              opts.on_tail('-h', '--help', 'Show this message') do
         | 
| 18 | 
            -
                puts opts
         | 
| 19 | 
            -
                exit
         | 
| 20 | 
            -
              end
         | 
| 21 | 
            -
              opts.on_tail('--version', 'Show version') do
         | 
| 22 | 
            -
                puts "Dropsite version: #{Dropsite::VERSION}"
         | 
| 23 | 
            -
                exit
         | 
| 24 | 
            -
              end
         | 
| 25 | 
            -
            end.parse!
         | 
| 26 | 
            -
             | 
| 27 | 
            -
            options[:dropbox_home] = Dropsite.find_dropbox_dir if not options[:dropbox_home]
         | 
| 28 | 
            -
             | 
| 29 | 
            -
            if !options[:dropbox_home] || !File.exist?(options[:dropbox_home])
         | 
| 30 | 
            -
              $stderr.puts 'Dropbox home directory cannot be found or does not exist'
         | 
| 31 | 
            -
              $stderr.puts 'Set valid directory with --dropbox-home DIRECTORY'
         | 
| 32 | 
            -
              exit 1
         | 
| 33 | 
            -
            end
         | 
| 34 | 
            -
             | 
| 35 | 
            -
            options[:public_dir] = File.join(options[:dropbox_home], 'Public')
         | 
| 36 4 |  | 
| 37 | 
            -
             | 
| 38 | 
            -
            site.process
         | 
| 5 | 
            +
            Dropsite::Application.new.run
         | 
    
        data/dropsite.gemspec
    CHANGED
    
    
| @@ -0,0 +1,93 @@ | |
| 1 | 
            +
            require 'optparse'
         | 
| 2 | 
            +
            require 'ostruct'
         | 
| 3 | 
            +
            require 'yaml'
         | 
| 4 | 
            +
             | 
| 5 | 
            +
            module Dropsite
         | 
| 6 | 
            +
              class Application
         | 
| 7 | 
            +
                def run
         | 
| 8 | 
            +
                  handle_options
         | 
| 9 | 
            +
             | 
| 10 | 
            +
                  options.dropbox_home = Dropsite.dropbox_dir if not options.dropbox_home
         | 
| 11 | 
            +
             | 
| 12 | 
            +
                  if !options.dropbox_home || !File.exist?(options.dropbox_home)
         | 
| 13 | 
            +
                    $stderr.puts 'Dropbox home directory cannot be found or does not exist'
         | 
| 14 | 
            +
                    $stderr.puts 'Set valid directory with --dropbox-home DIRECTORY'
         | 
| 15 | 
            +
                    exit 1
         | 
| 16 | 
            +
                  end
         | 
| 17 | 
            +
             | 
| 18 | 
            +
                  if options.create_config_dir
         | 
| 19 | 
            +
                    create_config_dir
         | 
| 20 | 
            +
                  else
         | 
| 21 | 
            +
                    options.public_dir = File.join(options.dropbox_home, 'Public')
         | 
| 22 | 
            +
                    cf = ConfigFile.new.read
         | 
| 23 | 
            +
                    options.exclude = cf.exclude if cf.exist?
         | 
| 24 | 
            +
                    site = Dropsite::Site.new(options)
         | 
| 25 | 
            +
                    site.process
         | 
| 26 | 
            +
                  end
         | 
| 27 | 
            +
                end
         | 
| 28 | 
            +
             | 
| 29 | 
            +
                def options
         | 
| 30 | 
            +
                  @options ||= OpenStruct.new
         | 
| 31 | 
            +
                end
         | 
| 32 | 
            +
             | 
| 33 | 
            +
                def create_config_dir
         | 
| 34 | 
            +
                  if Dropsite.dropsite_config_dir
         | 
| 35 | 
            +
                    puts "Config directory already exists at: #{Dropsite.dropsite_config_dir}"
         | 
| 36 | 
            +
                    exit
         | 
| 37 | 
            +
                  end
         | 
| 38 | 
            +
             | 
| 39 | 
            +
                  config_dir = File.join(Dropsite.dropbox_dir, '.dropsite')
         | 
| 40 | 
            +
                  Dir.mkdir(config_dir)
         | 
| 41 | 
            +
                  File.open(File.join(config_dir, 'config.yml'), 'w') do |f|
         | 
| 42 | 
            +
                    # TODO: put the contents in there
         | 
| 43 | 
            +
                    f.puts ''
         | 
| 44 | 
            +
                  end
         | 
| 45 | 
            +
                  Dir.mkdir(File.join(config_dir, 'plugins'))
         | 
| 46 | 
            +
                end
         | 
| 47 | 
            +
             | 
| 48 | 
            +
                private
         | 
| 49 | 
            +
             | 
| 50 | 
            +
                def handle_options
         | 
| 51 | 
            +
                  OptionParser.new do |opts|
         | 
| 52 | 
            +
                    opts.on('-d', '--dropbox-home [PATH]', 'Specify Dropbox directory') do |path|
         | 
| 53 | 
            +
                      options.dropbox_home = path
         | 
| 54 | 
            +
                    end
         | 
| 55 | 
            +
                    opts.on('-q', '--quiet', 'Suppress site processing output') do
         | 
| 56 | 
            +
                      options.quiet = true
         | 
| 57 | 
            +
                    end
         | 
| 58 | 
            +
                    opts.on('-c', '--create-config-files', 'Create a dropsite config dir in the Dropbox home') do
         | 
| 59 | 
            +
                      options.create_config_dir = true
         | 
| 60 | 
            +
                    end
         | 
| 61 | 
            +
                    opts.on_tail('-h', '--help', 'Show this message') do
         | 
| 62 | 
            +
                      puts opts
         | 
| 63 | 
            +
                      exit
         | 
| 64 | 
            +
                    end
         | 
| 65 | 
            +
                    opts.on_tail('--version', 'Show version') do
         | 
| 66 | 
            +
                      puts "Dropsite version: #{Dropsite::VERSION}"
         | 
| 67 | 
            +
                      exit
         | 
| 68 | 
            +
                    end
         | 
| 69 | 
            +
                  end.parse!
         | 
| 70 | 
            +
                end
         | 
| 71 | 
            +
              end
         | 
| 72 | 
            +
             | 
| 73 | 
            +
              # Wraps the main configuration file. Exists mostly in case of future
         | 
| 74 | 
            +
              # expansion of configuration options.
         | 
| 75 | 
            +
              class ConfigFile
         | 
| 76 | 
            +
                attr_reader :path, :exclude
         | 
| 77 | 
            +
             | 
| 78 | 
            +
                def initialize(path=nil)
         | 
| 79 | 
            +
                  @path = path || File.join(Dropsite.dropsite_config_dir, 'config.yml')
         | 
| 80 | 
            +
                end
         | 
| 81 | 
            +
             | 
| 82 | 
            +
                def read
         | 
| 83 | 
            +
                  return if not exist?
         | 
| 84 | 
            +
                  config = YAML::load(IO.read(path))
         | 
| 85 | 
            +
                  @exclude = config['exclude']
         | 
| 86 | 
            +
                  self
         | 
| 87 | 
            +
                end
         | 
| 88 | 
            +
             | 
| 89 | 
            +
                def exist?
         | 
| 90 | 
            +
                  File.exist? path
         | 
| 91 | 
            +
                end
         | 
| 92 | 
            +
              end
         | 
| 93 | 
            +
            end
         | 
| @@ -3,39 +3,37 @@ require 'erb' | |
| 3 3 | 
             
            module Dropsite
         | 
| 4 4 | 
             
              class DirRenderer
         | 
| 5 5 | 
             
                TEMPLATE_EXTENSIONS = ['.erb']
         | 
| 6 | 
            -
             | 
| 6 | 
            +
             | 
| 7 7 | 
             
                @@renderers = []
         | 
| 8 | 
            -
             | 
| 8 | 
            +
             | 
| 9 9 | 
             
                def self.inherited(subclass)
         | 
| 10 10 | 
             
                  renderer = subclass.new
         | 
| 11 | 
            -
             | 
| 11 | 
            +
             | 
| 12 12 | 
             
                  plugin_dir = File.dirname(caller[0].split(':')[0])
         | 
| 13 13 | 
             
                  template_file = Dir.entries(plugin_dir).find {|e| TEMPLATE_EXTENSIONS.include? File.extname(e)}
         | 
| 14 14 | 
             
                  renderer.template_path = template_file ? File.join(plugin_dir, template_file) : nil
         | 
| 15 15 | 
             
                  renderer.assets_dir = File.join(plugin_dir, 'assets')
         | 
| 16 16 | 
             
                  @@renderers << renderer
         | 
| 17 17 | 
             
                end
         | 
| 18 | 
            -
             | 
| 19 | 
            -
                def  | 
| 18 | 
            +
             | 
| 19 | 
            +
                def self.renderers
         | 
| 20 20 | 
             
                  @@renderers
         | 
| 21 21 | 
             
                end
         | 
| 22 | 
            -
             | 
| 23 | 
            -
                # Find the first renderer that can render the given SiteDir. Non-default (user) plugins
         | 
| 24 | 
            -
                # are searched first.
         | 
| 25 | 
            -
                def DirRenderer.find_renderer(site_dir)
         | 
| 26 | 
            -
                  @@renderers.partition {|r| !r.is_default? }.flatten.find {|r| r.can_render?(site_dir)}
         | 
| 27 | 
            -
                end
         | 
| 28 | 
            -
                
         | 
| 29 | 
            -
                def DirRenderer.find_renderer_and_render(site_dir)
         | 
| 30 | 
            -
                  DirRenderer.find_renderer(site_dir).render(site_dir)
         | 
| 31 | 
            -
                end
         | 
| 32 | 
            -
                
         | 
| 22 | 
            +
             | 
| 33 23 | 
             
                attr_accessor :template_path, :assets_dir
         | 
| 34 | 
            -
             | 
| 35 | 
            -
                # Overridden in subclass  | 
| 24 | 
            +
             | 
| 25 | 
            +
                # Overridden in subclass to indicate, usually based on the SiteDir contents, whether
         | 
| 26 | 
            +
                # this renderer can render the SiteDir. This is false by default, unless the renderer
         | 
| 27 | 
            +
                # is a built_in (included with Dropsite).
         | 
| 28 | 
            +
                def can_render?(site_dir)
         | 
| 29 | 
            +
                  built_in?
         | 
| 30 | 
            +
                end
         | 
| 31 | 
            +
             | 
| 32 | 
            +
                # Optionally overridden in subclass to do the work of rendering. By default this will
         | 
| 33 | 
            +
                # find plugin_name.erb in the plugin directory and use it to render.
         | 
| 36 34 | 
             
                def render(site_dir)
         | 
| 37 35 | 
             
                  site_dir.rendered_by = self.class
         | 
| 38 | 
            -
             | 
| 36 | 
            +
             | 
| 39 37 | 
             
                  if File.extname(template_path) == '.erb'
         | 
| 40 38 | 
             
                    @template = @template || ERB.new(IO.read(template_path))
         | 
| 41 39 | 
             
                    @template.result(site_dir.get_binding)
         | 
| @@ -43,13 +41,13 @@ module Dropsite | |
| 43 41 | 
             
                    raise "Don't know how to render: #{template_path}"
         | 
| 44 42 | 
             
                  end
         | 
| 45 43 | 
             
                end
         | 
| 46 | 
            -
             | 
| 47 | 
            -
                #  | 
| 48 | 
            -
                 | 
| 49 | 
            -
             | 
| 44 | 
            +
             | 
| 45 | 
            +
                # Optionally overridden in subclass to write any files that will be needed to display
         | 
| 46 | 
            +
                # the page (rendered by the render method) properly. This does nothing by default.
         | 
| 47 | 
            +
                def write_page_assets(site_dir)
         | 
| 50 48 | 
             
                end
         | 
| 51 | 
            -
             | 
| 52 | 
            -
                def  | 
| 49 | 
            +
             | 
| 50 | 
            +
                def built_in?
         | 
| 53 51 | 
             
                  false
         | 
| 54 52 | 
             
                end
         | 
| 55 53 | 
             
              end
         | 
| @@ -0,0 +1,87 @@ | |
| 1 | 
            +
            body {
         | 
| 2 | 
            +
            	background-color: white;
         | 
| 3 | 
            +
            	color: #484848;
         | 
| 4 | 
            +
            	font: 13.34px Helvetica, Arial, freesans, clean, sans-serif;
         | 
| 5 | 
            +
            	font-size: 90%;
         | 
| 6 | 
            +
            	text-align: center;
         | 
| 7 | 
            +
            }
         | 
| 8 | 
            +
             | 
| 9 | 
            +
            #content {
         | 
| 10 | 
            +
            	width: 920px;
         | 
| 11 | 
            +
            	margin-left: auto;
         | 
| 12 | 
            +
            	margin-right: auto;
         | 
| 13 | 
            +
            	text-align: left;
         | 
| 14 | 
            +
            }
         | 
| 15 | 
            +
             | 
| 16 | 
            +
            #breadcrumbs {
         | 
| 17 | 
            +
            	margin-top: 20px;
         | 
| 18 | 
            +
            	font-size: 140%;
         | 
| 19 | 
            +
            }
         | 
| 20 | 
            +
             | 
| 21 | 
            +
            #breadcrumbs .sep {
         | 
| 22 | 
            +
            	margin-left: 5px;
         | 
| 23 | 
            +
            	margin-right: 10px;
         | 
| 24 | 
            +
            }
         | 
| 25 | 
            +
             | 
| 26 | 
            +
            #breadcrumbs .root-link, #breadcrumbs .parent-dir-link {
         | 
| 27 | 
            +
            	text-decoration: none;
         | 
| 28 | 
            +
            }
         | 
| 29 | 
            +
             | 
| 30 | 
            +
            #breadcrumbs .root-link:hover, .parent-dir-link:hover {
         | 
| 31 | 
            +
            	text-decoration: underline;
         | 
| 32 | 
            +
            }
         | 
| 33 | 
            +
             | 
| 34 | 
            +
            #breadcrumbs .root-link {
         | 
| 35 | 
            +
            	color: #4183C4;
         | 
| 36 | 
            +
            	font-weight: bold;
         | 
| 37 | 
            +
            }
         | 
| 38 | 
            +
             | 
| 39 | 
            +
            #breadcrumbs .parent-dir-link {
         | 
| 40 | 
            +
            	color: #4183C4;
         | 
| 41 | 
            +
            }
         | 
| 42 | 
            +
             | 
| 43 | 
            +
            #breadcrumbs .current-dir {
         | 
| 44 | 
            +
            	color: #000000;
         | 
| 45 | 
            +
            }
         | 
| 46 | 
            +
             | 
| 47 | 
            +
            #file-list {
         | 
| 48 | 
            +
            	margin-top: 10px;
         | 
| 49 | 
            +
            	width: 100%;
         | 
| 50 | 
            +
            }
         | 
| 51 | 
            +
             | 
| 52 | 
            +
            #file-list .header {
         | 
| 53 | 
            +
            	background-color: #eaeaea;
         | 
| 54 | 
            +
            	border: 1px solid #e1e1e1;
         | 
| 55 | 
            +
            	color: #999999;
         | 
| 56 | 
            +
            	height: 28px;
         | 
| 57 | 
            +
            }
         | 
| 58 | 
            +
             | 
| 59 | 
            +
            .thumb-link {
         | 
| 60 | 
            +
            	width: 152px;
         | 
| 61 | 
            +
            	margin: 3px;
         | 
| 62 | 
            +
            	padding: 5px;
         | 
| 63 | 
            +
            	float: left;
         | 
| 64 | 
            +
            	text-align: center;
         | 
| 65 | 
            +
            	border: 2px solid #fff;
         | 
| 66 | 
            +
            	font-family: Monaco, 'Courier New', 'DejaVu Sans Mono', 'Bitstream Vera Sans Mono', monospace;
         | 
| 67 | 
            +
            	text-decoration: none;
         | 
| 68 | 
            +
            }
         | 
| 69 | 
            +
             | 
| 70 | 
            +
            .thumb-link:hover {
         | 
| 71 | 
            +
            	border: 2px solid #4183C4;
         | 
| 72 | 
            +
            }
         | 
| 73 | 
            +
             | 
| 74 | 
            +
            .thumb-link .dir-container {
         | 
| 75 | 
            +
            	width: 100px;
         | 
| 76 | 
            +
            	height: 100px;
         | 
| 77 | 
            +
            }
         | 
| 78 | 
            +
             | 
| 79 | 
            +
            .thumb-link .dir-container img {
         | 
| 80 | 
            +
            	margin-top: 30px;
         | 
| 81 | 
            +
            	margin-left: 54px;
         | 
| 82 | 
            +
            }
         | 
| 83 | 
            +
             | 
| 84 | 
            +
            .image .name {
         | 
| 85 | 
            +
            	margin-left: auto;
         | 
| 86 | 
            +
            	margin-right: auto;
         | 
| 87 | 
            +
            }
         | 
| @@ -0,0 +1,30 @@ | |
| 1 | 
            +
            body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,form,fieldset,input,textarea,p,blockquote,th,td { 
         | 
| 2 | 
            +
            	margin:0;
         | 
| 3 | 
            +
            	padding:0;
         | 
| 4 | 
            +
            }
         | 
| 5 | 
            +
            table {
         | 
| 6 | 
            +
            	border-collapse:collapse;
         | 
| 7 | 
            +
            	border-spacing:0;
         | 
| 8 | 
            +
            }
         | 
| 9 | 
            +
            fieldset,img { 
         | 
| 10 | 
            +
            	border:0;
         | 
| 11 | 
            +
            }
         | 
| 12 | 
            +
            address,caption,cite,code,dfn,em,strong,th,var {
         | 
| 13 | 
            +
            	font-style:normal;
         | 
| 14 | 
            +
            	font-weight:normal;
         | 
| 15 | 
            +
            }
         | 
| 16 | 
            +
            ol,ul {
         | 
| 17 | 
            +
            	list-style:none;
         | 
| 18 | 
            +
            }
         | 
| 19 | 
            +
            caption,th {
         | 
| 20 | 
            +
            	text-align:left;
         | 
| 21 | 
            +
            }
         | 
| 22 | 
            +
            h1,h2,h3,h4,h5,h6 {
         | 
| 23 | 
            +
            	font-size:100%;
         | 
| 24 | 
            +
            	font-weight:normal;
         | 
| 25 | 
            +
            }
         | 
| 26 | 
            +
            q:before,q:after {
         | 
| 27 | 
            +
            	content:'';
         | 
| 28 | 
            +
            }
         | 
| 29 | 
            +
            abbr,acronym { border:0;
         | 
| 30 | 
            +
            }
         | 
| Binary file | 
| Binary file | 
| @@ -0,0 +1,49 @@ | |
| 1 | 
            +
            <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
         | 
| 2 | 
            +
            	"http://www.w3.org/TR/html4/strict.dtd">
         | 
| 3 | 
            +
            <%
         | 
| 4 | 
            +
            def thumb_name(image_file_name)
         | 
| 5 | 
            +
            	File.basename(image_file_name).sub(/\.\w+$/, '') + '-thumb' + File.extname(image_file_name)
         | 
| 6 | 
            +
            end
         | 
| 7 | 
            +
            def shorten(file_name)
         | 
| 8 | 
            +
            	if file_name.size < 20
         | 
| 9 | 
            +
            		file_name
         | 
| 10 | 
            +
            	else
         | 
| 11 | 
            +
            		file_name[0..7] + '...' + file_name[-8..-1]
         | 
| 12 | 
            +
            	end
         | 
| 13 | 
            +
            end
         | 
| 14 | 
            +
            %>
         | 
| 15 | 
            +
            <html>
         | 
| 16 | 
            +
            	<head>
         | 
| 17 | 
            +
            		<meta http-equiv="Content-type" content="text/html; charset=utf-8">
         | 
| 18 | 
            +
            		<title>My Dropbox Files<%= " - #{name}" if !root? %></title>
         | 
| 19 | 
            +
            		<%= stylesheet_link_tag 'reset' %>
         | 
| 20 | 
            +
            		<%= stylesheet_link_tag 'image_thumbnails' %>
         | 
| 21 | 
            +
            	</head>
         | 
| 22 | 
            +
            	<body>
         | 
| 23 | 
            +
            		<div id="content">
         | 
| 24 | 
            +
            			<div id="breadcrumbs">
         | 
| 25 | 
            +
            				<a class="root-link" href="<%= back_link('root') %>">my files</a>
         | 
| 26 | 
            +
            				<% each_parent_directory_link_tag(false, {:class => 'parent-dir-link'}) do |tag| %>
         | 
| 27 | 
            +
            					<span class="sep">/</span><%= tag %>
         | 
| 28 | 
            +
            				<% end %>
         | 
| 29 | 
            +
            				<% if !root? %>
         | 
| 30 | 
            +
            					<span class="sep">/</span><span class="current-dir"><%= name %></span>
         | 
| 31 | 
            +
            				<% end %>
         | 
| 32 | 
            +
            			</div>
         | 
| 33 | 
            +
            			<% dirs.sort.each do |dir| %>
         | 
| 34 | 
            +
            				<a class="thumb-link" href="<%= url_for dir %>">
         | 
| 35 | 
            +
            					<div class="dir-container">
         | 
| 36 | 
            +
            						<%= image_tag 'icons/directory-large.png' %>
         | 
| 37 | 
            +
            					</div>
         | 
| 38 | 
            +
            					<div class="name"><%= shorten dir.name %></div>
         | 
| 39 | 
            +
            				</a>
         | 
| 40 | 
            +
            			<% end %>
         | 
| 41 | 
            +
            			<% files.sort.each do |file| %>
         | 
| 42 | 
            +
            				<a class="thumb-link" href="<%= url_for file %>">
         | 
| 43 | 
            +
            					<%= page_asset_image_tag thumb_name(file.name) %>
         | 
| 44 | 
            +
            					<div class="name"><%= shorten file.name %></div>
         | 
| 45 | 
            +
            				</a>
         | 
| 46 | 
            +
            			<% end %>
         | 
| 47 | 
            +
            		</div>
         | 
| 48 | 
            +
            	</body>
         | 
| 49 | 
            +
            </html>
         | 
| @@ -0,0 +1,65 @@ | |
| 1 | 
            +
            class ImageThumbnails < Dropsite::DirRenderer
         | 
| 2 | 
            +
              def can_render?(site_dir)
         | 
| 3 | 
            +
                return false if not thumbnail_generator
         | 
| 4 | 
            +
                !site_dir.files.empty? && site_dir.files.all? {|e| e.file_type == :image}
         | 
| 5 | 
            +
              end
         | 
| 6 | 
            +
             | 
| 7 | 
            +
              def write_page_assets(site_dir)
         | 
| 8 | 
            +
                raise 'No thumbnail generator' if not thumbnail_generator
         | 
| 9 | 
            +
             | 
| 10 | 
            +
                assets_dir = site_dir.page_assets_dir
         | 
| 11 | 
            +
                site_dir.entries.find_all {|e| e.is_a? SiteFile}.each do |e|
         | 
| 12 | 
            +
                  src_image = e.abs_path
         | 
| 13 | 
            +
                  case thumbnail_generator
         | 
| 14 | 
            +
                  when :image_science
         | 
| 15 | 
            +
                    write_thumb_with_image_science(src_image, assets_dir)
         | 
| 16 | 
            +
                  when :rmagick
         | 
| 17 | 
            +
                    write_thumb_with_rmagick(src_image, assets_dir)
         | 
| 18 | 
            +
                  else
         | 
| 19 | 
            +
                    raise "Unrecognized thumbnail generator: #{thumbnail_generator}"
         | 
| 20 | 
            +
                  end
         | 
| 21 | 
            +
                end
         | 
| 22 | 
            +
              end
         | 
| 23 | 
            +
             | 
| 24 | 
            +
              def built_in?
         | 
| 25 | 
            +
                true
         | 
| 26 | 
            +
              end
         | 
| 27 | 
            +
             | 
| 28 | 
            +
              def thumbnail_generator
         | 
| 29 | 
            +
                return @thumbnail_generator_cache if instance_variables.include?('@thumbnail_generator_cache')
         | 
| 30 | 
            +
             | 
| 31 | 
            +
                begin
         | 
| 32 | 
            +
                  require 'image_science'
         | 
| 33 | 
            +
                  return @thumbnail_generator_cache = :image_science
         | 
| 34 | 
            +
                rescue LoadError
         | 
| 35 | 
            +
                end
         | 
| 36 | 
            +
             | 
| 37 | 
            +
                begin
         | 
| 38 | 
            +
                  require 'rmagick'
         | 
| 39 | 
            +
                  return @thumbnail_generator_cache = :rmagick
         | 
| 40 | 
            +
                rescue LoadError
         | 
| 41 | 
            +
                end
         | 
| 42 | 
            +
             | 
| 43 | 
            +
                return @thumbnail_generator_cache = nil
         | 
| 44 | 
            +
              end
         | 
| 45 | 
            +
             | 
| 46 | 
            +
              protected
         | 
| 47 | 
            +
             | 
| 48 | 
            +
              def write_thumb_with_image_science(src_image, assets_dir)
         | 
| 49 | 
            +
                ImageScience.with_image(src_image) do |img|
         | 
| 50 | 
            +
                  img.cropped_thumbnail(100) do |thumb|
         | 
| 51 | 
            +
                    thumb.save(File.join(assets_dir, thumb_file_name(src_image)))
         | 
| 52 | 
            +
                  end
         | 
| 53 | 
            +
                end
         | 
| 54 | 
            +
              end
         | 
| 55 | 
            +
             | 
| 56 | 
            +
              def write_thumb_with_rmagick(src_image, assets_dir)
         | 
| 57 | 
            +
                img = Magick::Image::read(src_image).first
         | 
| 58 | 
            +
                thumb = img.resize_to_fill(100, 100)
         | 
| 59 | 
            +
                thumb.write File.join(assets_dir, thumb_file_name(src_image))
         | 
| 60 | 
            +
              end
         | 
| 61 | 
            +
             | 
| 62 | 
            +
              def thumb_file_name(image_file_name)
         | 
| 63 | 
            +
                File.basename(image_file_name).sub(/\.\w+$/, '') + '-thumb' + File.extname(image_file_name)
         | 
| 64 | 
            +
              end
         | 
| 65 | 
            +
            end
         | 
| @@ -26,7 +26,7 @@ | |
| 26 26 | 
             
            				<% @entries.sort.each do |entry| %>
         | 
| 27 27 | 
             
            				<tr class="entry">
         | 
| 28 28 | 
             
            					<td class="icon"><%= image_tag "icons/#{entry.file_type}.png" %></td>
         | 
| 29 | 
            -
            					<td class="link"><a href="<%= entry | 
| 29 | 
            +
            					<td class="link"><a href="<%= url_for entry %>"><%= entry.name %></a></td>
         | 
| 30 30 | 
             
            					<td class="type"><%= entry.file_type %></td>
         | 
| 31 31 | 
             
            					<td class="size"><%= entry.size %></td>
         | 
| 32 32 | 
             
            				</tr>
         | 
| @@ -4,6 +4,9 @@ module Dropsite | |
| 4 4 | 
             
              module RenderHelper
         | 
| 5 5 | 
             
                attr_accessor :rendered_by
         | 
| 6 6 |  | 
| 7 | 
            +
             | 
| 8 | 
            +
                # Helpers for linking to other Dropsite rendered pages
         | 
| 9 | 
            +
             | 
| 7 10 | 
             
                def link
         | 
| 8 11 | 
             
                  # TODO: URL escape links
         | 
| 9 12 | 
             
                  if top_level? && (!is_a? SiteDir)
         | 
| @@ -20,18 +23,21 @@ module Dropsite | |
| 20 23 | 
             
                  end
         | 
| 21 24 | 
             
                end
         | 
| 22 25 |  | 
| 23 | 
            -
                 | 
| 24 | 
            -
             | 
| 25 | 
            -
             | 
| 26 | 
            -
             | 
| 27 | 
            -
             | 
| 28 | 
            -
             | 
| 29 | 
            -
             | 
| 30 | 
            -
             | 
| 31 | 
            -
             | 
| 32 | 
            -
             | 
| 33 | 
            -
             | 
| 34 | 
            -
             | 
| 26 | 
            +
                # Creates a relative URL, from the page for the current object, for the given SiteItem.
         | 
| 27 | 
            +
                # This assumes the current object is a SiteDir.
         | 
| 28 | 
            +
                def url_for(entry)
         | 
| 29 | 
            +
                  if entry.top_level? && (!entry.is_a? SiteDir)
         | 
| 30 | 
            +
                    entry.name
         | 
| 31 | 
            +
                  else
         | 
| 32 | 
            +
                    if entry.is_a? SiteDir # TODO: do a dynamic renderable test?
         | 
| 33 | 
            +
                      entry.top_level? ? "dropsite/#{entry.path}.html" : "#{name}/#{entry.name}.html".sub(/^\//, '')
         | 
| 34 | 
            +
                    else
         | 
| 35 | 
            +
                      # Builds a link back up to the file in Public root since the pages
         | 
| 36 | 
            +
                      # are built in a parallel directory structure
         | 
| 37 | 
            +
                      dirs_up = entry.path.split(File::SEPARATOR).size - 1
         | 
| 38 | 
            +
                      (['..'] * dirs_up).join('/') + "/#{entry.path}"
         | 
| 39 | 
            +
                    end
         | 
| 40 | 
            +
                  end
         | 
| 35 41 | 
             
                end
         | 
| 36 42 |  | 
| 37 43 | 
             
                def parent_directory_link_tag(levels_up=1, options={})
         | 
| @@ -51,16 +57,6 @@ module Dropsite | |
| 51 57 | 
             
                  end
         | 
| 52 58 | 
             
                end
         | 
| 53 59 |  | 
| 54 | 
            -
                def assets_link_base
         | 
| 55 | 
            -
                  if root?
         | 
| 56 | 
            -
                    "dropsite/dropsite-assets/#{Dropsite.underscorize(rendered_by)}/"
         | 
| 57 | 
            -
                  else
         | 
| 58 | 
            -
                    # Work our way BACK up the path - crazy, right? Gotta do it though.
         | 
| 59 | 
            -
                    dirs_up = path.split(File::SEPARATOR).size - 1
         | 
| 60 | 
            -
                    (['..'] * dirs_up).join('/') + "#{'/' if dirs_up > 0}dropsite-assets/#{Dropsite.underscorize(rendered_by)}/"
         | 
| 61 | 
            -
                  end
         | 
| 62 | 
            -
                end
         | 
| 63 | 
            -
             | 
| 64 60 | 
             
                # Get a link to a parent page
         | 
| 65 61 | 
             
                def back_link(levels_up=1)
         | 
| 66 62 | 
             
                  # TODO: factor this out a bit between parent_dir_name
         | 
| @@ -84,6 +80,48 @@ module Dropsite | |
| 84 80 | 
             
                  end
         | 
| 85 81 | 
             
                end
         | 
| 86 82 |  | 
| 83 | 
            +
             | 
| 84 | 
            +
                # Helpers for including assets from the plugin assets directory
         | 
| 85 | 
            +
             | 
| 86 | 
            +
                def stylesheet_link_tag(stylesheet_name)
         | 
| 87 | 
            +
                  stylesheet_name = "#{stylesheet_name}.css" if not stylesheet_name =~ /\.css$/
         | 
| 88 | 
            +
                  %{<link rel="stylesheet" href="#{plugin_assets_link_base}css/#{stylesheet_name}" type="text/css" media="screen">}
         | 
| 89 | 
            +
                end
         | 
| 90 | 
            +
             | 
| 91 | 
            +
                def javascript_include_tag(javascript_file_name)
         | 
| 92 | 
            +
                  javascript_file_name = "#{javascript_file_name}.js" if not javascript_file_name =~ /\.js$/
         | 
| 93 | 
            +
                  %{<script type="text/javascript" src="#{plugin_assets_link_base}js/#{javascript_file_name}"></script>}
         | 
| 94 | 
            +
                end
         | 
| 95 | 
            +
             | 
| 96 | 
            +
                def image_tag(image_file_name)
         | 
| 97 | 
            +
                  %{<img src="#{plugin_assets_link_base}images/#{image_file_name}" />}
         | 
| 98 | 
            +
                end
         | 
| 99 | 
            +
             | 
| 100 | 
            +
             | 
| 101 | 
            +
                # Helpers for including assets from the page assets (assets for an individual page,
         | 
| 102 | 
            +
                # created by the write_page_assets method for a given renderer)
         | 
| 103 | 
            +
             | 
| 104 | 
            +
                # Creates an img tag for the given page asset image. This links to a file directly
         | 
| 105 | 
            +
                # in the page asset directory and an 'image' folder is not assumed.
         | 
| 106 | 
            +
                def page_asset_image_tag(image_file_name)
         | 
| 107 | 
            +
                  %{<img src="#{page_assets_link_base}#{image_file_name}" />}
         | 
| 108 | 
            +
                end
         | 
| 109 | 
            +
             | 
| 110 | 
            +
             | 
| 111 | 
            +
                def plugin_assets_link_base
         | 
| 112 | 
            +
                  if root?
         | 
| 113 | 
            +
                    "dropsite/dropsite-assets/#{Dropsite.underscorize(rendered_by)}/"
         | 
| 114 | 
            +
                  else
         | 
| 115 | 
            +
                    # Work our way BACK up the path - crazy, right? Gotta do it though.
         | 
| 116 | 
            +
                    dirs_up = path.split(File::SEPARATOR).size - 1
         | 
| 117 | 
            +
                    (['..'] * dirs_up).join('/') + "#{'/' if dirs_up > 0}dropsite-assets/#{Dropsite.underscorize(rendered_by)}/"
         | 
| 118 | 
            +
                  end
         | 
| 119 | 
            +
                end
         | 
| 120 | 
            +
             | 
| 121 | 
            +
                def page_assets_link_base
         | 
| 122 | 
            +
                  "#{root? ? 'dropsite/' : ''}#{page_assets_dir_name}/"
         | 
| 123 | 
            +
                end
         | 
| 124 | 
            +
             | 
| 87 125 | 
             
                def get_binding
         | 
| 88 126 | 
             
                  binding
         | 
| 89 127 | 
             
                end
         |