
/*  Copyright (c) 2000, 2003 by Oracle Corporation. All Rights Reserved. */

package oracle.portal.sample.v1.devguide.helloworld;

import oracle.portal.provider.v1.*;
import oracle.portal.provider.v1.http.*;
import oracle.portal.utils.xml.v1.XMLUtil;
import oracle.portal.sample.v1.devguide.helloworld.resource.HelloWorldBundle;

import java.io.*;
import java.util.*;
import java.text.*;

/**
 * A Class class.

 */
public class HelloWorldRenderer implements PortletRenderer {


    /**
     * Constructor
     */
    public HelloWorldRenderer() {
    }

    public void render(PortletRenderRequest pr) throws PortletException, AccessControlException {
        switch (pr.getMode()) {
        case PortletRenderer.MODE_SHOW:
            renderShow(pr);
            break;
        case PortletRenderer.MODE_EDIT:
            renderEdit(pr);
            break;
        case PortletRenderer.MODE_EDIT_DEFAULTS:
            renderEditDefaults(pr);
            break;
        case PortletRenderer.MODE_SHOW_DETAILS:
            renderShowDetails(pr);
            break;
        case PortletRenderer.MODE_PREVIEW:
            renderPreview(pr);
            break;
        case PortletRenderer.MODE_HELP:
            renderHelp(pr);
            break;
        case PortletRenderer.MODE_ABOUT:
            renderAbout(pr);
            break;
        case PortletRenderer.MODE_LINK:
            renderLink(pr);
            break;
        default:
            throw new PortletException("HelloWorld render failed: Invalid render mode " + pr.getMode());
        }
    }

