radiant-shop-extension 0.9.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (160) hide show
  1. data/.gitignore +6 -0
  2. data/Gemfile +26 -0
  3. data/Gemfile.lock +75 -0
  4. data/HISTORY.md +77 -0
  5. data/MIT-LICENSE +20 -0
  6. data/README.md +26 -0
  7. data/Rakefile +141 -0
  8. data/VERSION +1 -0
  9. data/app/.DS_Store +0 -0
  10. data/app/controllers/admin/shop/categories_controller.rb +206 -0
  11. data/app/controllers/admin/shop/customers_controller.rb +137 -0
  12. data/app/controllers/admin/shop/orders_controller.rb +171 -0
  13. data/app/controllers/admin/shop/products/images_controller.rb +144 -0
  14. data/app/controllers/admin/shop/products_controller.rb +217 -0
  15. data/app/controllers/admin/shops_controller.rb +9 -0
  16. data/app/controllers/shop/categories_controller.rb +49 -0
  17. data/app/controllers/shop/line_items_controller.rb +165 -0
  18. data/app/controllers/shop/orders_controller.rb +16 -0
  19. data/app/controllers/shop/products_controller.rb +48 -0
  20. data/app/models/form_checkout.rb +245 -0
  21. data/app/models/shop_address.rb +13 -0
  22. data/app/models/shop_addressable.rb +11 -0
  23. data/app/models/shop_category.rb +85 -0
  24. data/app/models/shop_category_page.rb +7 -0
  25. data/app/models/shop_customer.rb +27 -0
  26. data/app/models/shop_line_item.rb +32 -0
  27. data/app/models/shop_order.rb +108 -0
  28. data/app/models/shop_payment.rb +6 -0
  29. data/app/models/shop_payment_method.rb +5 -0
  30. data/app/models/shop_product.rb +87 -0
  31. data/app/models/shop_product_attachment.rb +30 -0
  32. data/app/models/shop_product_page.rb +7 -0
  33. data/app/views/.DS_Store +0 -0
  34. data/app/views/admin/.DS_Store +0 -0
  35. data/app/views/admin/pages/_shop_category.html.haml +4 -0
  36. data/app/views/admin/pages/_shop_product.html.haml +4 -0
  37. data/app/views/admin/shop/categories/edit.html.haml +12 -0
  38. data/app/views/admin/shop/categories/edit/_fields.html.haml +28 -0
  39. data/app/views/admin/shop/categories/edit/_head.html.haml +2 -0
  40. data/app/views/admin/shop/categories/edit/_meta.html.haml +7 -0
  41. data/app/views/admin/shop/categories/edit/_part.html.haml +3 -0
  42. data/app/views/admin/shop/categories/edit/_popup.html.haml +3 -0
  43. data/app/views/admin/shop/categories/edit/meta/_handle.html.haml +5 -0
  44. data/app/views/admin/shop/categories/edit/meta/_layouts.html.haml +10 -0
  45. data/app/views/admin/shop/categories/edit/parts/_description.html.haml +1 -0
  46. data/app/views/admin/shop/categories/index/_category.html.haml +16 -0
  47. data/app/views/admin/shop/categories/new.html.haml +10 -0
  48. data/app/views/admin/shop/categories/remove.html.haml +12 -0
  49. data/app/views/admin/shop/customers/index.html.haml +36 -0
  50. data/app/views/admin/shop/orders/index.html.haml +33 -0
  51. data/app/views/admin/shop/products/edit.html.haml +14 -0
  52. data/app/views/admin/shop/products/edit/_fields.html.haml +38 -0
  53. data/app/views/admin/shop/products/edit/_head.html.haml +2 -0
  54. data/app/views/admin/shop/products/edit/_image.html.haml +12 -0
  55. data/app/views/admin/shop/products/edit/_meta.html.haml +8 -0
  56. data/app/views/admin/shop/products/edit/_part.html.haml +3 -0
  57. data/app/views/admin/shop/products/edit/_popup.html.haml +3 -0
  58. data/app/views/admin/shop/products/edit/buttons/_browse_images.html.haml +1 -0
  59. data/app/views/admin/shop/products/edit/buttons/_new_image.html.haml +1 -0
  60. data/app/views/admin/shop/products/edit/meta/_category.html.haml +5 -0
  61. data/app/views/admin/shop/products/edit/meta/_sku.html.haml +5 -0
  62. data/app/views/admin/shop/products/edit/parts/_description.html.haml +1 -0
  63. data/app/views/admin/shop/products/edit/parts/_images.html.haml +5 -0
  64. data/app/views/admin/shop/products/edit/popups/_browse_images.html.haml +6 -0
  65. data/app/views/admin/shop/products/edit/popups/_new_image.html.haml +18 -0
  66. data/app/views/admin/shop/products/index.html.haml +10 -0
  67. data/app/views/admin/shop/products/index/_bottom.html.haml +5 -0
  68. data/app/views/admin/shop/products/index/_product.html.haml +13 -0
  69. data/app/views/admin/shop/products/new.html.haml +10 -0
  70. data/app/views/admin/shop/products/remove.html.haml +12 -0
  71. data/app/views/shop/categories/show.html.haml +1 -0
  72. data/app/views/shop/orders/show.html.haml +1 -0
  73. data/app/views/shop/products/index.html.haml +1 -0
  74. data/app/views/shop/products/show.html.haml +1 -0
  75. data/config/locales/en.yml +50 -0
  76. data/config/routes.rb +38 -0
  77. data/config/shop_cart.yml +16 -0
  78. data/cucumber.yml +1 -0
  79. data/db/migrate/20100311053701_initial.rb +153 -0
  80. data/db/migrate/20100520033059_create_layouts.rb +119 -0
  81. data/db/migrate/20100903122123_create_forms.rb +44 -0
  82. data/db/migrate/20100908063639_create_snippets.rb +22 -0
  83. data/features/support/env.rb +16 -0
  84. data/features/support/paths.rb +14 -0
  85. data/lib/shop/controllers/application_controller.rb +39 -0
  86. data/lib/shop/controllers/site_controller.rb +12 -0
  87. data/lib/shop/interface/products.rb +49 -0
  88. data/lib/shop/models/image.rb +14 -0
  89. data/lib/shop/models/page.rb +14 -0
  90. data/lib/shop/tags/address.rb +40 -0
  91. data/lib/shop/tags/cart.rb +49 -0
  92. data/lib/shop/tags/category.rb +83 -0
  93. data/lib/shop/tags/core.rb +12 -0
  94. data/lib/shop/tags/helpers.rb +142 -0
  95. data/lib/shop/tags/item.rb +109 -0
  96. data/lib/shop/tags/product.rb +109 -0
  97. data/lib/shop/tags/responses.rb +34 -0
  98. data/lib/tasks/shop_extension_tasks.rake +54 -0
  99. data/mockups/balsamiq/products-retro_fun_tshirt-more.bmml +0 -0
  100. data/mockups/balsamiq/products-retro_fun_tshirt.bmml +0 -0
  101. data/public/images/admin/extensions/shop/products/sort.png +0 -0
  102. data/public/javascripts/admin/extensions/shop/products/edit.js +115 -0
  103. data/public/javascripts/admin/extensions/shop/products/index.js +65 -0
  104. data/public/stylesheets/sass/admin/extensions/shop/edit.sass +86 -0
  105. data/public/stylesheets/sass/admin/extensions/shop/products/edit.sass +158 -0
  106. data/public/stylesheets/sass/admin/extensions/shop/products/index.sass +129 -0
  107. data/radiant-shop-extension.gemspec +245 -0
  108. data/shop_extension.rb +62 -0
  109. data/spec/controllers/admin/shop/categories_controller_spec.rb +443 -0
  110. data/spec/controllers/admin/shop/products/images_controller_spec.rb +477 -0
  111. data/spec/controllers/admin/shop/products_controller_spec.rb +394 -0
  112. data/spec/controllers/admin/shops_controller_spec.rb +19 -0
  113. data/spec/controllers/shop/categories_controller_spec.rb +42 -0
  114. data/spec/controllers/shop/line_items_controller_spec.rb +256 -0
  115. data/spec/controllers/shop/orders_controller_specs.rb +37 -0
  116. data/spec/controllers/shop/products_controller_spec.rb +51 -0
  117. data/spec/datasets/forms.rb +153 -0
  118. data/spec/datasets/images.rb +13 -0
  119. data/spec/datasets/shop_addresses.rb +27 -0
  120. data/spec/datasets/shop_categories.rb +13 -0
  121. data/spec/datasets/shop_line_items.rb +9 -0
  122. data/spec/datasets/shop_orders.rb +21 -0
  123. data/spec/datasets/shop_products.rb +34 -0
  124. data/spec/helpers/nested_tag_helper.rb +33 -0
  125. data/spec/lib/shop/models/image_spec.rb +28 -0
  126. data/spec/lib/shop/models/page_spec.rb +38 -0
  127. data/spec/lib/shop/tags/address_spec.rb +196 -0
  128. data/spec/lib/shop/tags/cart_spec.rb +169 -0
  129. data/spec/lib/shop/tags/category_spec.rb +201 -0
  130. data/spec/lib/shop/tags/core_spec.rb +16 -0
  131. data/spec/lib/shop/tags/helpers_spec.rb +381 -0
  132. data/spec/lib/shop/tags/item_spec.rb +313 -0
  133. data/spec/lib/shop/tags/product_spec.rb +334 -0
  134. data/spec/matchers/comparison.rb +72 -0
  135. data/spec/matchers/render_matcher.rb +33 -0
  136. data/spec/models/form_checkout_spec.rb +376 -0
  137. data/spec/models/shop_category_page_spec.rb +10 -0
  138. data/spec/models/shop_category_spec.rb +58 -0
  139. data/spec/models/shop_line_item_spec.rb +42 -0
  140. data/spec/models/shop_order_spec.rb +228 -0
  141. data/spec/models/shop_product_attachment_spec.rb +72 -0
  142. data/spec/models/shop_product_page_spec.rb +10 -0
  143. data/spec/models/shop_product_spec.rb +135 -0
  144. data/spec/spec.opts +6 -0
  145. data/spec/spec_helper.rb +22 -0
  146. data/vendor/plugins/acts_as_list/README +23 -0
  147. data/vendor/plugins/acts_as_list/init.rb +3 -0
  148. data/vendor/plugins/acts_as_list/lib/active_record/acts/list.rb +256 -0
  149. data/vendor/plugins/acts_as_list/test/list_test.rb +332 -0
  150. data/vendor/plugins/json_fields/.gitignore +3 -0
  151. data/vendor/plugins/json_fields/MIT-LICENSE +20 -0
  152. data/vendor/plugins/json_fields/README.rdoc +65 -0
  153. data/vendor/plugins/json_fields/Rakefile +55 -0
  154. data/vendor/plugins/json_fields/init.rb +2 -0
  155. data/vendor/plugins/json_fields/lib/json_fields.rb +99 -0
  156. data/vendor/plugins/json_fields/spec/lib/json_fields_spec.rb +124 -0
  157. data/vendor/plugins/json_fields/spec/spec.opts +6 -0
  158. data/vendor/plugins/json_fields/spec/spec_helper.rb +29 -0
  159. data/vendor/plugins/json_fields/spec/test_models.rb +12 -0
  160. metadata +324 -0
