ProMotion-XLForm

ProMotion-XLForm provides a PM::XLFormScreen for ProMotion powered by the CocoaPod XLForm.

Warning

This gem is currently in very early-stage. Use it at your own risk :)

Build Status Gem Version

Installation

gem 'ProMotion-XLForm'

Then:

$ bundle
$ rake pod:install

Usage

PM::XLFormScreen include PM::ScreenModule so you'll have all ProMotion methods available.

To create a form, create a new PM::XLFormScreen and implement form_data.

class TestFormScreen < PM::XLFormScreen
  def form_data
  [
    {
      title:  'Account information',
      cells: [
        {
          title:       'Email',
          name:        :email,
          type:        :email,
          placeholder: 'Enter your email',
          required:    true
        },
        {
          title: 'Name',
          name:  :name,
          type:  :text,
          value: 'Default value'
        },
        {
          title: 'Sex',
          name: :sex,
          type: :selector_push,
          options: {
            male: 'Male',
            female: 'Female',
            other: 'Other'
          }
        }
      ]
    }
  ]
  end
end

Available types

  • :text
  • :name
  • :url
  • :email
  • :password
  • :number
  • :phone
  • :twitter
  • :account
  • :integer
  • :decimal
  • :textview
  • :selector_push
  • :selector_popover
  • :selector_action_sheet
  • :selector_alert_view
  • :selector_picker_view
  • :selector_picker_view_inline
  • :multiple_selector
  • :multiple_selector_popover
  • :selector_left_right
  • :selector_segmented_control
  • :date_inline
  • :datetime_inline
  • :time_inline
  • :countdown_timer_inline
  • :date
  • :datetime
  • :time
  • :countdown_timer
  • :datepicker
  • :picker
  • :slider
  • :check
  • :switch
  • :button
  • :info
  • :step_counter
  • :image (ProMotion-XLForm specific)
  • :color (ProMotion-XLForm specific using RSColorPicker)

Class options

class TestFormScreen < PM::XLFormScreen

  form_options required:  :asterisks, # add an asterisk to required fields
               on_save:   :'save_form:', # will be called when you touch save
               on_cancel: :cancel_form # will be called when you touch cancel

   def save_form(values)
     mp values
   end

   def cancel_form
   end
end

Getting values

You can get the values of your form with values. You can also get validation errors with validation_errors and check if the form is valid with valid?

Events

on_change, on_add and on_remove are available for cells, on_add and on_remove are available for sections.

{
  title: 'Sex',
  name: :sex,
  type: :selector_push,
  options: {
    male: 'Male',
    female: 'Female',
    other: 'Other'
  },
  on_change: lambda do |old_value, new_value|
    puts "Changed from #{old_value} to #{new_value}"
  end
}

Multivalued Sections (Insert, Delete, Reorder rows)

{
  title:  'Multiple value',
  name:   :multi_values,
  options: [:insert, :delete, :reorder],
  cells: [
    {
      title: 'Add a new tag',
      name:  :tag,
      type:  :text
    }
  ]
}

Custom Selectors

You can create a custom subform with a few options

{
  title:  'Custom section',
  cells: [
    {
      title: 'Custom',
      name:  :custom,
      cells: [
        {
            title: 'Some text',
            name:  :some_text,
            type:  :text
        },
        {
            title: 'Other text',
            name:  :some_other_text,
            type:  :text
        }
      ]
    }
  ]
}

By default, the cell will print a Hash.inspect of your subcells. You can change this by creating a valueTransformer and set value_transformer:.

{
  title: 'Custom',
  name:  :custom,
  value_transformer: MyValueTransformer
  cells: []
}

class MyValueTransformer < PM::ValueTransformer
  def transformedValue(value)
    return nil if value.nil?

    str = []
    str << value['some_text'] if value['some_text']
    str << value['some_other_text'] if value['some_other_text']

    str.join(',')
  end
end

For a more advanced custom selector, you can set view_controller_class:. See XLForm documentation for more informations.

Validators

You can add validators to cells.

{
  title:       'Email',
  name:        :email,
  type:        :email,
  required:    true,
  validators: {
    email: true
  }
}

:email and :url are available out of the box, as well as :regex. You will have to provide a valid regex and a message.

{
  title:       'Only letters',
  name:        :letters,
  type:        :text,
  required:    true,
  validators: {
    regex: { regex: /^[a-zA-Z]+$/, message: "Only letters please !" }
  }
}

Finally, you can provide a PM::Validator with a valid?(cell) method.

Make a row or section invisible depending on other rows values

You can show/hide cells depending on a cell value with a predicate

{
  title: 'Hide and seek',
  cells: [
    {
      title: 'Switch me',
      type: :switch,
      name: :hide_and_seek,
      value: true
    },
    {
      title: 'Appear when switch is on',
      name: :show_me,
      type: :info,
      hidden: {
        # the cell name wich will "trigger" the visibility
        name: :hide_and_seek,

        # the operand. Valid operands are :equal, :not_equal, :contains, :not_contains
        is: :equal,

        # the value which trigger the visibility
        value: true }
    },
    {
      title: 'Appear when switch is off',
      name: :hide_me,
      type: :info,

      # you can also write it this way
      hidden: ':hide_and_seek == false'
      # also valid ':some_text contains "a text"'
      #            ':some_text not contains "a text"'
    }
  ]
}

Appearance

You can change the appearance of the cell using the appearance hash

{
  title:   'Options',
  name:    'options',
  type:    :selector_push,
  appearance: {
    font: UIFont.fontWithName('Helvetica Neue', size: 15.0),
    detail_font: UIFont.fontWithName('Helvetica Neue', size: 12.0),
    color: UIColor.greenColor,
    detail_color: UIColor.blueColor,
    background_color: UIColor.grayColor
  },
  options: {
    "value_1" => "Value 1",
    "value_2" => "Value 2",
    "value_3" => "Value 3",
    "value_4" => "Value 4",
  }
}

You can also pass any key-value to configure your cell. Take a look at this for more information

{
  appearance: {
    "slider.tintColor" => UIColor.grayColor
  }
}

Contributing

  1. Fork it
  2. Create your feature branch (git checkout -b my-new-feature)
  3. Commit your changes (git commit -am 'Add some feature')
  4. Make some specs pass
  5. Push to the branch (git push origin my-new-feature)
  6. Create new Pull Request

License

Released under the MIT license.