Search code examples
javascriptmeteorcheckboxradio-buttonmeteor-blaze

Meteor enable/disable checkbox with radio, show/hide with checkbox


In a table I have a list of users,and some options that I can selecte for them.

||USER          ||      OPTIONs  ||
||User1         ||  Opt1 || Opt2 ||
||User2         ||  Opt1 || Opt2 ||

The users are displayed as radio button, the options are checkboxes of info about the user that I want to display(both/just one at time).

1 I want to disable the selection of the options if you didn't select the user before them. After the user is selected you can select the options you want

2 I need to change something in the code becose if now I select the user 1 and the option 1, and then I select the user 2 I can see the info for the option 1 of user 2 without clicking on the option 1 check box.

This is my code:

HTML

<template name="patients">
  <table>
     <tr>
        <th>Patient</th>
        <th>Options</th>
     </tr>
  </table>
  {{#each Users}}
  <table>
     <tr>
       <th>
          <label><input type="radio" class="selected" name="patient" value="{{this._id}}">{{this.profile.lastName}} {{this.profile.firstName}}</label>
       </th>
       <td>
         <div class="patinf">
           <label><input type="checkbox" class="infos" name="{{this._id}}"  id="showInfos"><span>OPT1</span></label>
           <label><input type="checkbox" class="answers" name="{{this._id}}" id="showAnswers"><span>OPT2</i></span></label>
        </div>
      </td>
    </tr>
  </table>
  {{/each}}
  {{>display}}
</template>


<template name="display">
  {{#if isInfosClicked}}
      <div name="showInfos">
        <h4>Infos for {{data.profile.lastName}} {{data.profile.firstName}}</h4>

      </div>
  {{/if}}
  {{#if isAnswersClicked}}
    <div name="showAnswers">
        <h4>Answers for {{data.profile.lastName}} {{data.profile.firstName}}</h4>
    </div>
  {{/if}}
</template>

This is my JS

     Template.patients.helpers({
        Users: function() {
            return Meteor.users.find({});
        },
     });

     Template.patients.events({
        'click .selected': function (){
        var selPat = $('input[name="patient"]:checked').val();
        Session.set("selPat",selPat);
        }
     });


     Template.patients.events({
        'click .infos': function(){
          Session.set("infosClicked", true);
         },
        'click .answers': function(){
          Session.set("answersClicked", true);
         },        
     });

     Template.display.helpers({
        isInfosClicked: function(){
            return Session.get("infosClicked");
        },
        isAnswersClicked: function(){
            return Session.get("answersClicked");
        },
        data: function(){
            var PAT= Meteor.users.findOne({ _id: Session.get("selPat")});
            return PAT;
       }
     });

Solution

  • The code bellow should put you on the track to where you want to get.

    JS:

    Template.patients.helpers({
     Users: function() { // I used the fake Users collection
            return Meteor.users.find({}).fetch();
        },
        isChecked: function(){ // disable the checkboxes if not choosen
            return !(Session.get("selPat") === this._id);
        }
    });
    
    Template.patients.events({
        'click .selected': function (e){
            var selPat = $('input[name="patient"]:checked').val();
            if(selPat !== Session.get("selPat")){ 
                // if a different user is choosen, 
                // clear the checkboxes and the Sessions
                Session.set("infosClicked", false);
                Session.set("answersClicked", false);
                $(`input[type="checkbox"]`).prop('checked', false);
            }
            Session.set("selPat",selPat);
        },
        'click .infos': function(){
            Session.set("infosClicked", !Session.get("infosClicked"));
         },
        'click .answers': function(){
            Session.set("answersClicked", !Session.get("answersClicked"));
         },        
    });
    
    
    Template.display.helpers({
        isInfosClicked: function(){
            return Session.get("infosClicked");
        },
        isAnswersClicked: function(){
            return Session.get("answersClicked");
        },
        data: function(){ // I used the fake Users collection
            var PAT= Meteor.users.findOne({ _id: Session.get("selPat")});
            return PAT;
       }
    });
    

    In the html the main difference is adding disabled attr with helper logic. Other than that I formed it in a table as you showed.

    HTML:

    <template name="patients">
        <table>
           <tr>
              <th>Patient</th>
              <th colspan="2">Options</th>
           </tr>
    
            {{#each Users}}
            <tr>
                <td>
                    <label><input type="radio" class="selected" name="patient" value="{{this._id}}">{{this.profile.lastName}} {{this.profile.firstName}}</label>
                </td>
                <td>
                    <div class="patinf">
                        <label><input type="checkbox" class="infos" name="{{this._id}}" id="showInfos" disabled="{{isChecked}}"><span>OPT1</span></label>
                    </div>
                </td>
                <td>
                    <div class="patinf">
                        <label><input type="checkbox" class="answers" name="{{this._id}}" id="showAnswers" disabled="{{isChecked}}"><span>OPT2</span></label>
                    </div>
                </td>
            </tr>
          {{/each}}
        </table>
        {{>display}}
    </template>
    
    
    <template name="display">
        {{#if isInfosClicked}}
            <div name="showInfos">
              <h4>Infos for {{data.profile.lastName}} {{data.profile.firstName}}</h4>
    
            </div>
        {{/if}}
        {{#if isAnswersClicked}}
          <div name="showAnswers">
              <h4>Answers for {{data.profile.lastName}} {{data.profile.firstName}}</h4>
          </div>
        {{/if}}
    </template>
    

    After making it to work with this, I would suggest you take a look at ReactiveVar, it is a more recommended solution for the template level variables, and you can combine it with template data context than you have more control on your data and the template state.