@@ -0,0 +1,34 @@
1
+ module Shop
2
+ module Tags
3
+ module Responses
4
+ include Radiant::Taggable
5
+
6
+ # Expand if there is a checkout response
7
+ desc %{ Expand if there is a checkout response }
8
+ tag 'response:checkout' do |tag|
9
+ tag.locals.response_checkout = tag.locals.response.result[:results][:checkout]
10
+
11
+ tag.expand if tag.locals.response_checkout.present?
12
+ end
13
+
14
+ # Expand if there is a checkout payment response
15
+ desc %{ Expand if there is a checkout payment response }
16
+ tag 'response:checkout:payment' do |tag|
17
+ tag.expand if tag.locals.response_checkout[:payment].present?
18
+ end
19
+
20
+ # Expand if the payment was successful
21
+ desc %{ Expand if the payment was successful }
22
+ tag 'response:checkout:payment:if_success' do |tag|
23
+ tag.expand if tag.locals.response_checkout[:payment][:success]
24
+ end
25
+
26
+ # Expand if the payment was not successful
27
+ desc %{ Expand if the payment was not successful }
28
+ tag 'response:checkout:payment:unless_success' do |tag|
29
+ tag.expand unless tag.locals.response_checkout[:payment][:success]
30
+ end
31
+
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,54 @@
1
+ namespace :radiant do
2
+ namespace :extensions do
3
+ namespace :shop do
4
+
5
+ desc "Runs the migration of the Shop extension"
6
+ task :migrate => [ :environment, 'radiant:extensions:forms:migrate' ] do
7
+ require 'radiant/extension_migrator'
8
+ if ENV["VERSION"]
9
+ ShopExtension.migrator.migrate(ENV["VERSION"].to_i)
10
+ else
11
+ ShopExtension.migrator.migrate
12
+ end
13
+ Rake::Task['db:schema:dump'].invoke
14
+ end
15
+
16
+ desc "Copies public assets of the Shop to the instance public/ directory."
17
+ task :update => :environment do
18
+ is_svn_or_dir = proc {|path| path =~ /\.svn/ || File.directory?(path) }
19
+ puts "Copying assets from ShopExtension"
20
+ Dir[ShopExtension.root + "/public/**/*"].reject(&is_svn_or_dir).each do |file|
21
+ path = file.sub(ShopExtension.root, '')
22
+ directory = File.dirname(path)
23
+ mkdir_p RAILS_ROOT + directory, :verbose => false
24
+ cp file, RAILS_ROOT + path, :verbose => false
25
+ end
26
+ unless ShopExtension.root.starts_with? RAILS_ROOT # don't need to copy vendored tasks
27
+ puts "Copying rake tasks from ShopExtension"
28
+ local_tasks_path = File.join(RAILS_ROOT, %w(lib tasks))
29
+ mkdir_p local_tasks_path, :verbose => false
30
+ Dir[File.join ImagesExtension.root, %w(lib tasks *.rake)].each do |file|
31
+ cp file, local_tasks_path, :verbose => false
32
+ end
33
+ end
34
+ end
35
+
36
+ desc "Syncs all available translations for this ext to the English ext master"
37
+ task :sync => :environment do
38
+ # The main translation root, basically where English is kept
39
+ language_root = ShopExtension.root + "/config/locales"
40
+ words = TranslationSupport.get_translation_keys(language_root)
41
+
42
+ Dir["#{language_root}/*.yml"].each do |filename|
43
+ next if filename.match('_available_tags')
44
+ basename = File.basename(filename, '.yml')
45
+ puts "Syncing #{basename}"
46
+ (comments, other) = TranslationSupport.read_file(filename, basename)
47
+ words.each { |k,v| other[k] ||= words[k] } # Initializing hash variable as empty if it does not exist
48
+ other.delete_if { |k,v| !words[k] } # Remove if not defined in en.yml
49
+ TranslationSupport.write_file(filename, basename, comments, other)
50
+ end
51
+ end
52
+ end
53
+ end
54
+ end
File without changes
@@ -0,0 +1,115 @@
1
+ var ShopProductAssets = {}
2
+
3
+ document.observe("dom:loaded", function() {
4
+ shop = new Shop()
5
+ shop.ProductInitialize()
6
+
7
+ Event.addBehavior({
8
+ '#browse_images_popup_close:click' : function(e) { shop.ImageClose() },
9
+ '#new_image_popup_close:click' : function(e) { shop.ImageClose() },
10
+
11
+ '#image_form:submit' : function(e) { shop.ImageSubmit() },
12
+
13
+ '#browse_images_popup .image:click' : function(e) { shop.ProductImageCreate($(this)) },
14
+ '#product_attachments .delete:click' : function(e) { shop.ProductImageDestroy($(this).up('.image')) }
15
+ })
16
+ })
17
+
18
+ ShopProductAssets.List = Behavior.create({
19
+
20
+ onclick: function() {
21
+ shop.ProductImageCreate(this.element)
22
+ }
23
+
24
+ });
25
+
26
+ var Shop = Class.create({
27
+
28
+ ProductInitialize: function() {
29
+ if($('shop_product_id')) {
30
+ this.ProductImagesSort()
31
+ }
32
+ },
33
+
34
+ ProductImagesSort: function() {
35
+ Sortable.create('product_attachments', {
36
+ constraint: false,
37
+ overlap: 'horizontal',
38
+ containment: ['product_attachments'],
39
+ onUpdate: function(element) {
40
+ new Ajax.Request(urlify($('sort_admin_shop_product_images_path').value), {
41
+ method: 'put',
42
+ parameters: {
43
+ 'product_id': $('shop_product_id').value,
44
+ 'attachments':Sortable.serialize('product_attachments')
45
+ }
46
+ });
47
+ }.bind(this)
48
+ })
49
+ },
50
+
51
+ ProductImageCreate: function(element) {
52
+ showStatus('Adding Image...')
53
+ element.hide()
54
+ new Ajax.Request(urlify($('admin_shop_product_images_path').value), {
55
+ method: 'post',
56
+ parameters: {
57
+ 'product_id' : $('shop_product_id').value,
58
+ 'attachment[image_id]' : element.getAttribute('data-image_id')
59
+ },
60
+ onSuccess: function(data) {
61
+ // Insert item into list, re-call events
62
+ $('product_attachments').insert({ 'bottom' : data.responseText})
63
+ shop.ProductImagesSort()
64
+ element.remove()
65
+ hideStatus()
66
+ }.bind(element),
67
+ onFailure: function() {
68
+ element.show()
69
+ hideStatus()
70
+ }
71
+ });
72
+ },
73
+
74
+ ProductImageDestroy: function(element) {
75
+ showStatus('Removing Image...');
76
+ element.hide();
77
+ new Ajax.Request(urlify($('admin_shop_product_images_path').value, element.readAttribute('data-attachment_id')), {
78
+ method: 'delete',
79
+ onSuccess: function(data) {
80
+ $('images').insert({ 'bottom' : data.responseText })
81
+ element.remove()
82
+ hideStatus()
83
+ }.bind(this),
84
+ onFailure: function(data) {
85
+ element.show();
86
+ hideStatus();
87
+ }.bind(this)
88
+ });
89
+ },
90
+
91
+ ImageSubmit: function() {
92
+ showStatus('Uploading Image...')
93
+ },
94
+
95
+ ImageClose: function() {
96
+ Element.closePopup('new_image_popup')
97
+ Element.closePopup('browse_images_popup')
98
+
99
+ $$('.clearable').each(function(input) {
100
+ input.value = ''
101
+ })
102
+ }
103
+
104
+ })
105
+
106
+ function urlify(route, id) {
107
+ var url = route
108
+ if ( id !== undefined ) {
109
+ url += '/' + id
110
+ }
111
+
112
+ url += '.js?' + new Date().getTime()
113
+
114
+ return url
115
+ }
@@ -0,0 +1,65 @@
1
+ var ShopProducts = {}
2
+
3
+ document.observe("dom:loaded", function() {
4
+ shop = new Shop()
5
+ shop.ProductsInitialize()
6
+
7
+ Event.addBehavior({
8
+ // empty
9
+ })
10
+ })
11
+
12
+ var Shop = Class.create({
13
+
14
+ ProductsInitialize: function() {
15
+ if($('products_map')) {
16
+ this.ProductsSort()
17
+ this.CategoriesSort()
18
+ }
19
+ },
20
+
21
+
22
+ CategoriesSort: function() {
23
+ Sortable.create('shop_categories', {
24
+ overlap: 'vertical',
25
+ only: 'category',
26
+ handle: 'handle',
27
+ onUpdate: function() {
28
+ new Ajax.Request('/admin/shop/categories/sort', {
29
+ method: 'put',
30
+ parameters: {
31
+ 'categories':Sortable.serialize('shop_categories')
32
+ }
33
+ })
34
+ }
35
+ })
36
+ },
37
+
38
+ ProductsSort: function() {
39
+ var categories = Array()
40
+ $$('li.category').each(function(el, i) {
41
+ categories[i] = $(el).id + '_products'
42
+ })
43
+
44
+ categories.each(function(category) {
45
+ Sortable.create(category, {
46
+ overlap: 'vertical',
47
+ only: 'product',
48
+ handle: 'handle',
49
+ dropOnEmpty: true,
50
+ hoverclass: 'hover',
51
+ containment: categories,
52
+ onUpdate: function() {
53
+ new Ajax.Request('/admin/shop/products/sort', {
54
+ method: 'put',
55
+ parameters: {
56
+ 'category_id': $(category).readAttribute('data-id'),
57
+ 'products':Sortable.serialize(category)
58
+ }
59
+ })
60
+ }.bind(this)
61
+ })
62
+ })
63
+ }
64
+
65
+ })
@@ -0,0 +1,86 @@
1
+ .drawer_contents th.label
2
+ white:
3
+ space: nowrap
4
+
5
+ .drawer_contents select
6
+ width: 100%
7
+
8
+ .drawer_contents .date
9
+ float: left
10
+ width: 93%
11
+ heigth: 18px
12
+ font:
13
+ size: 16px
14
+
15
+ .tabs .close
16
+ display: none
17
+
18
+ #content
19
+ positon: relative
20
+
21
+ #popups
22
+ display: none
23
+
24
+ .popup
25
+ position: relative
26
+ overflow: hidden
27
+
28
+ .close
29
+ position: absolute
30
+ right: 2px
31
+ top: 9px
32
+ width: 20px
33
+ height: 20px
34
+ overflow: hidden
35
+ display: block
36
+ cursor: pointer
37
+ background:
38
+ image: url('/images/admin/minus_disabled.png')
39
+ repeat: no-repeat
40
+ position: 0 0
41
+ cursor: pointer
42
+
43
+ &:hover
44
+ background:
45
+ image: url('/images/admin/minus.png')
46
+
47
+ h1
48
+ position: relative
49
+
50
+ .button
51
+ float: right
52
+ margin-left: 10px
53
+ margin-top: -5px
54
+ display: block
55
+ height: 16px
56
+ padding: 6px 8px
57
+ font:
58
+ size: 12px
59
+ background:
60
+ color: #eeeeee
61
+ image: url(/images/admin/buttons_background.png)
62
+ position: 0 0
63
+ repeat: repeat-x
64
+ color: #333333
65
+ text:
66
+ decoration: none
67
+ shadow: 1px 1px 1px #eeeeee
68
+ cursor: pointer
69
+ border:
70
+ radius: 5px
71
+ -moz:
72
+ border:
73
+ radius: 5px
74
+ -webkit:
75
+ border:
76
+ radius: 5px
77
+
78
+ img
79
+ position: relative
80
+ top: -2px
81
+
82
+ &:hover
83
+ background: #ffffff
84
+ color: #000000
85
+ text:
86
+ shadow: 1px 1px 1px #ffffff
@@ -0,0 +1,158 @@
1
+ #product_attachments
2
+ overflow: hidden
3
+ padding:
4
+ top: 10px
5
+
6
+ li.image
7
+ float: left
8
+ padding: 10px
9
+ height: 100px
10
+ width: 100px
11
+ margin:
12
+ right: 10px
13
+ border:
14
+ radius: 6px
15
+ -moz:
16
+ border:
17
+ radius: 6px
18
+ -webkit:
19
+ border:
20
+ radius: 6px
21
+ cursor: move
22
+ overflow: hidden
23
+ *
24
+ vertical:
25
+ align: middle
26
+
27
+ .wrapper
28
+ display: table-cell
29
+ height: 100px
30
+ width: 100px
31
+ text:
32
+ align: center
33
+ vertical:
34
+ align: middle
35
+
36
+ img
37
+ width: 100px
38
+ max:
39
+ height: 100px
40
+
41
+ .title, .caption
42
+ display: none
43
+
44
+ .actions
45
+ position: absolute
46
+ display: block
47
+ width: 100%
48
+ top: 0
49
+ left: 0
50
+
51
+ .delete
52
+ position: absolute
53
+ right: -2px
54
+ top: 4px
55
+ width: 20px
56
+ height: 20px
57
+ overflow: hidden
58
+ display: block
59
+ cursor: pointer
60
+ background:
61
+ image: url('/images/admin/minus_disabled.png')
62
+ repeat: no-repeat
63
+ position: 0 0
64
+ cursor: pointer
65
+
66
+ &:hover
67
+ background:
68
+ image: url('/images/admin/minus.png')
69
+
70
+ &:first-child
71
+
72
+ img
73
+ border:
74
+ width: 2px
75
+ color: #cc0000
76
+ style: solid
77
+
78
+ &:hover
79
+ background:
80
+ color: #f9f6fe
81
+
82
+ #browse_images_popup
83
+ width: 460px
84
+ padding:
85
+ bottom: 10px
86
+
87
+ #images
88
+ overflow: hidden
89
+ padding: 5px
90
+ bottom: 10px
91
+
92
+ li.image
93
+ position: relative
94
+ display: block
95
+ float: left
96
+ height: 70px
97
+ padding: 10px
98
+ border:
99
+ radius: 6px
100
+ -moz:
101
+ border:
102
+ radius: 6px
103
+ -webkit:
104
+ border:
105
+ radius: 6px
106
+ cursor: pointer
107
+
108
+ *
109
+ vertical:
110
+ align: middle
111
+
112
+ .wrapper
113
+ display: table-cell
114
+ height: 70px
115
+ width: 70px
116
+ text:
117
+ align: center
118
+ vertical:
119
+ algin: middle
120
+
121
+ img
122
+ width: 70px
123
+
124
+ .title
125
+ display: none
126
+
127
+ .caption
128
+ display: none
129
+
130
+ &:hover
131
+ background:
132
+ color: #8888888
133
+
134
+ #new_image_popup
135
+ color: #333333
136
+
137
+ ol
138
+ padding: 10px
139
+
140
+ li
141
+ overflow: hidden
142
+ padding:
143
+ bottom: 18px
144
+ &.image_file
145
+ padding-bottom: 38px
146
+ text-align: right
147
+ &.image_submit
148
+ position: absolute
149
+ right: 10px
150
+ bottom: 10px
151
+ padding-bottom: 0
152
+ label
153
+ display: block
154
+ float: left
155
+ width: 70px
156
+
157
+ input[type=text]
158
+ float: left