/* ====================================================================
   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.poi.xslf.usermodel;

import java.net.URI;

import org.apache.poi.common.usermodel.HyperlinkType;
import org.apache.poi.openxml4j.opc.PackagePart;
import org.apache.poi.openxml4j.opc.PackagePartName;
import org.apache.poi.openxml4j.opc.PackageRelationship;
import org.apache.poi.openxml4j.opc.TargetMode;
import org.apache.poi.sl.usermodel.Hyperlink;
import org.apache.poi.sl.usermodel.Slide;
import org.apache.poi.util.Internal;
import org.openxmlformats.schemas.drawingml.x2006.main.CTHyperlink;

public class XSLFHyperlink implements Hyperlink<XSLFShape,XSLFTextParagraph> {
    final XSLFSheet _sheet;
    final CTHyperlink _link;

    XSLFHyperlink(CTHyperlink link, XSLFSheet sheet){
        _sheet = sheet;
        _link = link;
    }

    @Internal
    public CTHyperlink getXmlObject(){
        return _link;
    }

    @Override
    public void setAddress(String address) {
        linkToUrl(address);
    }

    @Override
    public String getAddress() {
        String id = _link.getId();
        if (id == null || "".equals(id)) {
            return _link.getAction();
        }

        URI targetURI = _sheet.getPackagePart().getRelationship(id).getTargetURI();
        
        return targetURI.toASCIIString();
    }

    @Override
    public String getLabel() {
        return _link.getTooltip();
    }

    @Override
    public void setLabel(String label) {
        _link.setTooltip(label);
    }

    @Override
    public int getType() {
        return getTypeEnum().getCode();
    }
    
    @Override
    public HyperlinkType getTypeEnum() {
        String action = _link.getAction();
        if (action == null) {
            action = "";
        }
        if (action.equals("ppaction://hlinksldjump") || action.startsWith("ppaction://hlinkshowjump")) {
            return HyperlinkType.DOCUMENT;
        }
        
        String address = getAddress();
        if (address == null) {
            address = "";
        }
        if (address.startsWith("mailto:")) {
            return HyperlinkType.EMAIL;
        } else {
            return HyperlinkType.URL;
        }
    }

    @Override
    public void linkToEmail(String emailAddress) {
        linkToExternal("mailto:"+emailAddress);
        setLabel(emailAddress);
    }

    @Override
    public void linkToUrl(String url) {
        linkToExternal(url);
        setLabel(url);
    }

    private void linkToExternal(String url) {
        PackagePart thisPP = _sheet.getPackagePart();
        if (_link.isSetId() && !_link.getId().isEmpty()) {
            thisPP.removeRelationship(_link.getId());
        }
        PackageRelationship rel = thisPP.addExternalRelationship(url, XSLFRelation.HYPERLINK.getRelation());
        _link.setId(rel.getId());
        if (_link.isSetAction()) {
            _link.unsetAction();
        }
    }

    @Override
    public void linkToSlide(Slide<XSLFShape,XSLFTextParagraph> slide) {
        PackagePart thisPP = _sheet.getPackagePart();
        PackagePartName otherPPN = ((XSLFSheet)slide).getPackagePart().getPartName();
        if (_link.isSetId() && !_link.getId().isEmpty()) {
            thisPP.removeRelationship(_link.getId());
        }
        PackageRelationship rel =
            thisPP.addRelationship(otherPPN, TargetMode.INTERNAL, XSLFRelation.SLIDE.getRelation());
        _link.setId(rel.getId());
        _link.setAction("ppaction://hlinksldjump");
    }

    @Override
    public void linkToNextSlide() {
        linkToRelativeSlide("nextslide");
    }

    @Override
    public void linkToPreviousSlide() {
        linkToRelativeSlide("previousslide");
    }

    @Override
    public void linkToFirstSlide() {
        linkToRelativeSlide("firstslide");
    }

    @Override
    public void linkToLastSlide() {
        linkToRelativeSlide("lastslide");
    }
    
    private void linkToRelativeSlide(String jump) {
        PackagePart thisPP = _sheet.getPackagePart();
        if (_link.isSetId() && !_link.getId().isEmpty()) {
            thisPP.removeRelationship(_link.getId());
        }
        _link.setId("");
        _link.setAction("ppaction://hlinkshowjump?jump="+jump);
    }
}