/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

package org.apache.myfaces.tobago.internal.renderkit.renderer;

import org.apache.myfaces.tobago.component.Facets;
import org.apache.myfaces.tobago.component.RendererTypes;
import org.apache.myfaces.tobago.context.Markup;
import org.apache.myfaces.tobago.internal.component.AbstractUIOut;
import org.apache.myfaces.tobago.internal.component.AbstractUISection;
import org.apache.myfaces.tobago.internal.util.HtmlRendererUtils;
import org.apache.myfaces.tobago.internal.util.RenderUtils;
import org.apache.myfaces.tobago.model.CollapseMode;
import org.apache.myfaces.tobago.renderkit.css.TobagoClass;
import org.apache.myfaces.tobago.renderkit.html.HtmlElements;
import org.apache.myfaces.tobago.util.ComponentUtils;
import org.apache.myfaces.tobago.webapp.TobagoResponseWriter;

import javax.faces.component.UIComponent;
import javax.faces.context.FacesContext;
import java.io.IOException;

public class SectionRenderer extends PanelRendererBase {

  @Override
  public void encodeBegin(final FacesContext facesContext, final UIComponent component) throws IOException {

    final AbstractUISection section = (AbstractUISection) component;
    final TobagoResponseWriter writer = getResponseWriter(facesContext);
    final String clientId = section.getClientId(facesContext);
    final boolean collapsed = section.isCollapsed();
    final Markup markup = section.getMarkup();

    writer.startElement(HtmlElements.DIV);
    writer.writeIdAttribute(clientId);
    writer.writeClassAttribute(
        TobagoClass.SECTION,
        TobagoClass.SECTION.createMarkup(markup),
        collapsed ? TobagoClass.COLLAPSED : null,
        section.getCustomClass());
    HtmlRendererUtils.writeDataAttributes(facesContext, writer, section);

    final HtmlElements tag;
    switch (section.getLevel()) {
      case 1:
        tag = HtmlElements.H1;
        break;
      case 2:
        tag = HtmlElements.H2;
        break;
      case 3:
        tag = HtmlElements.H3;
        break;
      case 4:
        tag = HtmlElements.H4;
        break;
      case 5:
        tag = HtmlElements.H5;
        break;
      default:
        tag = HtmlElements.H6;
    }

    if (section.getCollapsedMode() != CollapseMode.none) {
      encodeHidden(writer, clientId, collapsed);
    }

    writer.startElement(HtmlElements.DIV);
    writer.writeClassAttribute(TobagoClass.SECTION__HEADER);
    writer.startElement(tag);

    final String image = section.getImage();
    HtmlRendererUtils.encodeIconOrImage(writer, image);

    final UIComponent labelFacet = ComponentUtils.getFacet(section, Facets.label);
    final String labelString = section.getLabel();
    if (labelFacet != null) {
      for (final UIComponent child : RenderUtils.getFacetChildren(labelFacet)) {
        if (child instanceof AbstractUIOut) {
          child.setRendererType(RendererTypes.OutInsideSectionLabel.name());
        }
        child.encodeAll(facesContext);
      }
    } else if (labelString != null) {
      writer.startElement(HtmlElements.SPAN);
      writer.writeText(labelString);
      writer.endElement(HtmlElements.SPAN);
    }
    writer.endElement(tag);

    final UIComponent bar = ComponentUtils.getFacet(section, Facets.bar);
    if (bar != null) {
      bar.encodeAll(facesContext);
    }

    writer.endElement(HtmlElements.DIV);

    writer.startElement(HtmlElements.DIV);
    writer.writeClassAttribute(TobagoClass.SECTION__CONTENT);
  }

  @Override
  public void encodeEnd(final FacesContext facesContext, final UIComponent component) throws IOException {

    final TobagoResponseWriter writer = getResponseWriter(facesContext);
    writer.endElement(HtmlElements.DIV);
    writer.endElement(HtmlElements.DIV);
  }
}
