0

I'm having an issue using javascript onchange event listener in cakephp3.7. In fact I have a e-commerce web application built with cakephp3.7 running fine. Now I want to enhance the sales submission form in the website, by dynamically loading extra fields that sellers fill based on the category of products the seller chooses. That means, if the sellers chooses electronic from the category input field, then the electronic exta fields that were previously of style display:none in the CSS, will now be displayed. The electronic extra fields are as follow with id=elctronic:

<div id="electronic">
<?php echo $this->Form->control('subcategorie',['label'=>'choose sub category', 'class'=>'form-control', 'option'=>['Computer','Phone','Multimedia'],'empty'=>'choose'); ?>
<?php echo $this->Form->control('brand',['class'=>'form-control', 'placeholder'=>'the brand']); ?>
<?php echo $this->Form->control('model',['class'=>'form-control', 'placeholder'=>'the model']); ?>
</div>

Then if the product is about clothes for exemple, the electronic input fields will be hidden and the clothes extra fields will be displayed with id=clothe as bellow:

   <div id="clothe">
    <?php echo $this->Form->control('Gender',['label'=>'What gender?', 'class'=>'form-control', 'option'=>['Males','Females'],'empty'=>'choose'); ?>
    <?php echo $this->Form->control('Size',['class'=>'form-control', 'placeholder'=>'Size']); ?>
    <?php echo $this->Form->control('model',['class'=>'form-control', 'placeholder'=>'the model']); ?>
    </div>

The category input field where the onchange event listener is used is as bellow, and the javascript function extraForm() should get called, but it doesn't and there is the issue:

<?php echo $this->Form->control('category',['id'=>'categ','label'=>'choose category', 'class'=>'form-control', 'options'=>['electronics','clothes'],'empty'=>'choose'),'onchange'=>'extraForm("categ"); ?>

And then in the layout for the method add() of ProductsController, I set the extraForm() function as below:

<script>
function extraForm(s1){
 var s1=documentgetElementById(s1);
 var s2=documentgetElementById("electronics");
 var s3=documentgetElementById("clothes");
  if(s1.value == "electronics"){
    s2.style.display = "bloc"
} else {
    s3.style.display = "bloc"
}
}
</script>

It's three days now since I can't figure out what I'm missing. Yesterday I searched through the net and there were people saying that event listener such as onchange, onclick and onselect event listeners are deprecated for cakephp 3 and I don't understand how. So how to achieve the dynamic load of extra input form triggered by selected option in cakephp3.7.

**

  • FIRST EDIT

**

Like I said in the comments, I simplified the question to make it understandable. The full context is that I have 2 standarts fields category and subcategory. When the user select a category, an AJAX fonction presentes to the user a list of subcategories to choose from. My AJAX is:

$(document).ready(function(){

$('#getSubCat').change(function(e){

    $.ajax({
        type: "POST",
        url:  "/products/getsubsaterogie",
        data: {categ: $(this).find('option:selected').text()},
        dataType: 'json',
        cache: false,
        headers : {
            'X-CSRF-Token': $('[name="_csrfToken"]').val()
        },
        success: function(data){
            console.log(data);
            let subcat = $('#subcategories')

            for (let sc of data) {
                console.log(sc.subcategorie)
                $('<option />', {value: sc.subcategorie_id, text: sc.subcategorie}).appendTo(subcat);
            }
        }
    });

    e.preventDefault();
})

}) The categorie input field is:

  <?php echo $this->Form->control('categorie_id', ['id'=>'getSubCat', 'options' => $categories, 'label' => __("What category ?"), 'class'=>'form-control', 'empty' => '(choose)']); 
                                               ?>

After the user choose a category the list of subcategory fetched from database by AJAX appears well in this form input, and this is where the onchange is set to call the extraForm() function, but does not:

 <?php echo $this->Form->control('subcategorie_id', ['id'=>'subcategories', 'label' => __("What subcategory ?"), 'class'=>'form-control', 'options'=> [],'empty' => '', 'onchange' => 'myFormShow("getSubCat","subcategories")']); 
                                               ?>

And After subcategory selected, the relevant extra form doesn't appear, but if I manually change display to bloc in CSS, it does show, which means that the javascript function isn't called onchange event, I even used onselect but still not having it. And the javascript function extraForm is actually receiving 2 arguments like extraForm(s1, s2). This is my real context.

I'm really stuck here. Any help is really appreciated, thanks in advance.

- EDIT ACCORDING TO GREG'S REQUEST: According to Greg's comment this is my cake code to generate the list inside subcategory. I didn't know all these details were necessary since I thought it was cakephp 3 issues regarding javascript events listeners.

public function getsubsaterogie(){
            if($this->request->is('ajax')){
                $d = $this->request->getData();
                $subcat = '';
                $cat = TableRegistry::get('Categories')->find()
                ->where(['categorie' => $d['categ']])
                ->select('id')
                ->first();

                if(!empty($cat)){
                    $subcat = TableRegistry::get('Subcategories')->find()
                    ->where(['categorie_id' => $cat->id])
                    ->all();
                }

                echo json_encode($subcat);
                exit();
            }
        }

Thanks in advance, best regards !

Himmels DJ
  • 395
  • 5
  • 20
  • In your code, `Form->control('category',['id'=>'categ','label'=>'choose category', 'class'=>'form-control', 'option'=>['electronics','clothes'],'empty'=>'choose'),'onchange'=>'extraForm("categ"); ?>`, there are multiple syntax errors. If this is the actual code, then is the problem a PHP error? If so, those should be easily fixed. If not, then please update the question with exactly the code you're using, so that we're all on the same page. – Greg Schmidt Apr 12 '20 at 16:03
  • @Greg Schmidt, this my actual code, what's wrong please, I want to know. – Himmels DJ Apr 12 '20 at 17:57
  • But the 'option' => ['electronics', 'clothes'] in the part you highlight is not actually what i have because those 'electronics' and 'clothes' are actually data fetch from database. The options are are showing in the form view, but after the user select an option the onchange doesn't call the extraForm() function. I made this this way so you understand what i need. – Himmels DJ Apr 12 '20 at 18:07
  • You're right @Greg Schmidth it's important to be on the same page, that snipet you highlighted is actually like so. There is a field for the user to choose category, it's like this: Form->control('categorie_id', ['id'=>'categories', 'label' => __("Choose the category ?"), 'class'=>'form-control', 'options'=> [],'empty' => '', 'onchange' => 'extraForm("categories")']); ?> – Himmels DJ Apr 12 '20 at 18:13
  • After the user select a category, a list of subcatories fetched from database with an AJAX code is presented to him. The AJAX is as bellow: $(document).ready(function(){ $('#getSubCat').change(function(e){ $.ajax({ type: "GET", url: "annonces/getsubsaterogie", data: {categ: $(this).find('option:selected').text()}, //dataType: 'json', cache: false, success: function(data){ console.log(data); } }); e.preventDefault(); }) }) – Himmels DJ Apr 12 '20 at 18:30
  • And after subcategory selected, normally the onchange event should be called when, and that part is actually: Form->control('subcategorie_id', ['id'=>'subcategories', 'label' => __("What subcategory ?"), 'class'=>'form-control', 'options'=> [],'empty' => '', 'onchange' => extraForm("getSubCat","subcategories")']); ?> – Himmels DJ Apr 12 '20 at 18:35
  • then I give the javascript 2 arguments extraForm(s1, s2). Also the ' id' in category field is 'id' => 'getSubCat' and not 'id' => 'categories'. This is the full context, I simplified just to make it understandable. – Himmels DJ Apr 12 '20 at 18:39
  • Your initial code (for the "category" input) cannot possibly run. You've got an unmatched `[`, an extra `)` after `'empty'=>`choose', no closing quote around `extraForm("categ");`, and no closing `)` at the end. So that can't possibly be running, and thus the specific problem isn't clear from that bit. Could be different things, depending on exactly what you changed in transcribing this. That's why it's important to copy-and-paste exact code. – Greg Schmidt Apr 12 '20 at 22:33
  • With the additional code posted, your `change` function for `#getSubCat` isn't doing anything with the data returned from the Ajax call. Again, without knowing exactly what that's really doing, it's hard to guess at what might be going wrong. With the code as shown, it seems like the subcategory would not have any options in it, and thus the `change` handler couldn't ever be triggered at all? – Greg Schmidt Apr 12 '20 at 22:39
  • @GregSchmidt, I have the "getsubsaterogie" method in the controller that handles that with an "if($this->request->is('ajax')){}", so the subcategories are well displayed. The issue is not about the getting the data, it's about whether cakephp3 support the "onchange, onclick or onselect" events listeners, and if so how can I do that? As for the data, I get all subcategories as soon as category is selected. Now when I select a subcategory, some extra fields with the specific selected subcategories' properties should be displayed. Tha's my issue – Himmels DJ Apr 13 '20 at 16:23
  • "Cake" doesn't support any of those things. Cake is a server-side technology. It generates JavaScript code that will run on the browser, so as long as what you are generating is valid JS, then that's fine. – Greg Schmidt Apr 13 '20 at 20:16
  • Since you haven't shown us the Cake code that generates your subcategories or your JS code that puts that result into your HTML, it's still very hard to say where the problem lies. If you're replacing the entire `select` input, for example, then no surprise that the event previously attached to it isn't working. – Greg Schmidt Apr 13 '20 at 20:17
  • What you've provided, in other words, are bits of code, but not a [minimal complete reproducible example](https://stackoverflow.com/help/minimal-reproducible-example). – Greg Schmidt Apr 13 '20 at 20:18
  • Hi Greg, I edited and added the cake code to generate the list inside subcategories, thanks in advance. – Himmels DJ Apr 14 '20 at 15:26
  • @GregSchmidt, you were right on 2 points, the previous ajax code was not the one inside the js folder, it was my sample forgotten inside webroot, since I worked on that ajax part 6 months ago, now I edited the ajax code with the right one in the question. Secondly, i tried to use the onclick, onchange and onselect events in one of this same project' view file and the onchange worked, but in plain HTML without cakephp's FormHelper. It seem to me that it's the Cakephp's FormHelper bringing the issue in my case, i'm not sure, just an assumption. I keep searching how to do that with the FormHelper – Himmels DJ Apr 16 '20 at 16:24
  • If you now have HTML and JS that is together working how you want, and can't get the Cake FormHelper to generate equivalent HTML, then my suggestion would be to heavily edit your question, removing everything that's unrelated to just this, and including the now working and not-working code. That will very much refocus the question and help you to get to a useful answer. – Greg Schmidt Apr 16 '20 at 18:39
  • Ok Greg, I will try to check what I'm missing by testing every single part separately, then may be I will open a new question about the real issue if solution still not found. Thanks – Himmels DJ Apr 16 '20 at 19:07

1 Answers1

0

It's always very daunting not knowing what the real problem is, since this is not my first foray in using ajax along with cakephp. I can attest on Greg Schmidth great experience when he said "the subcategories won't display at all". In fact, 2 days later and when endeavouring to hunt down the real issue,

  • I emptied cache,
  • I removed browser cookies

And suddenly the whole app started behaving unexpectedly,

  • The subcategories were not displaying any more

  • The jQuery based animations codes I made for animating advertisements on the website frontend were also getting weird.

These all made me think of jQuery issue, and indeed it was the real issue. I'm using 3 differents versions of jQuery and all 3 versions are necessary for my projects. The 3 jquery versions were silently conflicting and were not giving me any clue to troubleshoot what was going wrong. Now that I know it's a jquery issue, I used the jQuery noConflict approach described in this link

 <?= $this->Html- >script('http://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js') ?>
    <?= $this->Html->script('lecker/ajax/getSubCategorie.js') ?>
    <script>
        var jQuery_1_12 = $.noConflict(true);
    </script>
<?= $this->Html->script('https://code.jquery.com/ui/1.12.1/jquery-ui.js') ?>
// This for the second jquery version

The description was not as straightforward as it seemed but other questions on stackoverflow also contributed to help me.

Ultimately, It's not an issue about whether we can still use enchange event with cakephp version 3 form helper, but rather an issue about the right $ variable used by jquery in ajax code to get subcategories, it was not yielding.

Himmels DJ
  • 395
  • 5
  • 20