Details

    • Type: New Feature New Feature
    • Status: Resolved
    • Priority: Major Major
    • Resolution: Duplicate
    • Affects Version/s: 5.3.2
    • Fix Version/s: None
    • Component/s: tapestry-core
    • Labels:
      None

      Description

      I've seen several posts on the mailing lists asking for how to render blocks manually in pages/components.

      Had a use case in this issue: https://issues.apache.org/jira/browse/TAP5-1863

      Basically I tried with:
      --------
      RenderCommand renderCommand = (RenderCommand)alertBlock;
      MarkupWriter markupWriter = new MarkupWriterImpl();
      RenderQueueImpl renderQueue = new RenderQueueImpl(log);
      renderQueue.push(renderCommand);
      renderQueue.run(markupWriter);

      alertManager.info(markupWriter.toString());
      --------

      Don't know if it's the 'correct' way of doing things so requesting a service or a helper class available in core that does the job.

        Issue Links

          Activity

          Magnus Kvalheim created issue -
          Hide
          Lance added a comment -

          See http://tapestry.1045711.n5.nabble.com/Getting-the-HTML-markup-string-from-a-RenderCommand-td5564418.html for a solution that does not require the use of internal classes.

          Show
          Lance added a comment - See http://tapestry.1045711.n5.nabble.com/Getting-the-HTML-markup-string-from-a-RenderCommand-td5564418.html for a solution that does not require the use of internal classes.
          Jochen Kemnade made changes -
          Field Original Value New Value
          Link This issue relates to TAP5-938 [ TAP5-938 ]
          Hide
          Michael Wyraz added a comment -

          This feature is much discussed and often requested. There seems to be several ways to do so, it's unclear which is the best.

          I use the one above beacuse it is the cleanest, most easy to understand - but I have no idea if there are any drawbacks. Too much internal knowledge is required to decide this.

          To please pick this issue and add the service to T5.4!

          Thank you!

          Show
          Michael Wyraz added a comment - This feature is much discussed and often requested. There seems to be several ways to do so, it's unclear which is the best. I use the one above beacuse it is the cleanest, most easy to understand - but I have no idea if there are any drawbacks. Too much internal knowledge is required to decide this. To please pick this issue and add the service to T5.4! Thank you!
          Hide
          Michael Wyraz added a comment -

          Attached a minimal service+impl

          Show
          Michael Wyraz added a comment - Attached a minimal service+impl
          Michael Wyraz made changes -
          Attachment RenderCommandToStringService.java [ 12612692 ]
          Attachment RenderCommandToStringServiceImpl.java [ 12612693 ]
          Hide
          Michael Wyraz added a comment -

          What happens if such a render command adds scripts or css to the page? I assume It would be added to the page, not to the new queue or so - so more investigation is required here.

          Show
          Michael Wyraz added a comment - What happens if such a render command adds scripts or css to the page? I assume It would be added to the page, not to the new queue or so - so more investigation is required here.
          Hide
          Dmitry Gusev added a comment -

          Rendering block is not that trivial, because, in general, block may require context for rendering.
          And by context I mean parameters bindings. It's often happens that you first need to initialize some properties of your page/component before you can render a block.

          In my projects I usually create separate internal pages, usually one page per block. Then I declare properties/parameters on that page which are consumed by block.

          Then later in code I programmatically initialize properties for that page and trigger some component event on that page so that the event handler return me a block or render it via AjaxResponseRenderer. I use tapestry's AJAX functionality to grab generated event response in JSON format that contains rendered HTML snippets which corresponds to rendered blocks. Not sure if you can add CSS to response programmatically, but you can surely add JavaScripts – so all those JS contributions also can be found in the resulting JSON.

          I've described this approach on the T5 mailing list few times with code snippets, here is my blog entry about that: http://dmitrygusev.blogspot.ru/2013/04/render-tapestry5-block-to-string-from.html

          Show
          Dmitry Gusev added a comment - Rendering block is not that trivial, because, in general, block may require context for rendering. And by context I mean parameters bindings. It's often happens that you first need to initialize some properties of your page/component before you can render a block. In my projects I usually create separate internal pages, usually one page per block. Then I declare properties/parameters on that page which are consumed by block. Then later in code I programmatically initialize properties for that page and trigger some component event on that page so that the event handler return me a block or render it via AjaxResponseRenderer. I use tapestry's AJAX functionality to grab generated event response in JSON format that contains rendered HTML snippets which corresponds to rendered blocks. Not sure if you can add CSS to response programmatically, but you can surely add JavaScripts – so all those JS contributions also can be found in the resulting JSON. I've described this approach on the T5 mailing list few times with code snippets, here is my blog entry about that: http://dmitrygusev.blogspot.ru/2013/04/render-tapestry5-block-to-string-from.html
          Hide
          Lance added a comment -

          FYI I have an outstanding issue to add a component to tapestry-stitch which will convert it's body to an html string and either set a property or invoke an action here https://github.com/uklance/tapestry-stitch/issues/14

          It sould be possible to invoke this via page render or ajax update.

          Show
          Lance added a comment - FYI I have an outstanding issue to add a component to tapestry-stitch which will convert it's body to an html string and either set a property or invoke an action here https://github.com/uklance/tapestry-stitch/issues/14 It sould be possible to invoke this via page render or ajax update.
          Hide
          Michael Wyraz added a comment -

          Lance For doing such in a render phase there are better ways (namely intercepting "beforrender"/"afterrender" and capture/remove the generated markup from the actual document).

          Show
          Michael Wyraz added a comment - Lance For doing such in a render phase there are better ways (namely intercepting "beforrender"/"afterrender" and capture/remove the generated markup from the actual document).
          Lance made changes -
          Comment [ Something like this:

          {code}
          package foo.bar.components;

          public class CaptureBody {
             @Property
             private Binding value;

             @Property
             private MarkupHandler handler;

             void beforeRender(MarkupWriter writer) {
                if (value == null && handler == null) {
                   throw new IllegalStateException("value or handler must be specified");
                }
                writer.element("deleteme");
             }

             // let the body render

             void afterRender(MarkupWriter writer) {
                Element container = writer.getElement();
                writer.end();
                String markup = container.getChildMarkup();
                container.remove();

                if (value != null) {
                   value.set(markup);
                }

                if (handler != null) {
                   handler.handle(markup);
                }
             }
          }
          {code} ]
          Lance made changes -
          Comment [ Yes, that's exactly what the proposed component will do. It will use it's own render phases to capture/remove the markup from the current render (page or ajax). ]
          Hide
          Lance added a comment -

          I've added a 'capture' component to tapestry-stitch and a demo which demonstrates capturing markup during page render and ajax update.

          Demo here: http://tapestry-stitch.uklance.cloudbees.net/capturedemo

          Show
          Lance added a comment - I've added a 'capture' component to tapestry-stitch and a demo which demonstrates capturing markup during page render and ajax update. Demo here: http://tapestry-stitch.uklance.cloudbees.net/capturedemo
          Hide
          Thiago H. de Paula Figueiredo added a comment -

          Duplicate of TAP5-938.

          Show
          Thiago H. de Paula Figueiredo added a comment - Duplicate of TAP5-938 .
          Thiago H. de Paula Figueiredo made changes -
          Status Open [ 1 ] Resolved [ 5 ]
          Resolution Duplicate [ 3 ]

            People

            • Assignee:
              Unassigned
              Reporter:
              Magnus Kvalheim
            • Votes:
              7 Vote for this issue
              Watchers:
              7 Start watching this issue

              Dates

              • Created:
                Updated:
                Resolved:

                Development