5use Ajax\php\ubiquity\utils\DataFormHelper;
6use Ajax\semantic\html\collections\form\HtmlFormCheckbox;
7use Ajax\semantic\html\collections\form\HtmlFormField;
8use Ajax\semantic\html\collections\form\HtmlFormInput;
9use Ajax\semantic\html\elements\HtmlButton;
10use Ajax\semantic\html\elements\HtmlIconGroups;
11use Ajax\semantic\widgets\dataform\DataForm;
12use Ajax\semantic\widgets\datatable\DataTable;
13use Ajax\service\JArray;
35 foreach ($relations as $field => $member) {
36 if (\array_search($field, $fields) !==
false) {
37 unset($fieldTypes[$field]);
38 if (OrmUtils::getAnnotationInfoMember($className,
'#manyToOne', $member) !==
false) {
40 } elseif (($annot = OrmUtils::getAnnotationInfoMember($className,
'#oneToMany', $member)) !==
false) {
41 $fkClass = $annot[
'className'];
42 if (OrmUtils::isManyToMany($fkClass)) {
47 } elseif (($annot = OrmUtils::getAnnotationInfoMember($className,
'#manyToMany', $member)) !==
false) {
55 $joinColumn = OrmUtils::getAnnotationInfoMember($className,
'#joinColumn', $member);
57 $fkObject = Reflexion::getMemberValue($instance, $member);
58 $fkClass = $joinColumn [
'className'];
59 if ($fkObject ===
null) {
60 $fkObject =
new $fkClass ();
62 $fkId = OrmUtils::getFirstKey($fkClass);
64 $fkIdGetter =
'get' . \ucfirst($fkId);
65 if (\method_exists($fkObject,
'__toString') && \method_exists($fkObject, $fkIdGetter)) {
66 $fkField = $joinColumn [
'name'];
67 $fkValue = OrmUtils::getFirstKeyValue($fkObject);
68 if (!Reflexion::setMemberValue($instance, $fkField, $fkValue)) {
69 $instance->{$fkField} = OrmUtils::getFirstKeyValue($fkObject);
72 if (OrmUtils::isNullable($className, $member)) {
73 $attr = [
'jsCallback' =>
function ($elm) {
74 $elm->getField()->setClearable(
true);
77 $attr = [
'jsCallback' =>
function ($elm) {
78 $elm->addRules([
'empty']);
81 $form->fieldAsDropDown($fkField, JArray::modelArray($this->controller->_getAdminData()->getManyToOneDatas($fkClass, $instance, $member), $fkIdGetter,
'__toString'),
false, $attr);
82 $form->setCaption($fkField, \ucfirst($member));
88 $newField = $member .
'Ids';
89 $fkClass = $annot [
'className'];
90 $fkId = OrmUtils::getFirstKey($fkClass);
91 $fkIdGetter =
'get' . \ucfirst($fkId);
92 $fkInstances = Reflexion::getMemberValue($instance, $member);
93 $ids = \array_map(
function ($elm) use ($fkIdGetter) {
94 return $elm->{$fkIdGetter} ();
96 $instance->{$newField} = \implode(
",", $ids);
97 $form->fieldAsDropDown($newField, JArray::modelArray($this->controller->_getAdminData()->getOneToManyDatas($fkClass, $instance, $member), $fkIdGetter,
"__toString"),
true);
98 $form->setCaption($newField, \ucfirst($member));
102 $newField = $member .
'Ids';
103 $fkClass = $annot [
'className'];
104 $fkv = OrmUtils::getFirstKeyValue($instance);
106 $fkInstances = DAO::getOneToMany($instance, $member);
108 $fields = OrmUtils::getManyToManyFieldsDt(\get_class($instance), $fkClass);
109 $fkInstances[] =
new $fkClass();
110 $relFields = OrmUtils::getFieldsInRelations_($fkClass);
111 $form->fieldAsDataTable($newField, $fkClass, $fkInstances, $fields, [
'jsCallback' =>
function (DataTable $dt) use ($fkClass, $relFields, $fields, $newField) {
112 $this->dtManyField($dt, $fkClass, $relFields, $fields);
113 $id = $dt->getIdentifier();
114 $removeSelected =
'function updateCmb(){let cmb=$("#' . $id .
' tbody tr:last-child div.dropdown");cmb.find("a[data-value]").removeClass("disabled");$("#' . $id .
' tbody tr div.dropdown input").each(function(){if($(this).val()) cmb.find("[data-value="+$(this).val()+"]").addClass("disabled");});}';
115 $this->jquery->execAtLast($removeSelected .
'updateCmb();$("#' . $id .
' tbody tr:last-child .dropdown").removeClass("disabled");$("#' . $id .
' tbody tr:last-child").find("input._status").val("added");');
116 $deleteJS = $this->jquery->execJSFromFile(
'@framework/js/delete', [],
false);
117 $this->jquery->click(
'._delete',
'$("[name=' . $newField .
']").val("updated");' . $deleteJS,
true,
false,
false,
"#$id");
118 $this->jquery->change(
'tr:last-child input', $this->jquery->execJSFromFile(
'@framework/js/change', compact(
'id'),
false),
false,
false,
"#$id");
119 $this->jquery->change(
'tr .dropdown input',
'updateCmb();',
false,
false,
"#$id");
120 $this->jquery->change(
'tr input',
'$("[name=' . $newField .
']").val("updated");if($(this).closest("tr").find("input._status").val()!=="added"){$(this).closest("tr").find("input._status").val("updated");}',
false,
false,
"#$id");
123 $form->setCaption($newField, \ucfirst($member));
126 protected function dtManyField(DataTable $dt, $className, array $relations, array $fields) {
127 foreach ($relations as $field => $member) {
128 if (\array_search($field, $fields) !==
false) {
129 if (OrmUtils::getAnnotationInfoMember($className,
"#manyToOne", $member) !==
false) {
130 $this->dtManyFieldCmb($dt, $member, $className);
137 $joinColumn = OrmUtils::getAnnotationInfoMember($className,
"#joinColumn", $member);
139 $fkClass = $joinColumn [
'className'];
140 $fkId = OrmUtils::getFirstKey($fkClass);
142 $fkIdGetter =
'get' . \ucfirst($fkId);
143 $fkField = $joinColumn [
'name'];
146 if (OrmUtils::isNullable($className, $member)) {
147 $attr = [
'jsCallback' =>
function ($elm) {
148 $f = $elm->getField();
149 $f->setClearable(
true);
150 $f->addClass(
'disabled');
153 $attr = [
'jsCallback' =>
function ($elm) {
154 $elm->getField()->addClass(
'disabled');
157 $dt->fieldAsDropDown($fkField, JArray::modelArray($this->controller->_getAdminData()->getManyToOneDatas($fkClass,
null, $member), $fkIdGetter,
'__toString'),
false, $attr);
162 $newField = $member .
'Ids';
163 $fkClass = $annot [
'targetEntity'];
164 $fkId = OrmUtils::getFirstKey($fkClass);
165 $fkIdGetter =
'get' . \ucfirst($fkId);
166 $fkInstances = Reflexion::getMemberValue($instance, $member);
167 $ids = \array_map(
function ($elm) use ($fkIdGetter) {
168 return $elm->{$fkIdGetter} ();
170 $instance->{$newField} = \implode(
',', $ids);
171 $form->fieldAsDropDown($newField, JArray::modelArray($this->controller->_getAdminData()->getManyToManyDatas($fkClass, $instance, $member), $fkIdGetter,
'__toString'),
true, [
'jsCallback' => function ($elm) {
172 $elm->getField()->asSearch();
174 $form->setCaption($newField, \ucfirst($member));
182 return $this->defaultEditMemberParams();
191 $params = $this->getEditMemberParams();
192 if ($params && isset ($params [$part])) {
193 return $params [$part];
202 return [
'dataTable' => EditMemberParams::dataTable(
'#' . $this->getDataTableId()),
'dataElement' => EditMemberParams::dataElement()];
213 public function getForm($identifier, $instance, $updateUrl =
'updateModel') {
214 $hasMessage = $this->formHasMessage();
215 $form = $this->jquery->semantic()->dataForm($identifier, $instance);
216 $form->setLibraryId(
'frmEdit');
217 $className = \get_class($instance);
218 $fields = \array_unique($this->controller->_getAdminData()->getFormFieldNames($className, $instance));
219 $relFields = OrmUtils::getFieldsInRelations_($className);
221 $this->setFormFields_($fields, $relFields);
223 \array_unshift($fields,
'_message');
225 $form->setFields($fields);
226 $fieldTypes = OrmUtils::getFieldTypes($className);
227 $attrs = ValidatorsManager::getUIConstraints($instance);
229 $this->relationMembersInForm($form, $instance, $className, $fields, $relFields, $fieldTypes);
230 OrmUtils::setFieldToMemberNames($fields, $relFields);
231 $form->setCaptions($this->getFormCaptions($fields, $className, $instance));
233 $message = $this->getFormTitle($form, $instance);
234 $form->setCaption(
'_message', $message [
'subMessage']);
235 $form->fieldAsMessage(
'_message', [
'icon' => $message [
'icon']]);
236 $instance->_message = $message [
'message'];
239 $this->setFormFieldsComponent($form, $fieldTypes, $attrs);
240 $form->setSubmitParams($this->controller->_getBaseRoute() .
'/' . $updateUrl,
'#frm-add-update');
241 $form->onGenerateField([$this,
'onGenerateFormField']);
256 public function getMemberForm($identifier, $instance, $member, $td, $part, $updateUrl =
'_updateMember') {
257 $editMemberParams = $this->getEditMemberParams_($part);
259 $form = $this->jquery->semantic()->dataForm($identifier, $instance);
260 $form->on(
"dblclick",
"",
true,
true);
261 $form->setProperty(
"onsubmit",
"return false;");
262 $form->setProperty(
'style',
'margin:0;');
263 $form->addClass(
"_memberForm");
264 $className = \get_class($instance);
265 $fields = [
"id", $member];
266 $relFields = OrmUtils::getFieldsInRelations_($className);
267 $hasRelations = $this->setFormFields_($fields, $relFields);
268 $form->setFields($fields);
269 $fieldTypes = OrmUtils::getFieldTypes($className);
270 $form->fieldAsHidden(0);
271 $attrs = ValidatorsManager::getUIConstraints($instance);
272 $this->setMemberFormFieldsComponent($form, $fieldTypes, $attrs);
274 $this->relationMembersInForm($form, $instance, $className, $fields, $relFields, $fieldTypes);
276 $form->setCaptions([
"",
""]);
277 $form->onGenerateField(
function (HtmlFormField $f, $nb) use ($identifier, $editMemberParams) {
280 if ($editMemberParams->getHasButtons()) {
281 $btO = HtmlButton::icon(
"btO",
"check")->addClass(
"green mini compact")->onClick(
"\$('#" . $identifier .
"').trigger('validate');", true, true);
282 $btC = HtmlButton::icon(
"btC",
"close")->addClass(
"mini compact")->onClick(
"\$('#" . $identifier .
"').trigger('endEdit');");
283 $f->wrap(
"<div class='inline fields' style='margin:0;'>", [$btO, $btC,
"</div>"]);
284 if (!$editMemberParams->getHasPopup()) {
285 if (!($f instanceof HtmlFormCheckbox)) {
286 $f->setWidth(16)->setProperty(
"style",
"padding-left:0;");
290 $f->on(
"keydown",
"if(event.keyCode===27) {\$('#" . $identifier .
"').trigger('endEdit');}");
291 $f->onClick(
"return false;",
true,
true);
293 $f->setProperty(
"style",
"display: none;");
296 $form->setSubmitParams($this->controller->_getBaseRoute() .
"/$updateUrl/" . $member .
"/" . $editMemberParams->getUpdateCallback(),
"#" . $td, [
"attr" =>
"",
"hasLoader" =>
false,
"jsCallback" =>
"$(self).remove();",
"jqueryDone" =>
"html"]);
297 if ($editMemberParams->getHasPopup()) {
298 $endEdit =
"\$('#" . $identifier .
"').html();\$('.popup').hide();\$('#" . $td .
"').popup('destroy');";
299 $validate = $endEdit;
301 $endEdit =
"let td=\$('#" . $td .
"');td.html(td.data('originalText'));";
304 $form->on(
"endEdit", $endEdit);
305 $form->on(
"validate",
"\$('#" . $identifier .
"').form('submit');" . $validate);
306 $this->jquery->execAtLast(
"$('form').find('input[type=text],textarea,select').filter(':visible:first').focus();");
311 $hasRelations =
false;
312 $relFields = \array_flip($relFields);
313 foreach ($fields as $index => $field) {
314 if (isset ($relFields [$field])) {
315 $fields [$index] = $relFields [$field];
316 $hasRelations =
true;
319 return $hasRelations;
330 $type = ($instance->_new) ?
'new' :
'edit';
331 $messageInfos = [
'new' => [
'icon' => HtmlIconGroups::corner(
'table ' . $this->style,
'plus ' . $this->style,
'big'),
'subMessage' =>
' New object creation'],
'edit' => [
'icon' => HtmlIconGroups::corner(
'table ' . $this->style,
'edit ' . $this->style,
'big'),
'subMessage' =>
' Editing an existing object']];
332 $message = $messageInfos [$type];
333 $message [
'message'] =
' ' . \get_class($instance);
345 DataFormHelper::addDefaultUIConstraints($form, $fieldTypes, $attributes);
356 DataFormHelper::addDefaultUIConstraints($form, $fieldTypes, $attributes);
365 if ($field instanceof HtmlFormInput) {
366 if ($field->getDataField()->getProperty(
'type') ==
"datetime-local") {
367 $v = $field->getDataField()->getProperty(
'value');
369 $field->getDataField()->setValue(date(
"Y-m-d\TH:i:s", \strtotime($v)));
384 return \count($objects) > 5;
394 return \array_map(
'ucfirst', $captions);
403 return \get_class($instance);
420 $btOkay->setValue(
"Validate modifications");
For using in a CRUDController ModelViewer with getEditMemberParams method.
Gateway class between database and object model.
Object/relational mapping utilities.
Reflection utilities in dev environment only.