简体   繁体   English

触发Primefaces p:selectOneMenu onchange

[英]Triggering Primefaces p:selectOneMenu onchange

It seems Primefaces p:selectOneMenu component wraps the rendered HTML <select> tag in a div and shows the selected item as a different label. 看来Primefaces p:selectOneMenu组件将呈现的HTML <select>标记包装在div中,并将所选项目显示为其他标签。 The changes made by the user are reflected to original <select> by javascript I guess, resulting the onchange event binded to <select> not to be worked. 我想,由用户做出的更改将通过javascript反映到原始的<select> ,从而导致onchange事件绑定到<select>无法工作。 Thus my following binding of onchange event for all :input s is not working for p:selectOneMenu s. 因此,我对所有:input的以下onchange事件绑定不适用于p:selectOneMenu

function applyChangeHandler() {
    $(':input').on('change', function() {
        console.log('on change: ' + this.id);
    });
}

However onchange attribute of p:selectOneMenu is being fired. 但是,将触发p:selectOneMenu onchange属性。 So Primefaces triggers this handler under the hood (again I guess). 因此,Primefaces会在后台触发该处理程序(同样,我想)。

<p:selectOneMenu id="myList" onchange="console.log('selectOneMenu')">
    <f:selectItem itemLabel="val1" itemValue="val1"/>
    <f:selectItem itemLabel="val2" itemValue="val2"/>
</p:selectOneMenu>

So my requirement is to somehow bind the onchange handler to all p:selectOneMenu s from applyChangeHandler() function above. 所以我的要求是以某种方式将onchange处理程序绑定到上述applyChangeHandler()函数中的所有p:selectOneMenu Or it may be triggerred manually with Primefaces specific API or other ways which I expect from you guys to share with. 或者可以通过Primefaces特定的API手动触发,也可以使用我希望与大家共享的其他方式。 Otherwise a quick workaround will be to use h:selectOneMenu instead. 否则,一种快速的解决方法是改用h:selectOneMenu

My goal is to detect "unsaved changes on the page". 我的目标是检测“页面上未保存的更改”。 So script above will be placed in a common template as: 因此,以上脚本将被放置在通用模板中,如下所示:

<p:outputPanel id="sc" autoUpdate="true">
    <script type="text/javascript">
        applyChangeHandler();
    </script>
</p:outputPanel>

Why do you need to provide additional listeners when the framework has already provided you with such? 当框架已经为您提供了这样的侦听器时,为什么还要提供其他侦听器呢?

If your goal is to use jQuery you just put your handler in a js file accessible from the window global scope. 如果您的目标是使用jQuery,则只需将处理程序放入可从窗口全局范围访问的js文件中。

function myChangeHandler(that) {
    //wrap the element with jQuery
    var select = jQuery(that);
    //Get the div parent. The actual wrapper of the `selection-menu` widget markup
    var selectMenu = select.parents('div.ui-selectonemenu');
    //From here I can manipulate any HTML child element using jQuery
    jQuery('label.ui-selectonemenu-label', selectMenu).text('mooo');
}

Then call your handler onchange , passing the selectOneMenu as parameter 然后调用您的处理程序onchange ,将selectOneMenu作为参数传递

<p:selectOneMenu id="myList" onchange="myChangeHandler(this)">
    <f:selectItem itemLabel="val1" itemValue="val1" />
    <f:selectItem itemLabel="val2" itemValue="val2" />
</p:selectOneMenu>

Instead of using onChange, you could utilize "DOMSubtreeModified". 除了使用onChange之外,您还可以使用“ DOMSubtreeModified”。

This works for p:selectOneMenu 这适用于p:selectOneMenu

$(".ui-selectonemenu-label").each(function(index) {
    $(this).on("DOMSubtreeModified", setDirty());
});

Also. 也。 Another possibility if you want the same generic code everywhere is to overwrite the prototype of SelectOneMenu as follows: 如果您想在各处使用相同的通用代码,则另一种可能的方法是如下重写SelectOneMenu的原型:

var origTriggerChange = PrimeFaces.widget.SelectOneMenu.prototype.triggerChange;
// if this code has been run already, don't accumulate triggerChangemethods!
if(origTriggerChange.isModified != "true"){
      PrimeFaces.widget.SelectOneMenu.prototype.triggerChange = function(b){
      this.jq.find("select").change();
      origTriggerChange.call(this, b);
   };
   PrimeFaces.widget.SelectOneMenu.prototype.triggerChange.isModified = "true";
}

You need to add widgetVar to p:selectOneMenu to play with it in JS 您需要将widgetVar添加到p:selectOneMenu才能在JS中使用它

<p:selectOneMenu id="myList" onchange="console.log('selectOneMenu')" widgetVar="myList">
  <f:selectItem itemLabel="val1" itemValue="val1"/>
  <f:selectItem itemLabel="val2" itemValue="val2"/>
</p:selectOneMenu>

this Will add this code to you page 这会将这段代码添加到您的页面

$(function(){
  PrimeFaces.cw("SelectOneMenu","myList",{
       id:"A2:Form:myList",
       effect:"fade"
  })
});

Hope this will help. 希望这会有所帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM