ProcessWire - Dynamic Backend Fields
How To populate or show fields in backend depending on selection of other fields ?
Field Dependencies in ProcessWire[Bearbeiten]
https://processwire.com/docs/fields/dependencies/
Show If und Required If[Bearbeiten]
Show if Dependency[Bearbeiten]
Zeige ein Feld nur dann im Backend an, wenn eine Bedingung erfüllt ist.
Wo stellt man Show if ein ?[Bearbeiten]
1. Auf Feldebene
In den Feldeinstellungen (auch innerhalb eines Templates) unter Visibility / Sichtbarkeit.
2. Über die API auf einem beliebigen Inputfield Objekt oder Module
$inputfield->showIf = "field=value";
3. Über Module (z.B. im Formbuilder)
Require if[Bearbeiten]
Benötigt wenn - funktioniert ähnlich wie show if. Option im Backend bei den Feldeinstellungen wenn man Required bei einem Feld anhakt.
API Zugriff auf require if[Bearbeiten]
$inputfield->required = 1; // must be set $inputfield->requiredIf = "field=value";
Selectors[Bearbeiten]
Selector string format
field=value
"field" is the name of the field you want to check, "=" is the operator you want to use for comparison, and "value" is the value you want to compare.
- multiple conditions by separating each field=value condition with a comma, i.e.
fullname!=, items>5
Allowed operators
= equal != not equal > greater than < less than >= greater than or equal <= less than or equal %= contains phrase *= contains phrase (same as above)
Beispiele:
categories.count>0, categories.count<3 // one or two categories selected categories.count=0 // no categorie selected first_name!=, last_name= categories=1234, categories.count=1 // Nützlich bei Page Reference checkbox=1 checkbox=0
Limitations[Bearbeiten]
OR geht nur im Selektor:
Populate Multiple Select Field depending on Single Select Field[Bearbeiten]
Ungetestet aus: https://processwire.com/talk/topic/17960-dependent-selects/
var initChildSelect = function() {
// THE "PARENT" FIELD
var thisID = $(this).attr('id');
var repeaterID = thisID.split('_repeater')[1]; // if in repeater?
var optID = parseInt($(this).val()); // the selected option
// THE "CHILD/DEPENDENT" FIELD
childWorksSelect = $('select[name^="part_select_repeater'+repeaterID+'"]');
var allOptions = $(childWorksSelect.children()).clone();
var validOptions = allOptions.filter(function(){
return $(this).data('parent') == optID;
});
childWorksSelect.html(validOptions);
var options = {};
if(!optID) {
var options = {'placeholder': 'No Work Selected'}
}
if(optID && !validOptions.length) {
var options = {'placeholder': 'No Parts For The Selected Work'}
}
childWorksSelect.selectize(options);
// DEAL WITH CHANGES TO THE PARENT FIELD
$(this).change(function() {
var optID = parseInt($(this).val());
var newOptions = allOptions.filter(function(){
return $(this).data('parent') == optID;
});
childWorksSelect[0].selectize.destroy();
// Re-init the select
childWorksSelect = $('select[name^="part_select_repeater'+repeaterID+'"]');
childWorksSelect.html(newOptions);
var options = {};
if(!optID) {
var options = {'placeholder': 'No Work Selected'}
}
if(optID && !newOptions.length) {
var options = {'placeholder': 'No Parts For The Selected Work'}
}
childWorksSelect.selectize(options);
childWorksSelect[0].selectize.open();
});
}
$(function(){
$('select[name^="work_select_single"]').each(initChildSelect);
$(document).on('reloaded opened repeateradd wiretabclick', '.InputfieldPage', function() {
$(this).find('select[name^="work_select_single"]').each(initChildSelect);
});
});
function initInputfieldPage($this) {
$this.find("p.InputfieldPageAddButton a").click(function() {
var $input = $(this).parent('p').next('.InputfieldPageAddItems');
if($input.is(":visible")) $input.slideUp('fast').find(":input").val('');
else $input.slideDown('fast').parents('.ui-widget-content').slice(0,1).effect('highlight', {}, 500)
return false;
});
// support for dependent selects
$this.find(".findPagesSelector").each(function() {
var $repeater = $this.parents('.InputfieldRepeaterItem');
var $t = $(this);
var selector = $t.val();
// if there is no "=page." present in the selector, then this can't be a dependent select
if(selector.indexOf('=page.') == -1) return;
var labelFieldName = $t.attr('data-label');
var formatName = $t.attr('data-formatname');
if(!labelFieldName.length) $labelFieldName = 'name';
// if it doesn't contain a dynamic request from the page, then stop now
var $wrap = $t.parents(".InputfieldPage");
var $select = $('select#' + $wrap.attr('id').replace(/^wrap_/, ''));
if($select.length < 1) return;
var parts = selector.match(/(=page.[_a-zA-Z0-9]+)/g);
for(var n = 0; n < parts.length; n++) {
var part = parts[n];
var name = part.replace('=page.', '');
var $inputfield = $repeater.length === 0 ? $('#Inputfield_' + name) : $('#Inputfield_' + name + "_repeater" + $repeater.data('page'));
if($inputfield.length < 1) return;
// monitor changes to the dependency field
$inputfield.off('change');
$inputfield.on('change', function() {
var s = selector;
var v = $inputfield.val();
if(v == null) {
// no values selected
$select.children().remove();
$select.change();
return;
}
v = v.toString();
v = v.replace(/,/g, '|'); // if multi-value field, convert commas to pipes
s = s.replace(part, '=' + v);
s = s.replace(/,\s*/g, '&');
if(s.indexOf('_LPID')) s = s.replace(/_LPID[0-9]+/g, '');
var url = ProcessWire.config.urls.admin + 'page/search/for?' + s + '&limit=999&get=' + labelFieldName;
if(formatName.length) url += '&format_name=' + formatName;
$.getJSON(url, {}, function(data) {
//$select.children().remove();
$select.children().addClass('option-tbd'); // mark existing options as to-be-deleted
for(n = 0; n < data.matches.length; n++) {
var page = data.matches[n];
// first see if we can find the existing option already present
var $option = $select.children("[value=" + page.id + "]");
// if that option isn't already there, then make a new one
var selected = false;
if($option.size() > 0) selected = $option.is(":checked");
$option.remove();
var label = '';
if(formatName.length) label = page[formatName];
if(!label.length) label = page[labelFieldName];
if(!label.length) label = page.name;
var $option = $("<option value='" + page.id + "'>" + label + "</option>");
if(selected) $option.attr('selected', 'selected');
// add the <option> to the <select>
$select.append($option);
}
$blankOption = $("<option value=''></option>");
$select.prepend($blankOption);
$select.children(".option-tbd").remove();
$select.change();
});
});
}
});
}
$(document).ready(function() {
$(".InputfieldPage").each(function() {
initInputfieldPage($(this));
});
$(document).on("reloaded", ".InputfieldPage", function() {
initInputfieldPage($(this));
});
});