class CamaleonCms::CustomFieldGroup < CamaleonCms::CustomField
self.primary_key = :id
# attrs required: name, slug, description
alias_attribute :site_id, :parent_id
default_scope { where.not(object_class: '_fields').reorder("#{CamaleonCms::CustomField.table_name}.field_order ASC") }
has_many :metas, ->{ where(object_class: 'CustomFieldGroup')}, :class_name => "CamaleonCms::Meta", foreign_key: :objectid, dependent: :destroy
has_many :fields, -> {where(object_class: '_fields')}, :class_name => "CamaleonCms::CustomField", foreign_key: :parent_id, dependent: :destroy
belongs_to :site, :class_name => "CamaleonCms::Site", foreign_key: :parent_id
validates_uniqueness_of :slug, scope: [:object_class, :objectid, :parent_id]
before_validation :before_validating
# add fields to group
# item:
# - sample: {"name"=>"Label", "slug"=>"my_slug", "description"=>"my description (optional)"}
# - options (textbox sample): {"field_key":"text_box","multiple":"1","required":"1","translate":"1"}
# * field_key (string) | translate (boolean) | default_value (unique value) | default_values (array - multiple values for this field) | label_eval (boolean) | multiple_options (array)
# * multiple_options (used for select, radio and checkboxes ): [{"title"=>"Option Title", "value"=>"2", "default"=>"1"}, {"title"=>"abcde", "value"=>"3"}]
# * label_eval: (Boolean, default false), true => will evaluate the label and description of current field using (eval('my_label')) to have translatable|dynamic labels
#****** check all options for each case in Admin::CustomFieldsHelper ****
# SAMPLE: my_model.add_field({"name"=>"Sub Title", "slug"=>"subtitle"}, {"field_key"=>"text_box", "translate"=>true, default_value: "Get in Touch"})
def add_manual_field(item, options)
c = get_field(item[:slug] || item["slug"])
return c if c.present?
field_item = self.fields.new(item)
if field_item.save
field_item.set_options(options)
auto_save_default_values(field_item, options)
end
field_item
end
alias_method :add_field, :add_manual_field
# return a field with slug = slug from current group
def get_field(slug)
self.fields.where(slug: slug).first
end
# only used by form on admin panel (protected)
# return array of failed_fields and full_fields [[failed fields], [all fields]]
def add_fields(items, item_options)
self.fields.where.not(id: items.map{|k, obj| obj['id'] }.uniq).destroy_all
cache_fields, order_index, errors_saved = [], 0, []
if items.present?
items.each do |i,item|
item[:field_order] = order_index
options = item_options[i] || {}
if item[:id].present? && (field_item = self.fields.where(id: item[:id]).first).present?
saved = field_item.update(item)
cache_fields << field_item
else
field_item = self.fields.new(item)
cache_fields << field_item
saved = field_item.save
auto_save_default_values(field_item, options) if saved
errors_saved << field_item unless saved
end
if saved
field_item.set_meta('_default', options)
order_index += 1
end
end
end
[errors_saved, cache_fields]
end
# generate the caption for this group
def get_caption
caption = ""
begin
case self.object_class
when "PostType_Post"
caption = "Fields for Contents in #{self.site.post_types.find(self.objectid).decorate.the_title}"
when 'PostType_Category'
caption = "Fields for Categories in #{self.site.post_types.find(self.objectid).decorate.the_title}"
when 'PostType_PostTag'
caption = "Fields for Post tags in #{self.site.post_types.find(self.objectid).decorate.the_title}"
when 'Widget::Main'
caption = "Fields for Widget (#{CamaleonCms::Widget::Main.find(self.objectid).name.translate})"
when 'Theme'
caption = "Field settings for Theme (#{self.site.themes.find(self.objectid).name rescue self.objectid})"
when 'NavMenu'
caption = "Field settings for Menus (#{CamaleonCms::NavMenu.find(self.objectid).name})"
when 'Site'
caption = "Field settings the site"
when 'PostType'
caption = "Fields for all Post_Types"
when 'Post'
p = CamaleonCms::Post.find(self.objectid).decorate
caption = "Fields for content (#{p.the_title})"
else # 'Plugin' or other class
caption = "Fields for #{self.object_class}"
end
rescue => e
Rails.logger.info "----------#{e.message}----#{self.attributes}"
end
caption
end
private
def before_validating
self.slug = "_group-#{self.name.to_s.parameterize}" unless self.slug.present?
end
# auto save the default field values
def auto_save_default_values(field, options)
options = options.with_indifferent_access
class_name = self.object_class.split("_").first
if ["Post", "Category", "Plugin", "Theme"].include?(class_name) && self.objectid.present? && (options[:default_value].present? || options[:default_values].present?)
if class_name == "Theme"
owner = "CamaleonCms::#{class_name}".constantize.where(id: self.objectid).first # owner model
else
owner = "CamaleonCms::#{class_name}".constantize.find(self.objectid) rescue "CamaleonCms::#{class_name}".constantize.where(slug: self.objectid).first # owner model
end
(options[:default_values] || [options[:default_value]] || []).each do |value|
owner.field_values.create!({custom_field_id: field.id, custom_field_slug: field.slug, value: fix_meta_value(value)}) if owner.present?
end
end
end
end