OSDN Git Service

t#32471:add profiles
[pettanr/pettanr.git] / app / models / sheet_panel.rb
1 class SheetPanel < ActiveRecord::Base
2   belongs_to :author
3   belongs_to :panel
4   belongs_to :sheet
5   accepts_nested_attributes_for :panel, :allow_destroy => true
6   
7   validates :sheet_id, :numericality => {:allow_blank => true}
8   validates :panel_id, :numericality => {:allow_blank => true}
9   validates :author_id, :presence => true, :numericality => true, :existence => {:both => false}
10   validates :x, :presence => true, :numericality => true
11   validates :y, :presence => true, :numericality => true
12   validates :z, :presence => true, :numericality => {:greater_than => 0}
13   validates :t, :presence => true, :numericality => {:greater_than_or_equal_to => 0}
14   
15   def supply_default
16     self.x = 15
17     self.y = 15
18     if self.sheet
19       self.t = self.sheet.new_t 
20       self.z = self.sheet.new_z 
21     else
22       self.sheet_id = nil
23       self.panel_id = nil
24       self.z = 1
25       self.t = nil
26     end
27   end
28   
29   def overwrite au
30     return false unless au
31     self.author_id = au.id
32   end
33   
34   def own? roles
35     roles = [roles] unless roles.respond_to?(:each)
36     au = SheetPanel.get_author_from_roles roles
37     return false unless au
38     self.author_id == au.id
39   end
40   
41   def visible? roles
42     if MagicNumber['run_mode'] == 0
43       return false unless guest_role_check(roles)
44     else
45       return false unless reader_role_check(roles)
46     end
47     return true if self.sheet.own?(roles)
48     self.sheet.visible? roles
49   end
50   
51   def self.default_page_size
52     25
53   end
54   
55   def self.max_page_size
56     100
57   end
58   
59   def self.page prm = nil
60     page = prm.to_i
61     page = 1 if page < 1
62     page
63   end
64   
65   def self.page_size prm = self.default_page_size
66     page_size = prm.to_i
67     page_size = self.max_page_size if page_size > self.max_page_size
68     page_size = self.default_page_size if page_size < 1
69     page_size
70   end
71   
72   def self.play_list_where cid
73     ['sheet_panels.sheet_id = ?', cid]
74   end
75   
76   def self.list_where
77     'sheets.visible > 0'
78   end
79   
80   def self.mylist_where au
81     ['sheet_panels.author_id = ?', au.id]
82   end
83   
84   def self.himlist_where au
85     ['sheet_panels.author_id = ? and sheets.visible > 0', au.id]
86   end
87   
88   def self.play_list sheet, author
89     SheetPanel.where(self.play_list_where(sheet.id)).includes(SheetPanel.list_opt).order('sheet_panels.t')
90   end
91   
92   def self.list page = 1, page_size = self.default_page_size
93     SheetPanel.where(self.list_where()).includes(SheetPanel.list_opt).order('sheet_panels.updated_at desc').offset((page -1) * page_size).limit(page_size)
94   end
95   
96   def self.mylist au, page = 1, page_size = Author.default_sheet_panel_page_size
97     SheetPanel.where(self.mylist_where(au)).includes(SheetPanel.list_opt).order('sheet_panels.updated_at desc').offset((page -1) * page_size).limit(page_size)
98   end
99   
100   def self.himlist au, page = 1, page_size = Author.default_sheet_panel_page_size
101     SheetPanel.where(self.himlist_where(au)).includes(SheetPanel.list_opt).order('sheet_panels.updated_at desc').offset((page -1) * page_size).limit(page_size)
102   end
103   
104   def self.list_paginate page = 1, page_size = self.default_page_size
105     Kaminari.paginate_array(Array.new(SheetPanel.where(self.list_where()).includes(SheetPanel.list_opt).count, nil)).page(page).per(page_size)
106   end
107   
108   def self.mylist_paginate au, page = 1, page_size = Author.default_sheet_panel_page_size
109     Kaminari.paginate_array(Array.new(SheetPanel.where(self.mylist_where(au)).includes(SheetPanel.list_opt).count, nil)).page(page).per(page_size)
110   end
111   
112   def self.himlist_paginate au, page = 1, page_size = Author.default_sheet_panel_page_size
113     Kaminari.paginate_array(Array.new(SheetPanel.where(self.himlist_where(au)).includes(SheetPanel.list_opt).count, nil)).page(page).per(page_size)
114   end
115   
116   def self.list_by_sheet_where sheet_id
117     ['sheet_panels.sheet_id = ?', sheet_id]
118   end
119   
120   def self.list_by_sheet sheet_id, roles, page = 1, page_size = self.default_page_size
121     self.where(self.list_by_sheet_where(sheet_id)).includes(self.list_opt).order('sheet_panels.updated_at desc').offset((page -1) * page_size).limit(page_size)
122   end
123   
124   def self.list_by_panel_where panel_id
125     ['sheet_panels.panel_id = ?', panel_id]
126   end
127   
128   def self.list_by_panel panel_id, roles, page = 1, page_size = self.default_page_size
129     self.where(self.list_by_panel_where(panel_id)).includes(self.list_opt).order('sheet_panels.updated_at desc').offset((page -1) * page_size).limit(page_size)
130   end
131   
132   def self.list_opt
133     {
134       :author => {}, 
135       :sheet => {
136         :author => {}
137       }, 
138       :panel => {
139         :author => {}, 
140         :panel_pictures => {:picture => {:artist => {}, :license => {}}}, 
141         :speech_balloons =>{:balloon => {}, :speech => {}}
142       }
143     }
144   end
145   
146   def self.list_json_opt
147     {:include => {
148       :author => {}, 
149       :sheet => {
150         :author => {}
151       }, 
152       :panel => {
153         :author => {}, 
154         :panel_pictures => {:picture => {:artist => {}, :license => {}}}, 
155         :speech_balloons =>{:balloon => {}, :speech => {}}
156       }
157     }}
158   end
159   
160   def self.show spid, roles
161     opt = {}
162     opt.merge!(SheetPanel.show_opt)
163     res = SheetPanel.find spid, opt
164     raise ActiveRecord::Forbidden unless res.visible?(roles)
165     res
166   end
167   
168   def self.edit spid, au
169     opt = {}
170     opt.merge!(SheetPanel.show_opt)
171     res = SheetPanel.find spid, opt
172     raise ActiveRecord::Forbidden unless res.own?(au)
173     res
174   end
175   
176   def self.show_opt
177     {:include => {
178       :author => {}, 
179       :sheet => {
180         :author => {}
181       }, 
182       :panel => {
183         :author => {}, 
184         :panel_pictures => {:picture => {:artist => {}, :license => {}}}, 
185         :speech_balloons =>{:balloon => {}, :speech => {}}
186       }
187     }}
188   end
189   
190   def elements
191     self.panel.elements
192   end
193   
194   def sheet_panel_as_json au
195     panel_include = if self.panel and self.panel.visible?(au)
196       {:include => {:author => {}}, :methods => :elements}
197     else
198       {:include => {:author => {}}}
199     end
200     self.to_json({:include => {:sheet => {:include => {:author => {}}}, :author => {}, :panel => panel_include}})
201   end
202   
203   def self.list_as_json_text ary, au
204     '[' + ary.map {|i| i.sheet_panel_as_json(au) }.join(',') + ']'
205   end
206   
207   def licensed_pictures
208     if self.panel
209       self.panel.licensed_pictures
210     else
211       {}
212     end
213   end
214   
215     def self.panelize elements_attributes
216       elements_attributes = [elements_attributes] unless elements_attributes.is_a?(Array)
217       hash = {}
218       index = 0
219       elements_attributes.each do |element_attributes|
220         hash[self.to_s.tableize + '_attributes'] ||= {}
221         n = if element_attributes['id']
222           element_attributes['id'].to_s
223         else
224           index += 1
225           'new' + index.to_s 
226         end
227         hash[self.to_s.tableize + '_attributes'][n] = element_attributes
228       end
229       hash
230     end
231     
232     def copy_attributes
233       r = self.attributes
234       r.delete 'id'
235       r.delete 'sheet_id'
236       r.delete 'panel_id'   # create panel
237       r.delete 'created_at'
238       r.delete 'updated_at'
239       r
240     end
241   
242   def copyable?
243     if self.panel and self.panel.publish? == false
244       false
245     else
246       true
247     end
248   end
249   
250   def boost au
251     if self.panel
252       self.panel.author_id = au.id
253       self.panel.panel_elements.each do |elm|
254         elm.new_panel = self
255         elm.boost
256       end
257     end
258   end
259   
260   def panel_attributes
261     if self.panel
262       {'panel_attributes' => self.panel.copy}
263     else
264       {}
265     end
266   end
267   
268   def self.new_t sheet_id
269     r = SheetPanel.max_t(sheet_id)
270     r.blank? ? 0 : r.to_i + 1
271   end
272   
273   def self.max_t sheet_id
274     SheetPanel.maximum(:t, :conditions => ['sheet_id = ?', sheet_id])
275   end
276   
277   def self.find_t sheet_id, t
278     SheetPanel.find(:first, :conditions => ['sheet_id = ? and t = ?', sheet_id, t])
279   end
280   
281   def self.collect_t sheet_panel
282     r = SheetPanel.find(:all, :conditions => ['sheet_id = ?', sheet_panel.sheet_id], :order => 't')
283     r.map {|sp| sp.t}
284   end
285   
286   def self.serial? ary
287     i = 0
288     ary.compact.sort.each do |t|
289       break false unless t == i
290       i += 1
291     end
292     ary.compact.size == i
293   end
294   
295   def self.validate_t sheet_panel
296     SheetPanel.serial?(SheetPanel.collect_t(sheet_panel))
297   end
298   
299   def insert_shift
300     SheetPanel.update_all('t = t + 1', ['sheet_id = ? and t >= ?', self.sheet_id, self.t])
301   end
302   
303   def lesser_shift old_t
304     self.t = 0 if self.t < 0
305     SheetPanel.update_all('t = t + 1', ['sheet_id = ? and (t >= ? and t < ?)', self.sheet_id, self.t, old_t])
306   end
307   
308   def higher_shift old_t
309     nf = SheetPanel.find_t(self.sheet_id, self.t)
310     max_t = SheetPanel.max_t(self.sheet_id).to_i
311     self.t = max_t if self.t > max_t
312     SheetPanel.update_all('t = t - 1', ['sheet_id = ? and (t > ? and t <= ?)', self.sheet_id, old_t, self.t])
313   end
314   
315   def update_shift old_t
316     if self.t > old_t
317       higher_shift old_t
318     else
319       lesser_shift old_t
320     end
321   end
322   
323   def rotate old_t = nil
324     if self.new_record?
325       if self.t.blank?
326         self.t = SheetPanel.new_t self.sheet_id
327       else
328         self.insert_shift
329       end
330     else
331       if self.t.blank?
332       else
333         self.update_shift old_t
334       end
335     end
336   end
337   
338   def allow?
339     return nil if self.sheet_id == nil or self.panel_id == nil
340     self.sheet.own?(self.author) and self.panel.usable?(self.author)
341   end
342   
343   def store old_t = nil
344     res = false
345     SheetPanel.transaction do
346       case self.allow?
347       when true
348         self.rotate old_t
349       when false
350         raise ActiveRecord::Forbidden
351       else
352       end
353       res = self.save
354       raise ActiveRecord::Rollback unless res
355       res = SheetPanel.validate_t(self) 
356       unless res
357         self.errors.add :t, 'unserialized'
358         raise ActiveRecord::Rollback 
359       end
360     end
361     res
362   end
363   
364   def destroy_and_shorten
365     res = false
366     SheetPanel.transaction do
367       SheetPanel.update_all('t = t - 1', ['sheet_id = ? and (t > ?)', self.sheet_id, self.t])
368       raise ActiveRecord::Rollback unless self.destroy
369       res = true
370     end
371     res
372   end
373   
374     # element.rb
375     def self.colum_structures
376       @@colum_structures ||= {
377       }
378     end
379     
380     def self.path_name with_engine = false
381       self.to_s.tableize
382     end
383     
384     def new_index
385       @new_index
386     end
387     
388     def new_index= v
389       @new_index = v
390     end
391     
392     def new_sheet
393       @new_sheet
394     end
395     
396     def new_sheet= v
397       @new_sheet = v
398     end
399     
400     def get_sheet
401       self.sheet || @new_sheet
402     end
403     
404     def tag_id c = nil
405       'sheet' + self.tag_sheet_id + self.tag_element_type + self.tag_element_id + c.to_s
406     end
407     
408     def field_tag_id f
409       self.tag_id + f.to_s
410     end
411     
412     def tag_sheet_id
413       self.get_sheet == nil or self.get_sheet.new_record? ? '0' : self.get_sheet.id.to_s
414     end
415     
416     def tag_element_id
417       self.new_record? ? '0' : self.id.to_s
418     end
419     
420     def tag_element_type
421       'sheet_panel'
422     end
423     
424     def tag_new_index
425       self.new_index.to_s
426     end
427     
428     def path_name with_engine = false
429       self.class.path_name(with_engine)
430     end
431     
432     def form_template with_engine = false
433       self.path_name(with_engine) + '/form'
434     end
435     
436     def scenario_template with_engine = false
437       self.path_name(with_engine) + '/scenario'
438     end
439     
440     def element_face_template with_engine = false
441       self.path_name(with_engine) + '/element_face'
442     end
443     
444     def form_helper_template(colum_name)
445       self.class.colum_structures[colum_name][:helper]
446     end
447     
448     def tag_attributes column = nil, opt = {}
449       {
450         :id => self.field_tag_id(column), :sheet_id => self.tag_sheet_id, 
451         :element_id => self.tag_element_id, :element_type => self.tag_element_type
452       }.merge(opt)
453     end
454     
455     def field_tag_attributes column, no_attr, opt = {}
456       self.tag_attributes(column).merge(
457         {:column => column, :new_index => self.tag_new_index, :no_attr => no_attr}
458       ).merge(opt)
459     end
460     
461     #render element by body
462     def any_tag_attributes name = nil, opt = {}
463       r = self.tag_attributes(name)
464       r.merge!(
465         {:new_index => self.tag_new_index}
466       ) if self.new_index
467       r.merge(opt)
468     end
469     
470     def select_tag_attributes(selected, column, no_attr)
471       [
472         :last, :first, 
473         {:html => {:selected => selected}}, 
474         self.field_tag_attributes(column, no_attr)
475       ]
476     end
477     
478     def tag_attr column = nil, opt = {}
479       self.tag_attributes(column, opt).to_attr
480     end
481     
482     def field_tag_attr column, no_attr, opt = {}
483       self.field_tag_attributes(column, no_attr, opt).to_attr
484     end
485     
486     def any_tag_attr name = nil, opt = {}
487       self.any_tag_attributes(name, opt).to_attr
488     end
489     
490 end