Повтор XForms - запрашивать у пользователя количество строк

Я хотел бы спросить пользователя через xf: input, «сколько элементов» вы хотите в определенном повторе, а затем, основываясь на ответе пользователя, представить повтор с этим количеством строк (что, я думаю, также будет быть сгенерирован в экземпляре xf:).

Я знаком с использованием триггеров для вставки и удаления строк.

Здесь я спрашиваю, как предложить пользователю создать и представить начальное количество строк.

Например, предположим, что пользователю нужно 10 строк. Я предполагаю, что повторяющиеся данные могут быть сделаны неактуальными, пока они не ответят на этот вопрос, и когда они ответят на него, какое-то действие может динамически создать строки, а затем сделать повторяющиеся данные релевантными.

Но как это сделать?

Обновление 20 декабря

Разметка ниже представляет поле ввода и в улучшенной форме добавляет строки в экземпляр при нажатии кнопки. Однако BetterForm не отображает данные в пользовательском интерфейсе (хотя я думаю, что это отдельный вопрос). Я не пробовал другие реализации.

<xhtml:head>
    <xf:model id="m">
        <xf:instance id="main-instance">
          <data>
            <items>
              <item1>item 11</item1>
              <item2>item 12</item2>
              <item3>item 13</item3>
            </items>
          </data>
          </xf:instance>


        <xf:instance id="variable">
            <variable xmlns="">
                <iteration-count/>
            </variable>
        </xf:instance>
    </xf:model>
</xhtml:head>
<xhtml:body>

  <!-- Simple field to enter the number of iterations -->
  <xf:input ref="instance('variable')/iteration-count">
    <xf:label>How many iterations?</xf:label>
  </xf:input>

  <xf:trigger>
    <xf:label>Insert with while</xf:label>
    <xf:action ev:event="DOMActivate">
            <xf:action while="instance('variable')/iteration-count != 0">
                <xf:insert ev:event="DOMActivate" nodeset="items"/>
                <xf:setvalue ref="instance('variable')/iteration-count" value=". - 1"/>
            </xf:action>
          <!--<xf:refresh model="m"/>-->
        </xf:action>
    </xf:trigger>


  <table>

    <tbody id="r-attrs" xf:repeat-nodeset="items">
      <tr>
        <td>
          <xf:output ref="item1"></xf:output>
        </td>
        <td>
          <xf:output ref="item2"></xf:output>
        </td>
        <td>
          <xf:output ref="item3"></xf:output>
        </td>
      </tr>
    </tbody>

  </table>       

</xhtml:body>


person JasonPlutext    schedule 16.12.2012    source источник


Ответы (3)


Атрибуты while и iterate действия будут повторять это действие.

person Alain Couthures    schedule 16.12.2012

Один из способов получить информацию от пользователя — привязать виджет ввода к элементу вспомогательного документа (я часто называю этот документ ui, так как он содержит информацию о статусе пользовательского интерфейса) и управлять вставкой и отображением из него. Если вы хотите, чтобы пользователь предоставил значение, вы можете сделать его по умолчанию равным 0; если вы этого не сделаете, вы можете указать какой-нибудь правдоподобный номер по умолчанию, который пользователь может переопределить, если пожелает.

person C. M. Sperberg-McQueen    schedule 16.12.2012

Вы задаете два отдельных вопроса, если я хорошо понимаю:

  1. как подсказать пользователю
  2. как вставить заданное количество итераций

Здесь

  1. Чтобы запросить пользователя, вы можете использовать диалоговое окно (xforms:dialog стандартизировано XForms 2.0, а Orbeon Forms поддерживает расширение xxforms:dialog). Вы также можете использовать xforms:switch, чтобы показать/скрыть поле по сравнению с повтором.

  2. Как только значение получено, вы можете, как говорит Ален, использовать атрибут while или iterate для выполнения действия вставки несколько раз. Или, если у вас XPath 2.0, вы можете использовать for в выражении origin.

Вот полный пример, который показывает два способа вставки:

<xh:html xmlns:xh="http://www.w3.org/1999/xhtml"
      xmlns:xf="http://www.w3.org/2002/xforms"
      xmlns:ev="http://www.w3.org/2001/xml-events">
    <xh:head>
        <xf:model>
            <xf:instance id="repeats">
                <repeats/>
            </xf:instance>
            <xf:instance id="count">
                <count/>
            </xf:instance>
        </xf:model>
    </xh:head>
    <xh:body>

        <!-- Simple field to enter the number of iterations -->
        <xf:input ref="instance('count')">
            <xf:label>How many iterations?</xf:label>
        </xf:input>

        <!-- Variant 1 -->
        <xf:trigger>
            <xf:label>Insert with for</xf:label>
            <xf:insert
                ev:event="DOMActivate"
                if="instance('count') castable as xs:integer"
                context="instance('repeats')"
                ref="repeat"
                origin="for $i in 1 to instance('count')
                        return xf:element('repeat')"/>
        </xf:trigger>

        <!-- Variant 2 -->
        <xf:trigger>
            <xf:label>Insert with while</xf:label>
            <xf:insert
                ev:event="DOMActivate"
                if="instance('count') castable as xs:integer"
                context="instance('repeats')"
                while="count(repeat) lt xs:integer(instance('count'))"
                ref="repeat"
                origin="xf:element('repeat')"/>
        </xf:trigger>

        <xf:trigger>
            <xf:label>Clear</xf:label>
            <xf:delete ev:event="DOMActivate" ref="instance('repeats')/*"/>
        </xf:trigger>

        <!-- Your repeat -->
        <xf:repeat ref="repeat">
            <xf:output value="position()"/>
        </xf:repeat>

    </xh:body>
</xh:html>
person Community    schedule 17.12.2012
comment
Спасибо за эти 2 варианта. Но при запуске этого примера в BetterForm ни один из вариантов не добавлял никаких данных в экземпляр Repeats. - person JasonPlutext; 20.12.2012
comment
Возможно, betterForm еще не поддерживает функцию xf:element(). Вместо этого вы также можете попробовать использовать экземпляр шаблона. Назовите его repeat-template и вместо xf:element() используйте instance('repeat-template'). Кроме этого, я не знаю betterForm, поэтому, если это не поможет, вам следует задать вопрос в списке рассылки betterForm и направить их на этот вопрос StackOverflow. - person ebruchez; 21.12.2012