    private void renderShow(PortletRenderRequest pr) throws PortletException, AccessControlException {
        try {
            String user = pr.getUser().getName();
            PrintWriter out = pr.getWriter(pr.getPreferredContentType());
            ProviderSession session = pr.getSession();
            Locale l = pr.getLocale();

            if (session != null)
            {
                // increment session count
                int i = 0;
                Integer old = ((Integer) session.getValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "count")));
                if (old != null) {
                    i = old.intValue();
                }
                Integer newCount = new Integer(i + 1);
                session.putValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "count"), newCount);
            }

            // Use cached version until user changes values through customization
            String version = HttpPortletRendererUtil.getCachedVersion(pr);
            if (version != null && session != null)
            {
                // we are being asked to validate our version
                Boolean b = ((Boolean) session.getValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "hasChanged")));

                // A null value is the same as hasChanged == true
                if (b != null && !b.booleanValue())
                {
                    // reuse the existing version
                    HttpPortletRendererUtil.useCachedVersion(pr);
                    return;
                }
            }

            //  Remove any indication this portlet has changed
            if (session != null)
            {
                session.putValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "hasChanged"), Boolean.FALSE);
            }

            // Get the customized greeting and title
            NameValuePersonalizationObject data = (NameValuePersonalizationObject) PortletRendererUtil.getEditData(pr);
            String title = data.getPortletTitle();
            ResourceBundle b = pr.getPortlet().getResourceBundle(pr.getLocale());
            MessageFormat message = 
                new MessageFormat(b.getString(HelloWorldBundle.DEFAULT_MSG));

            Object[] messageArgs = {(user != null) ? user : "" };

            // determine whether an HTML render or an mobile render
            if (pr.getPreferredContentType().startsWith(PortletRenderer.TYPE_HTML)) {
                // Writes container -- handles rendering the border if necessary
                PortletRendererUtil.renderPortletHeader(pr, out, title);
                out.println(message.format(messageArgs));
                if (session == null)
                {
                    out.println("<p>Your provider session has been terminated.  Please log out and log back in again<p>");
                }
                out.println("<p><p><p><p><font size=\"-2\"><i>Last updated on " + new Date().toString() + "</i></font><p>");
                // Ends the container
                PortletRendererUtil.renderPortletFooter(pr, out);
            } else if (pr.getPreferredContentType().startsWith(PortletRenderer.TYPE_MOBILE)) {
                out.println("<SimpleText>");
                out.println("    <SimpleTextItem>" + XMLUtil.escapeXMLText(message.format(messageArgs)) + "</SimpleTextItem>");
                out.println("    <SimpleBreak/>");
                out.println("</SimpleText>");
            } else {
                throw new PortletException("Unsupported content-type: " + pr.getPreferredContentType());
            }

            // Tell the Portal to cache this result
            // As we maintain the render version in the session we don't need
            // to write anything meaningful in the cache information
            HttpPortletRendererUtil.setCachedVersion(pr, "OK_TO_CACHE", HttpProvider.USER_LEVEL);
        } catch (IllegalArgumentException ie) {
            logAndThrowException(pr.getProvider(), ie.getMessage());
        } catch (java.io.IOException ioe) {
            logAndThrowException(pr.getProvider(), ioe.getMessage());
        }
    }

    private void renderLink(PortletRenderRequest pr) throws PortletException, AccessControlException {
        try {
            PrintWriter out = pr.getWriter(pr.getPreferredContentType());
            
            // Get the customized greeting and title
            NameValuePersonalizationObject data = (NameValuePersonalizationObject) PortletRendererUtil.getEditData(pr);

            // determine whether an HTML render or an mobile render
            if (pr.getPreferredContentType().startsWith(PortletRenderer.TYPE_HTML)) {
                // Writes container -- handles rendering the border if necessary
                out.println("<a href=\"" + pr.getPageURL() + "\">" + data.getPortletTitle() + "</a>");
            } else if (pr.getPreferredContentType().startsWith(PortletRenderer.TYPE_MOBILE)) {
                String title = data.getPortletShortTitle();

                // shortTitles may be empty -- if it is use the title
                if (title == null || title.length() == 0)
                    title = data.getPortletTitle();

                // now output the response
                out.println("<SimpleHref target=\"" + XMLUtil.escapeXMLAttribute(pr.getPageURL()) + "\">");
                out.println(XMLUtil.escapeXMLText(title));
                out.println("</SimpleHref>");
            } else {
                throw new PortletException("Unsupported content-type: " + pr.getPreferredContentType());
            }
        } catch (IllegalArgumentException ie) {
            logAndThrowException(pr.getProvider(), ie.getMessage());
        } catch (java.io.IOException ioe) {
            logAndThrowException(pr.getProvider(), ioe.getMessage());
        }
    }

    private void logAndThrowException(Provider p, String msg) throws PortletException {
        p.log(msg);
        throw new PortletException(msg);
    }


    private void renderEdit(PortletRenderRequest pr) throws PortletException, AccessControlException {
        try {
            PrintWriter out = pr.getWriter("text/html");

            String action = pr.getParameter("hw_action");
            NameValuePersonalizationObject data = (NameValuePersonalizationObject) PortletRendererUtil.getEditData(pr);
            ProviderSession session = pr.getSession();
            Locale l = pr.getLocale();

            // Cancel automatically redirects to the page -- so will only receive 'OK' or 'APPLY'
            if (action != null) {
                String greeting = pr.getParameter("hw_greeting");
                String title = pr.getParameter("hw_title");
                String sTitle = pr.getParameter("hw_stitle");
                data.setPortletTitle(title);
                data.setPortletShortTitle(sTitle);
                PortletRendererUtil.submitEditData(pr, data);

                // write into session indication that cache is now invalid
                if(session != null)
                {
                    session.putValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "hasChanged"), Boolean.TRUE);
                }

                if (action.equalsIgnoreCase("OK")) {
                    HttpPortletRendererUtil.sendRedirect(pr, pr.getBackURL());
                    return;
                } else if (action.equalsIgnoreCase("APPLY")) {
                    HttpPortletRendererUtil.sendRedirect(pr, pr.getPageURL());
                    return;
                }
            } else {
                PortletRendererUtil.renderCustomizeFormHeader(pr, out, null, "hw_action", null, null);

                out.println("<TABLE BORDER=\"0\">");
                out.println("   <TR>");
                out.println("        <TD WIDTH=\"25%\">");
                out.println("            <P ALIGN=\"RIGHT\">("  + l.getDisplayLanguage(l) + ") title:");
                out.println("        </TD>");
                out.println("        <TD WIDTH=\"75%\">");
                out.println("            <INPUT TYPE=\"TEXT\" NAME=\"hw_title\" VALUE=\"");
                out.println(data.getPortletTitle() + "\" SIZE=\"20\" >");
                out.println("        </TD>");
                out.println("   </TR>");
                out.println("   <TR>");
                out.println("        <TD WIDTH=\"25%\">");
                out.println("            <P ALIGN=\"RIGHT\">(" + l.getDisplayLanguage(l) + ") short title:");
                out.println("        </TD>");
                out.println("        <TD WIDTH=\"75%\">");
                out.println("            <INPUT TYPE=\"TEXT\" NAME=\"hw_stitle\" VALUE=\"");
                out.println(data.getPortletShortTitle() + "\" SIZE=\"20\" MAXLENGTH=\"20\" >");
                out.println("       </TD>");
                out.println("   </TR>");
                out.println("</TABLE>");
                PortletRendererUtil.renderCustomizeFormFooter(pr, out);
            }

        } catch (IllegalArgumentException ie) {
            logAndThrowException(pr.getProvider(), ie.getMessage());
        } catch (java.io.IOException ioe) {
            logAndThrowException(pr.getProvider(), ioe.getMessage());
        }
    }

    private void renderEditDefaults(PortletRenderRequest pr) throws PortletException, AccessControlException {
        renderEdit(pr);
    }

    private void renderShowDetails(PortletRenderRequest pr) throws PortletException, AccessControlException {
        try {
            String user = pr.getUser().getName();
            PrintWriter out = pr.getWriter("text/html");
            ProviderSession session = pr.getSession();
            Locale l = pr.getLocale();
            Integer count = null;

            // See if a "clear count was submitted"
            if (pr.getParameter("details_action") != null) {
                // Clear the session count
                count = new Integer(0);
                session.putValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "count"), count);
                HttpPortletRendererUtil.sendRedirect(pr, pr.getBackURL());
            } else {
                // Get count of number of time the portlet has been rendered (in show mode)
                count = ((Integer) session.getValue(PortletRendererUtil.portletParameter(pr.getPortletReference(), "count")));
            }

            // Get other strings from the resource bundle
            ResourceBundle b = pr.getPortlet().getResourceBundle(l);

            if (b == null) logAndThrowException(pr.getProvider(), "Unable to locate the HelloWorld resource messages.");
            MessageFormat countMsg = new MessageFormat(b.getString(HelloWorldBundle.SESSION_MSG));
            MessageFormat lang = new MessageFormat(b.getString(HelloWorldBundle.LANGUAGE_MSG));

            Object[] countArgs = { count };
            Object[] langArgs = {l.getDisplayLanguage(l)};

            out.println("<center><h3>");
            out.println(lang.format(langArgs) + "<br>");
            out.println(countMsg.format(countArgs) + "</h3>");

            renderClearForm(pr, out, b);
            out.println("</center>");

        } catch (IllegalArgumentException ie) {
            logAndThrowException(pr.getProvider(), ie.getMessage());
        } catch (java.io.IOException ioe) {
            logAndThrowException(pr.getProvider(), ioe.getMessage());
        }
    }

    private void renderClearForm(PortletRenderRequest pr, PrintWriter out, ResourceBundle b) {
        // emit the form tag
        out.print("<form name=\"details_form\" action=\"");
        out.print(PortletRendererUtil.htmlFormActionLink(pr, PortletRendererUtil.PAGE_LINK));
        out.println("\" >");

        // emit hidden fields
        out.println(PortletRendererUtil.htmlFormHiddenFields(pr, PortletRendererUtil.PAGE_LINK));
        out.println("<INPUT TYPE=\"hidden\" name=\"details_action\" \" value=\"\" />");

        // emit javascript to avoid language/value issues
        out.println("<SCRIPT LANGUAGE=\"JavaScript1.1\">");
        out.println("<!-- Comment out script for old browsers");
        out.println("function doSubmit(action) {");
        out.println("   document.details_form.details_action.value=action");
        out.println("   document.details_form.submit()");
        out.println("}");
        out.println("//-->");
        out.println("</SCRIPT>");

        // output the button
        out.println("<INPUT TYPE=\"button\" NAME=\"clear\" VALUE=\"" + b.getString(HelloWorldBundle.CLEAR_MSG) + "\" onClick=\"javascript:doSubmit('CLEAR')\">");

        out.println("</form>");

    }

    private void renderPreview(PortletRenderRequest pr) throws PortletException, AccessControlException {
    }

    private void renderHelp(PortletRenderRequest pr) throws PortletException, AccessControlException {
        try {
            PrintWriter out = pr.getWriter("text/html");
            Locale l = pr.getLocale();

            // Get other strings from the resource bundle
            ResourceBundle b = pr.getPortlet().getResourceBundle(l);
            if (b == null) logAndThrowException(pr.getProvider(), "Unable to locate the HelloWorld resource messages.");

            PortletRendererUtil.renderInformationFormHeader(pr, out, null, b.getString(HelloWorldBundle.HELP_TITLE), null, null);

            out.println(b.getString(HelloWorldBundle.HELP_CONTENT));

            PortletRendererUtil.renderInformationFormFooter(pr, out);
        } catch (Exception e) {
            throw new PortletException(e);
        }
    }

    private void renderAbout(PortletRenderRequest pr) throws PortletException, AccessControlException {
        try {
            PrintWriter out = pr.getWriter("text/html");
            Locale l = pr.getLocale();

            // Get other strings from the resource bundle
            ResourceBundle b = pr.getPortlet().getResourceBundle(l);
            if (b == null) logAndThrowException(pr.getProvider(), "Unable to locate the HelloWorld resource messages.");


            PortletRendererUtil.renderInformationFormHeader(pr, out, null, b.getString(HelloWorldBundle.ABOUT_TITLE), null, null);
            out.println(pr.getParameter("_title"));
            out.println(b.getString(HelloWorldBundle.ABOUT_CONTENT));

            PortletRendererUtil.renderInformationFormFooter(pr, out);
        } catch (Exception e) {
            throw new PortletException(e);
        }
    }

}

