OSDN Git Service

m
[pettanr/pettanr.git] / app / models / sheet.rb
1 class Sheet < ActiveRecord::Base
2   has_many :sheet_panels
3   has_many :story_sheets
4   belongs_to :author
5   
6   validates :caption, :presence => true, :length => {:maximum => 100}
7   validates :width, :presence => true, :numericality => true, :natural_number => true
8   validates :height, :presence => true, :numericality => true, :natural_number => true
9   validates :visible, :presence => true, :numericality => true, :inclusion => {:in => 0..1}
10   accepts_nested_attributes_for :sheet_panels, :allow_destroy => true
11   before_validation :valid_encode
12   
13   def valid_encode
14     ['caption'].each do |a|
15       next if attributes[a] == nil
16       raise Pettanr::BadRequest unless attributes[a].valid_encoding?
17     end
18   end
19   
20   def self.each_element_class_names
21     {'SheetPanel' => 'sheet_panels'}.each do |k, n|
22       yield k
23     end
24   end
25   
26   def self.class_name_to_class k
27     Object.const_get k
28   end
29   
30   def self.each_element_classes
31     self.each_element_class_names do |k|
32       e = self.class_name_to_class k
33       yield e
34     end
35   end
36   
37   def elements_by_class_name class_name
38     self.__send__ class_name.tableize
39   end
40   
41   def supply_default
42     self.visible = 0 if self.visible.blank?
43   end
44   
45   def overwrite au
46     return false unless au
47     self.author_id = au.id
48   end
49   
50   def own? roles
51     roles = [roles] unless roles.respond_to?(:each)
52     au = Sheet.get_author_from_roles roles
53     return false unless au
54     self.author_id == au.id
55   end
56   
57   def visible? roles
58     if MagicNumber['run_mode'] == 0
59       return false unless guest_role_check(roles)
60     else
61       return false unless reader_role_check(roles)
62     end
63     return true if self.own?(roles)
64     return true if self.new_record?
65     self.visible > 0
66   end
67   
68   def usable? au
69     visible? au
70   end
71   
72   def symbol_filename
73   end
74   
75   def tag_id
76     'sheet' + self.tag_sheet_id
77   end
78   
79   def tag_sheet_id
80     self.new_record? ? '0' : self.id.to_s
81   end
82   
83   def field_tag_id f
84     self.tag_id + f.to_s
85   end
86   
87   def self.default_page_size
88     25
89   end
90   
91   def self.max_page_size
92     100
93   end
94   
95   def self.default_panel_size
96     30
97   end
98   
99   def self.max_panel_size
100     200
101   end
102   
103   def self.page prm = nil
104     page = prm.to_i
105     page = 1 if page < 1
106     page
107   end
108   
109   def self.page_size prm = self.default_page_size
110     page_size = prm.to_i
111     page_size = self.max_page_size if page_size > self.max_page_size
112     page_size = self.default_page_size if page_size < 1
113     page_size
114   end
115   
116   def self.list_where
117     'sheets.visible > 0'
118   end
119   
120   def self.mylist_where au
121     ['sheets.author_id = ?', au.id]
122   end
123   
124   def self.himlist_where au
125     ['sheets.author_id = ? and sheets.visible > 0', au.id]
126   end
127   
128   def self.list page = 1, page_size = self.default_page_size
129     Sheet.where(self.list_where()).includes(Sheet.list_opt).order('sheets.updated_at desc').offset((page -1) * page_size).limit(page_size)
130   end
131   
132   def self.mylist au, page = 1, page_size = Author.default_sheet_page_size
133     Sheet.where(self.mylist_where(au)).includes(Sheet.list_opt).order('sheets.updated_at desc').offset((page -1) * page_size).limit(page_size)
134   end
135   
136   def self.himlist au, page = 1, page_size = Author.default_sheet_page_size
137     Sheet.where(self.himlist_where(au)).includes(Sheet.list_opt).order('sheets.updated_at desc').offset((page -1) * page_size).limit(page_size)
138   end
139   
140   def self.list_paginate page = 1, page_size = self.default_page_size
141     Kaminari.paginate_array(Array.new(Sheet.where(self.list_where()).count, nil)).page(page).per(page_size)
142   end
143   
144   def self.mylist_paginate au, page = 1, page_size = Author.default_sheet_page_size
145     Kaminari.paginate_array(Array.new(Sheet.where(self.mylist_where(au)).count, nil)).page(page).per(page_size)
146   end
147   
148   def self.himlist_paginate au, page = 1, page_size = Author.default_sheet_page_size
149     Kaminari.paginate_array(Array.new(Sheet.where(self.himlist_where(au)).count, nil)).page(page).per(page_size)
150   end
151   
152   def self.list_opt
153     {:sheet_panels => {:panel => {}}, :author => {} }
154   end
155   
156   def self.list_json_opt
157     {:include => {:sheet_panels => {:include => {:panel => {}}}, :author => {}}}
158   end
159   
160   def self.show sid, roles
161     opt = {}
162     opt.merge!(Sheet.show_opt)
163     res = Sheet.find(sid, opt)
164     raise ActiveRecord::Forbidden unless res.visible?(roles)
165     res
166   end
167   
168   def self.edit sid, au
169     opt = {}
170     opt.merge!(Sheet.show_opt)
171     res = Sheet.find(sid, opt)
172     raise ActiveRecord::Forbidden unless res.own?(au)
173     res
174   end
175   
176   def self.show_opt
177     {:include => {:sheet_panels => {:panel => {}}, :author => {}}}
178   end
179   
180   def self.show_json_opt
181     {:include => {:sheet_panels => {:include => {:panel => {}}}, :author => {}}}
182   end
183   
184   def parts_element
185     r = []
186     self.class.each_element_class_names do |k|
187       r += (self.elements_by_class_name(k) || [])
188     end
189     r
190   end
191   
192   def zorderd_elements
193     res = []
194     self.parts_element.each do |e|
195       res[e.z-1] = e
196     end
197     res
198   end
199   
200   def sheet_elements
201     res = []
202     self.parts_element.each do |e|
203       res[e.t] = e
204     end
205     res
206   end
207   
208   def new_t
209     self.sheet_elements.size
210   end
211   
212   def new_z
213     self.sheet_elements.size + 1
214   end
215   
216   def self.visible_count
217     Sheet.count 'visible > 0'
218   end
219   
220   def self.collect_element_value elements, name
221     elements.map {|e|
222       e.map {|o|
223         if o['_destroy'] or o[:_destroy]
224           nil
225         else
226           o[name]
227         end
228       }.compact
229     }.flatten
230   end
231   
232   def self.validate_serial ary, offset = 0
233     i = offset
234     ary.compact.sort.each do |n|
235       break false unless n == i
236       i += 1
237     end
238     ary.compact.size == i - offset
239   end
240   
241   def self.validate_element_serial elements, name, offset = 0
242     Sheet.validate_serial(Sheet.collect_element_value(elements, name), offset)
243   end
244   
245   def self.validate_elements_serial c
246     c.map {|conf|
247       Sheet.validate_element_serial(conf[:elements], conf[:name], conf[:offset]) ? nil : false
248     }.compact.empty?
249   end
250   
251   def validate_serial_list
252     l = []
253     self.class.each_element_class_names do |k|
254       l << self.elements_by_class_name(k)
255     end
256 #    l = [self.sheet_panels]
257     [
258       {:elements => l, :name => :t, :offset => 0}, 
259       {:elements => l, :name => :z, :offset => 1}
260     ]
261   end
262   
263   def validate_child
264 #    r1 = Panel.validate_elements_id validate_id_list
265     Sheet.validate_elements_serial validate_serial_list
266   end
267   
268   def boost
269     @new_element_index = 0
270     self.panel_elements.each do |elm|
271       if elm.new_record?
272         elm.new_index = @new_element_index
273         @new_element_index += 1
274       end
275     end
276   end 
277   
278   def store attr, au
279     if attr == false
280       self.errors.add :base, I18n.t('errors.invalid_json')
281       return false
282     end
283     self.attributes = attr
284     self.overwrite au
285     res = false
286     Sheet.transaction do
287       self.sheet_elements.each do |elm|
288         elm.new_sheet = self
289         elm.boost au
290       end
291       res = self.save
292       unless validate_child
293         res = false
294         self.errors.add :base, I18n.t('errors.invalid_t')
295         raise ActiveRecord::Rollback
296       end
297     end
298     res
299   end
300   
301   def destroy_with_sheet_panel
302     res = false
303     Sheet.transaction do
304       self.sheet_panels.each do |sheet_panel|
305         raise ActiveRecord::Rollback unless sheet_panel.destroy
306       end
307       raise ActiveRecord::Rollback unless self.destroy
308       res = true
309     end
310     res
311   end
312   
313   def scenario
314     panels.map {|panel|
315       panel.scenario
316     }.join
317   end
318   
319   def plain_scenario
320     panels.map {|panel|
321       panel.plain_scenario
322     }.join
323   end
324   
325   def licensed_pictures
326     r = {}
327     self.sheet_elements.each do |elm|
328       r.merge!(elm.licensed_pictures)
329     end
330     r
331   end
332   
333   def copyable?
334     r = true
335     Sheet.each_element_class_names do |n|
336       self.elements_by_class_name(n).each do |elm|
337         next if elm.copyable?
338         r = false
339         break
340       end
341       break unless r
342     end
343     r
344   end
345   
346   def copy
347     attr = self.copy_attributes
348     Sheet.each_element_class_names do |n|
349       element_attr = Sheet.class_name_to_class(n).panelize(
350         self.elements_by_class_name(n).map {|elm|
351           elm.copy_attributes.merge elm.panel_attributes
352         }
353       )
354       attr.merge! element_attr
355     end
356     attr
357   end
358   
359   def copy_attributes
360     r = self.attributes
361     r.delete 'id'
362     r.delete 'author_id'
363     r.delete 'created_at'
364     r.delete 'updated_at'
365     r
366   end
367   
368   def self.panelize sheet
369     attr = sheet.attributes
370     attr.delete 'id'
371     attr
372   end
373   
374 end