38

セルが編集されると、PrimeFaces Datatable を再レンダリングするのが困難です。1 つのセルの値を変更すると、他のセルのエントリが変更される可能性があるため、テーブル全体を更新する必要があります。

JSFページは次のとおりです。

<h:form id="testForm">
    <p:outputPanel id="testContainer">

        <p:dataTable id="testTable" value="#{tableBean.data}" var="entry" editable="true" editMode="cell">

            <p:ajax event="cellEdit" listener="#{tableBean.onCellEdit}" update=":testForm:testContainer" />

            <p:column headerText="Col1">  
                <p:cellEditor>
                    <f:facet name="output"><h:outputText value="#{entry.col1}" /></f:facet>
                    <f:facet name="input"><p:inputText value="#{entry.col1}" /></f:facet>
                </p:cellEditor> 
            </p:column>

            <p:column headerText="Col2">
                <p:cellEditor>
                    <f:facet name="output"><h:outputText value="#{entry.col2}" /></f:facet>
                    <f:facet name="input"><p:inputText value="#{entry.col2}" /></f:facet>
                </p:cellEditor>  
            </p:column>

        </p:dataTable>

        <p:commandButton id="refreshButton" value="Redisplay" update="testContainer" />

    </p:outputPanel>                                    
</h:form>

バッキング Bean は次のとおりです。

@ManagedBean(name = "tableBean", eager = false)
@ViewScoped 
public class TableBean {

    public TableBean() {
        RowData entry = new RowData("a1", "b1");
        entries.add(entry);
        entry = new RowData("a2", "b2");
        entries.add(entry);
        entry = new RowData("a3", "b3");
        entries.add(entry);
    }

    public class RowData {

        private String col1;
        private String col2;

        public RowData(String col1, String col2) {
            this.col1 = col1;
            this.col2 = col2;
        }

        public String getCol1() {
            return col1;
        }

        public void setCol1(String col1) {
            this.col1 = col1;
        }

        public String getCol2() {
            return col2;
        }

        public void setCol2(String col2) {
            this.col2 = col2;
        }
    }

    private ArrayList<RowData> entries = new ArrayList<RowData>();

    public List<RowData> getData() {
        return entries;
    }

    public void onCellEdit(CellEditEvent event) {
        entries.get(event.getRowIndex()).setCol1("Dummy Col 1");
        entries.get(event.getRowIndex()).setCol2("Dummy Col 2");        
    }   
}

update=":testForm:testContainer" を cellEdit AJAX イベント内に含めると、セルの値を変更すると、画面上のデータ テーブルが削除され、セルのコンテンツのみが (ボタンと共に) レンダリングされます。これがなぜなのかわかりません。update 属性が指定されていない場合、テーブルはアクティブ セルが更新された状態で画面に残りますが、他のセルは更新されません (予想どおり)。

AJAX cellEdit イベント内で update 属性を指定せず、セルの値を編集した後に [再表示] ボタンをクリックすることで、目的の動作を (自動化されていない方法で) 実現できます。自動化された方法でこれを達成するにはどうすればよいですか? update 属性が期待どおりに機能しないのはなぜですか?

PrimeFaces 4.0 を使用しています。

4

8 に答える 8

6

どの解決策もうまくいかなかった場合、これは私にとってはうまくいきました

<p:dataTable ... id="theId" widgetVar="theWidget" ...>
                <p:ajax event="rowEdit" listener="#{...}"
                        oncomplete="PF('theWidget').filter()"/> 
....

テーブルの「リロード」を行うメソッドはすべて機能するはずです。テーブルに列フィルターがあるため、フィルターを使用しました。

于 2016-06-15T13:42:53.170 に答える
0

私はあなたのコードをテストしました。まず、p:outputPanel から p:commandButton を移動しました。変更されたコードは次のとおりです。

<h:form id="testForm">
            <p:outputPanel id="testContainer">

                <p:dataTable id="testTable" value="#{tableBean.data}" var="entry" editable="true" editMode="cell">

                    <p:ajax event="cellEdit" listener="#{tableBean.onCellEdit}" update=":testForm:testContainer" />

                    (...)

                </p:dataTable>
            </p:outputPanel>
            <p:commandButton id="refreshButton" value="Redisplay" update="testContainer" />
        </h:form>

このコードは正しく動作しないと思います。テーブル内の何かを変更すると、p:ajax は毎回完全なテーブルをレンダリングします。そのため、プログラムは TableBean コンストラクターから基本データをロードし、新しいデータを削除しました。

基本データ

p:ajax コードを省略しても、画面から新しいデータが消えることはありません。p:commandButtonはrefreshButton正しく機能します。

update=":testForm:testContainer" を cellEdit AJAX イベント内に含めると、セルの値を変更すると、画面上のデータ テーブルが削除され、セルのコンテンツのみが (ボタンと共に) レンダリングされます。これがなぜなのかわかりません。

update=":testForm:testContainer"それはあなたのoutputPanelを例外以上に更新するので、ajaxに追加するのは悪い設計だと思います(プログラムが何度もテーブルを更新するため、最初は正しく動作しますが、2回目はセルを編集できませんでした)。

私はあなたの目標が何であるかわかりません。commandButton を使用せずにテーブルをレンダリングする場合は、JavaScript イベントまたは p:message を 1 つ指定すると、テーブルをレンダリングできます。

p:ajax で update を省略したり、1 つの p:message の update を指定したりして、p.commandButton をtestContainerコードの外に移動すると、正しく動作すると思います。

于 2013-11-02T12:09:44.057 に答える
0

これは私の初めての投稿です。ltlBeBoy が述べたように、BalusC のソリューションは、セル編集がエンター キー ヒットで行われた場合にのみ機能します。ここにリストされている他の提案はどれも私にとってはうまくいきませんでした。私の場合、 cellEdit イベントでテーブルの特定の行 (各列の平均がある) を更新したかっただけです。誰かが解決策を探している場合に備えて、これを投稿しています。メインのデータテーブルのすぐ下にある2番目のデータテーブルでその行を分離することで、これを達成できました。コードは次のとおりです。

<pf:ajax event="cellEdit"
         listener="#{newAgentMetricBacking.onCellEdit}"
         update="c21413" />

<pf:dataTable id="c21413"
              styleClass="noHeader"
              value="">
    <pf:column>
        <h:outputText value="#{bundle.TeamAverage}"/>
    </pf:column>
    <pf:columns columnIndexVar="j"
                value="#{newAgentMetricBacking.averageArray}"
                var="avg">
        <h:outputText value="#{newAgentMetricBacking. 
                               averageArray[j]}"/>
    </pf:columns>
</pf:dataTable>

それ以外の場合は、今日の時点で、特に cellEdit イベントの成功時にテーブル全体または特定の行を更新するためのより良い解決策を見つけることができませんでした。乾杯!

于 2022-01-14T21:56:25.047 に答える
0

プロセスを使ってみる

<p:remoteCommand name="onCellEdit" update="testContainer" process="@this" /> <p:dataTable ...> <p:ajax event="cellEdit" listener="#{tableBean.onCellEdit}" oncomplete ="onCellEdit()" process="@this" /> ... </p:dataTable>

于 2021-06-15T15:02:57.397 に答える