"Edit Mode" button

  • 7
  • Idea
  • Updated 9 months ago
  • Implemented
I'd like a button on any field editors, tables, or headers/titles that allows the user to put the section into full edit mode. I like my pages to default to read mode, but the user should be able to put the page into edit mode when they want to, similar to standard SF UI.
Photo of Peter Bender

Peter Bender, Champion

  • 6,296 Points 5k badge 2x thumb

Posted 6 years ago

  • 7
Photo of Chris

Chris

  • 1,632 Points 1k badge 2x thumb
Dave - those classes (btnEdit and btnCancel) are only needed to identify the buttons. No CSS is needed for it to function, though you are welcome to put some style CSS on them if you want to make your buttons have some style.  Only btnHide needs actual CSS (to hide them).  The code uses btnEdit/btnCancel to understand the button that was clicked, and to flip btnHide between them (so you see either Edit or Cancel, but not both). 

Hope this helps...
Photo of Dave

Dave

  • 5,690 Points 5k badge 2x thumb
Ok thank you very much Chris,

But I must be doing something wrong then.

When i click the edit button, it does change all fields to edit mode(on the tab I'm on only), but the cancel button does not appear no matter what I do,

The snippet (named EditAll)is the exact copy from here so that is not the issue. the only thing possible then is my buttons. So here's a short description of how i have them set up

1- Edit button: Action type Run Skuid Snippet named EditAll . That button has a class named: btnEdit

2- Cancel button, i tried making it run skuid snippet EditAll, I tried a cancel action, tried no action ...
With classes: btnEditCancel btnHide (never used multiple classes, so separated by a space?)

button 1 works fine to edit and save

button 2 never appears


Thx in Advance
Photo of Chris

Chris

  • 1,632 Points 1k badge 2x thumb
When you click Edit (and the fields change), does the Edit button disappear?  Or does it stay on the page?

In looking at the code (it's been a while since I've done that!) I see the line:

$('#btnCancelEdit').removeClass('btnHide');

This indicates that the Cancel button must have the ID "btnCancelEdit" on it.  Can you verify that yours has that ID?  If not, that could cause this problem.  Sorry that that wasn't in the original description - didn't catch that one!
Photo of Dave

Dave

  • 5,690 Points 5k badge 2x thumb
The cancel button would appear at all in all scenarios

But you found the issue, I did not know about adding the ID, that fixed it. Thx!



One last question if I may,

My page has multiple tabs and 4-5 different models

Let's say on tab #1 When i click the Edit Button , the fields on that tab always go on edit mode,

then i go to other tabs they are not on edit mode.

Not sure if that is expected behavior, but if not, would there be any way to edit all the fields for all those tabs/models in the same page?

Thx a lot a again!
Photo of Chris

Chris

  • 1,632 Points 1k badge 2x thumb
We have that exact same scenario for one of our pages, and back when I worked on this I wasn't able to find a way to get it to work right.  A lot has changed in Skuid since then so it might be possible now, but I've not tried.  Sorry... 
Photo of Dave

Dave

  • 5,690 Points 5k badge 2x thumb
Nothing to be sorry,

the code and answers provided already is a huge help.

For now I'll simply add it on each tab, it's under consideration by Skuid, so hopefully maybe next major release there will be a native way

Thx for responding :)
(Edited)
Photo of Barry Schnell

Barry Schnell, Champion

  • 18,266 Points 10k badge 2x thumb
Dave/Chris -

The reason the tabs present a problem and don't "change" to edit mode when clicking on them is because the components on them are not yet loaded when you clicked "Edit" button.  This will occur if you are "deferring" loading the contents of the tabs.  When the script looks for components to "flip mode on", it will only find things that are in the DOM.  

To solve for this, you have two options:

1) Do not defer loading of tab contents - This is less than ideal but a possible solution

2) When a tab "loads" you need to run the script against the components in that tab.  You can do this by listening for the "attach" event of a custom component.  Skuid fires an attach event after building the components for the tab and adding them to the tab.  You need to wait for this to occur because the components that you want to flip the mode on must be in the DOM.  In a recent release of Skuid they added "When Tab is First Shown" and "When Tab is Shown" events.  These might be able to be used instead of using a custom component but I haven't looked in to whether or not they fire the required "attach" event or something similar.  We really need "Tab Loading Complete" and "Tab Shown Complete" events :)

Below is a sample page that demonstrates how to accomplish this.  Couple of notes:

1) This page uses the new "UI Only Field" which avoids having to use the btnEdit/btnCancel classes.  Instead of tracking which mode we are in with classes, we use a UI only field checkbox.
2) This page demonstrates how to be more "selective" about which components get their mode flipped.  For example, you might have a field editor that you want to flip to "Edit" but you might have another one that you do not.  If you want a component to "flip" add the class "dynamicmode" to it.  When the flip occurs, it will only flip those with the class "dynamicmode".  The sample has two field editors on each tab, one that flips and one that doesn't.

Hope this helps!

<skuidpage unsavedchangeswarning="yes" personalizationmode="server" showsidebar="true" showheader="true" tabtooverride="Account">   <models>
      <model id="Account" limit="1" query="true" createrowifnonefound="false" sobject="Account">
         <fields>
            <field id="Name"/>
            <field id="CreatedDate"/>
            <field id="Description"/>
         </fields>
         <conditions>
            <condition type="param" enclosevalueinquotes="true" operator="=" field="Id" value="id"/>
         </conditions>
         <actions/>
      </model>
      <model id="ModeTracker" limit="1" query="false" createrowifnonefound="true" adapter="" type="" sobject="Account" doclone="" unloadwarningifunsavedchanges="false">
         <fields>
            <field id="IsEditMode" uionly="true" displaytype="BOOLEAN" defaultValue="false" label="Is Edit Mode"/>
            <field id="Name"/>
            <field id="Description"/>
         </fields>
         <conditions/>
         <actions/>
      </model>
   </models>
   <components>
      <pagetitle model="Account" uniqueid="sk-1_t4jb-68">
         <maintitle>
            <template>{{Name}}</template>
         </maintitle>
         <subtitle>
            <template>{{Model.label}}</template>
         </subtitle>
         <actions>
            <action type="multi" label="Edit" uniqueid="" cssclass="" snippet="updateComponentMode" icon="sk-icon-edit">
               <actions>
                  <action type="updateRow" fieldmodel="ModeTracker" field="IsEditMode" enclosevalueinquotes="false" value="true"/>
                  <action type="custom" snippet="updateComponentMode"/>
               </actions>
            </action>
            <action type="multi" label="Cancel" icon="sk-icon-cancel">
               <actions>
                  <action type="cancel">
                     <models>
                        <model>Account</model>
                     </models>
                  </action>
                  <action type="updateRow" fieldmodel="ModeTracker" field="IsEditMode" enclosevalueinquotes="false"/>
                  <action type="custom" snippet="updateComponentMode"/>
               </actions>
            </action>
         </actions>
      </pagetitle>
      <tabset rememberlastusertab="false" defertabrendering="true" uniqueid="sk-1_tBUl-82" renderas="">
         <tabs>
            <tab name="Tab 1">
               <components>
                  <custom name="toggletabcontentsdisplaymode" uniqueid="sk-1-QRWn-606"/>
                  <grid uniqueid="sk-1-EA4Q-729">
                     <divisions>
                        <division behavior="flex" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showsavecancel="false" showheader="true" model="Account" mode="read" uniqueid="sk-1_t4jb-69" buttonposition="" layout="" cssclass="dynamicmode">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Dynamic Mode" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                        <division behavior="flex" verticalalign="top" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showheader="true" showsavecancel="false" showerrorsinline="true" model="ModeTracker" buttonposition="" uniqueid="sk-1-E6O3-719" mode="read" layout="">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Read Only" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                     </divisions>
                     <styles>
                        <styleitem type="background" bgtype="none"/>
                     </styles>
                  </grid>
               </components>
               <oninitialshowactions/>
               <onshowactions>
                  <action type="custom" snippet="updateTabComponents"/>
               </onshowactions>
            </tab>
            <tab name="Tab 2" loadlazypanels="true">
               <components>
                  <custom name="toggletabcontentsdisplaymode" uniqueid="sk-1-NACY-142"/>
                  <grid uniqueid="sk-1-EA4Q-729">
                     <divisions>
                        <division behavior="flex" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showsavecancel="false" showheader="true" model="Account" mode="readonly" uniqueid="sk-1_t4jb-777" buttonposition="" layout="" cssclass="dynamicmode">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Dynamic Mode" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                             <renderconditions logictype="and"/>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                        <division behavior="flex" verticalalign="top" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showheader="true" showsavecancel="false" showerrorsinline="true" model="ModeTracker" buttonposition="" uniqueid="sk-1-E6O3-778" mode="read" layout="">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Read Only" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                     </divisions>
                     <styles>
                        <styleitem type="background" bgtype="none"/>
                     </styles>
                  </grid>
               </components>
               <oninitialshowactions/>
               <onshowactions>
                  <action type="custom" snippet="updateTabComponents"/>
               </onshowactions>
            </tab>
            <tab name="Tab 3" loadlazypanels="true">
               <components>
                  <custom name="toggletabcontentsdisplaymode" uniqueid="sk-1-NC1K-146"/>
                  <grid uniqueid="sk-1-EA4Q-729">
                     <divisions>
                        <division behavior="flex" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showsavecancel="false" showheader="true" model="Account" mode="read" uniqueid="sk-1_t4jb-779" buttonposition="" layout="" cssclass="dynamicmode">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Dynamic Mode" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                        <division behavior="flex" verticalalign="top" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showheader="true" showsavecancel="false" showerrorsinline="true" model="ModeTracker" buttonposition="" uniqueid="sk-1-E6O3-780" mode="read" layout="">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Read Only" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                     </divisions>
                     <styles>
                        <styleitem type="background" bgtype="none"/>
                     </styles>
                  </grid>
               </components>
               <oninitialshowactions/>
               <onshowactions>
                  <action type="custom" snippet="updateTabComponents"/>
               </onshowactions>
            </tab>
            <tab name="Tab 4" loadlazypanels="true">
               <components>
                  <custom name="toggletabcontentsdisplaymode" uniqueid="sk-1-NDH_-150"/>
                  <grid uniqueid="sk-1-EA4Q-729">
                     <divisions>
                        <division behavior="flex" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showsavecancel="false" showheader="true" model="Account" mode="read" uniqueid="sk-1_t4jb-781" buttonposition="" layout="" cssclass="dynamicmode">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Dynamic Mode" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                        <division behavior="flex" verticalalign="top" minwidth="100px" ratio="1">
                           <components>
                              <basicfieldeditor showheader="true" showsavecancel="false" showerrorsinline="true" model="ModeTracker" buttonposition="" uniqueid="sk-1-E6O3-782" mode="read" layout="">
                                 <columns>
                                    <column width="100%">
                                       <sections>
                                          <section title="Read Only" collapsible="no">
                                             <fields>
                                                <field id="Name"/>
                                                <field id="Description"/>
                                             </fields>
                                          </section>
                                       </sections>
                                    </column>
                                 </columns>
                              </basicfieldeditor>
                           </components>
                        </division>
                     </divisions>
                     <styles>
                        <styleitem type="background" bgtype="none"/>
                     </styles>
                  </grid>
               </components>
               <oninitialshowactions/>
               <onshowactions>
                  <action type="custom" snippet="updateTabComponents"/>
               </onshowactions>
            </tab>
         </tabs>
      </tabset>
   </components>
   <resources>
      <labels/>
      <css/>
      <javascript>
         <jsitem location="inline" name="updateComponentMode" cachelocation="false" url="">(function( $S, $, undefined ) {
    'use strict';
    // put this class on each component that you want to dynamically flip modes with
    var dynamicModeSelector = '.dynamicmode';
    
    // jquery extension method
$.fn.myns__updateComponentMode = function() {
        // get the desired mode from the UI only field in the model
        var mode = $S.$M('ModeTracker').getFirstRow().IsEditMode ? 'edit' : 'readonly';
        
return this.each(function() {
var componentElem = this
, component = $( componentElem ).data( 'component' )
, componentType = component.getType();
// Currently, this snippet only supports toggling tables and field editors
// However, it would be relatively easy to add other types of components
// as appropriate by adding a "case" statement below:
switch ( componentType ){
case 'skootable':
case 'basicfieldeditor':
var componentObject = $( componentElem ).data( 'object' );
if (!componentObject || !componentObject.list || !componentObject.list.mode) {
console.log('component [' + componentElem.id + '] does not contain skuid object.  Possibly conditionally rendered out of page.');
} else if ((componentObject.mode !== mode) || (componentObject.list.mode !== mode)) {
componentObject.mode = componentObject.list.mode = mode;
componentObject.list.render({doNotCache:true});
} else {
console.log('myns__updateComponentMode - Component already in target mode, no need to change');
}
break;
// case 'othertype':
//    ...
//    break;
}
});
};
    // custom component that should be placed at the top of each tab
    $S.componentType.register('toggletabcontentsdisplaymode', function(domElement, xmlConfig, component) {
        // skuid will fire an attach event when it adds the tab to the DOM
        // we take advantage of this so that we can walk the tab and update the mode for
        // components in the tab that have our dynamicmode class
$(domElement).bind('attach', function() {
// store off reference to ourself
    var self = this;
// select any components within this tab that are marked for display mode toggling
var selector = $(self).parent().find(dynamicModeSelector);
    // update component mode
    $(selector).myns__updateComponentMode();
    });
   
    });
    skuid.snippet.registerSnippet('updateComponentMode', function() {
        // update all components that have the class dynamicmode
$(dynamicModeSelector).myns__updateComponentMode();
    });
})(skuid, skuid.$);</jsitem>
      </javascript>
   </resources>
   <styles>
      <styleitem type="background" bgtype="none"/>
   </styles>
</skuidpage>
(Edited)
Photo of Karen Waldschmitt

Karen Waldschmitt, Official Rep

  • 8,710 Points 5k badge 2x thumb
Official Response
Good news! Check out this documentation about the Run Component Action that went live in the 11.2.0 release. One use is to change a field editor or table mode from read to edit mode via a button!