themeum / kirki

Extending the customizer
https://kirki.org
MIT License
1.26k stars 328 forks source link

Select Field Won't Save When Using Options Over Theme_Mods #1751

Closed coleh33 closed 6 years ago

coleh33 commented 6 years ago

I am using the latest version from the develop branch but still having issues.

I have a select field inside a repeater element and it will not save values to the database. I am using options instead of theme_mods due to backwards compatibility I need with other options. I saw that there was some issues resolved previously with saving options when using options over theme_mods however the select field still doesn't appear to save values when used inside a repeater.

aristath commented 6 years ago

Can you please post your config here?

coleh33 commented 6 years ago
Kirki::add_config( 'alphamedia-blacklab-option', array(
  'capability'    => 'edit_theme_options',
  'option_type'   => 'option',
  'option_name'   => 'alphamedia_options'
) );

Kirki::add_field( 'alphamedia-blacklab-option', array(
  'type'        => 'repeater',
  'settings'    => 'audio-player-multiple-options',
  'label'       => esc_attr__( 'Streams', 'alphamedia-blacklab' ),
  'description' => esc_attr__( 'Setup the audio player streams.', 'alphamedia-blacklab' ),
  'section'     => 'audio_player_settings',
  'row_label' => array(
    'type' => 'text',
    'value' =>  esc_attr__( 'Audio Stream', 'alphamedia-blacklab' ),
  ),
  'fields' => array(
    'station_name' => array(
      'type'        => 'text',
      'label'       => esc_attr__( 'Station Name', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Enter the station name that will appear with the audio stream.', 'alphamedia-blacklab' ),
    ),
    'station_logo' => array(
      'type'        => 'image',
      'label'       => esc_attr__( 'Station Logo', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Upload the station logo for the stream here.', 'alphamedia-blacklab' ),
    ),
    'provider' => array(
      'type'        => 'select',
      'label'       => esc_attr__( 'Streaming Provider', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Select a streaming provider if the station plays music and needs playlist data.', 'alphamedia-blacklab' ),
      'choices' => array(
        'wide-orbit' => 'Wide Orbit',
        'triton' => 'Triton',
        'first-streaming' => 'First Streaming',
      ),
    ),
    'playlist_id' => array(
      'type'        => 'text',
      'label'       => esc_attr__( 'Playlist ID', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Enter the playlist ID provided by the streaming provider. This will allow song history to work.', 'alphamedia-blacklab' ),
    ),
    'aac_link' => array(
      'type'        => 'text',
      'label'       => esc_attr__( 'AAC Stream Link', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Enter the URL to the AAC version of the audio stream.', 'alphamedia-blacklab' ),
    ),
    'mp3_link' => array(
      'type'        => 'text',
      'label'       => esc_attr__( 'MP3 Stream Link', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Enter the URL to the MP3 version of the audio stream.', 'alphamedia-blacklab' ),
    ),
    'dfp_id' => array(
      'type'        => 'text',
      'label'       => esc_attr__( 'DFP ID', 'alphamedia-blacklab' ),
      'description' => esc_attr__( 'Enter the DFP ID for the station.', 'alphamedia-blacklab' ),
    ),
  ),
  'active_callback' => array(
    array(
      'setting' => 'audio-player-mode',
      'operator' => '==',
      'value'    => 'multiple',
    ),
  ),
) );
aristath commented 6 years ago

@coleh33 I just tested this and I can't replicate your issue... On a fresh installation I added your code, went to the customizer, added a couple of rows in the repeater and saved. After saving the options I added this

var_dump( get_option( 'alphamedia_options', array() ) );

The value of the select control inside the repeater gets saved fine in the db! This is what I got:

array (size=1)
  'audio-player-multiple-options' => 
    array (size=2)
      0 => 
        array (size=7)
          'station_name' => string 'aaaa' (length=4)
          'station_logo' => int 1692
          'provider' => string 'first-streaming' (length=15)
          'playlist_id' => string '' (length=0)
          'aac_link' => string '' (length=0)
          'mp3_link' => string '' (length=0)
          'dfp_id' => string '' (length=0)
      1 => 
        array (size=7)
          'station_name' => string 'lalalalalololo' (length=14)
          'station_logo' => string '' (length=0)
          'provider' => string 'triton' (length=6)
          'playlist_id' => string '' (length=0)
          'aac_link' => string '' (length=0)
          'mp3_link' => string '' (length=0)
          'dfp_id' => string '' (length=0)
coleh33 commented 6 years ago

I found out the issue. When hitting save in the customizer it won't save the first selection if another selection hasn't been selected. When I used the dropdown and selected another option, it saved properly. Is the select field supposed to save the initial loaded option once save is hit or does it need to actually select another option first and then go back to the initial selection to save it properly?

aristath commented 6 years ago

Is the select field supposed to save the initial loaded option once save is hit or does it need to actually select another option first and then go back to the initial selection to save it properly?

Ah ok, that makes sense. That is just the default behavior of the WP Customizer. The customizer only saves modified values and not the default values, because it assumes that you'll use get_theme_mod() by defining a default value there. This way it doesn't clutter the database with unnecessary information.

aristath commented 6 years ago

@coleh33 this will have to be addressed in the method you use to get the values. So if the value is unset, then use the default. Closing this ticket as this is what WP does in the customizer by default for good reason and we should not really change it and force-save default values.