package com.ruoyi.warehouseBusiness.service.impl;


import com.ruoyi.basicData.mapper.TFeesMapper;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.finance.excel.FleetExcel;
import com.ruoyi.warehouseBusiness.domain.TWarehousebillsfees;
import com.ruoyi.warehouseBusiness.excel.BillDetailsSubItem;
import com.ruoyi.warehouseBusiness.excel.InStock;
import com.ruoyi.warehouseBusiness.excel.ListMapToBeanUtils;
import com.ruoyi.warehouseBusiness.excel.QueryMenu;
import com.ruoyi.warehouseBusiness.mapper.TWarehousebillsfeesMapper;
import com.ruoyi.warehouseBusiness.service.ITWarehousebillsfeesService;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.BorderStyle;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.VerticalAlignment;
import org.apache.poi.ss.util.CellRangeAddress;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.*;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;

/**
 * 仓库费用明细Service业务层处理
 *
 * @author ruoyi
 * @date 2020-12-11
 */
@Service
public class TWarehousebillsfeesServiceImpl implements ITWarehousebillsfeesService {
    @Autowired
    private TWarehousebillsfeesMapper tWarehousebillsfeesMapper;

    @Autowired
    private TFeesMapper tFeesMapper;

    /**
     * 查询仓库费用明细
     *
     * @param fId 仓库费用明细ID
     * @return 仓库费用明细
     */
    @Override
    public TWarehousebillsfees selectTWarehousebillsfeesById(Long fId) {
        return tWarehousebillsfeesMapper.selectTWarehousebillsfeesById(fId);
    }

    /**
     * 查询仓库费用明细列表
     *
     * @param tWarehousebillsfees 仓库费用明细
     * @return 仓库费用明细
     */
    @Override
    public List<TWarehousebillsfees> selectTWarehousebillsfeesList(TWarehousebillsfees tWarehousebillsfees) {
        return tWarehousebillsfeesMapper.selectTWarehousebillsfeesList(tWarehousebillsfees);
    }

    /**
     * 新增仓库费用明细
     *
     * @param tWarehousebillsfees 仓库费用明细
     * @return 结果
     */
    @Override
    public int insertTWarehousebillsfees(TWarehousebillsfees tWarehousebillsfees) {
        tWarehousebillsfees.setCreateTime(DateUtils.getNowDate());
        return tWarehousebillsfeesMapper.insertTWarehousebillsfees(tWarehousebillsfees);
    }

    /**
     * 修改仓库费用明细
     *
     * @param tWarehousebillsfees 仓库费用明细
     * @return 结果
     */
    @Override
    public int updateTWarehousebillsfees(TWarehousebillsfees tWarehousebillsfees) {
        tWarehousebillsfees.setUpdateTime(DateUtils.getNowDate());
        return tWarehousebillsfeesMapper.updateTWarehousebillsfees(tWarehousebillsfees);
    }

    /**
     * 批量删除仓库费用明细
     *
     * @param fIds 需要删除的仓库费用明细ID
     * @return 结果
     */
    @Override
    public int deleteTWarehousebillsfeesByIds(Long[] fIds) {
        return tWarehousebillsfeesMapper.deleteTWarehousebillsfeesByIds(fIds);
    }

    /**
     * 删除仓库费用明细信息
     *
     * @param fId 仓库费用明细ID
     * @return 结果
     */
    @Override
    public int deleteTWarehousebillsfeesById(Long fId) {
        return tWarehousebillsfeesMapper.deleteTWarehousebillsfeesById(fId);
    }

    /**
     * 查询报表
     *
     * @param tWarehousebillsfees
     * @return
     */
    @Override
    public List<FleetExcel> selectFleetExcelList(TWarehousebillsfees tWarehousebillsfees) {
        List<FleetExcel> fleetExcelList = new ArrayList<>();
        // 开始月份
        int startMonth = 1;
        // 结束月份
        int endMonth = 1;
        if (StringUtils.isNotEmpty(tWarehousebillsfees.getfYears())) {
            // 年份
            List<String> month = tWarehousebillsfees.getfMonth();
            if (StringUtils.isNotEmpty(month.get(0))) {
                startMonth = Integer.parseInt(month.get(0));
            }
            if (StringUtils.isNotEmpty(month.get(1))) {
                endMonth = Integer.parseInt(month.get(1));
            }
            if (endMonth < startMonth) {
                return null;
            }
            for (int i = startMonth; i <= endMonth; i++) {
                String firstDay = DateUtils.getFirstDay(Integer.parseInt(tWarehousebillsfees.getfYears()), i);
                String lastDay = DateUtils.getLastDay(Integer.parseInt(tWarehousebillsfees.getfYears()), i);
                month.set(0, firstDay);
                month.set(1, lastDay);
                tWarehousebillsfees.setfMonth(month);
                List<FleetExcel> fleetExcels = tWarehousebillsfeesMapper.selectFleetExcelList(tWarehousebillsfees);
                if (StringUtils.isNotEmpty(fleetExcels)) {
                    for (FleetExcel e : fleetExcels) {
                        fleetExcelList.add(e);
                    }
                    fleetExcelList.add(tWarehousebillsfeesMapper.selectFleetExcelMonthList(tWarehousebillsfees));
                }
            }
        }
        return fleetExcelList;
    }

    /**
     * 查询报表合计
     *
     * @param fleetExcelsList
     * @return
     */
    @Override
    public List<String> selectFleetExcel(List<FleetExcel> fleetExcelsList) {
        List<String> stringList = new ArrayList<>();
        if (StringUtils.isEmpty(fleetExcelsList)) {
            stringList.add("0");
            stringList.add("0");
            stringList.add("0");
            return stringList;
        }
        BigDecimal ccf = new BigDecimal(0);
        BigDecimal fAmount = new BigDecimal(0);
        BigDecimal totalAmount = new BigDecimal(0);
        for (FleetExcel f : fleetExcelsList) {
            if (StringUtils.isEmpty(f.getUserName())) {
                if (StringUtils.isNotEmpty(f.getCcf())) {
                    ccf = ccf.add(new BigDecimal(f.getCcf()));
                } else {
                    ccf = ccf.add(new BigDecimal(0));
                }
                if (StringUtils.isNotEmpty(f.getfAmount())) {
                    fAmount = fAmount.add(new BigDecimal(f.getfAmount()));
                } else {
                    fAmount = fAmount.add(new BigDecimal(0));
                }
                if (StringUtils.isNotEmpty(f.getTotalAmount())) {
                    totalAmount = totalAmount.add(new BigDecimal(f.getTotalAmount()));
                } else {
                    totalAmount = totalAmount.add(new BigDecimal(0));
                }
            }
        }
        stringList.add(ccf + "");
        stringList.add(fAmount + "");
        stringList.add(totalAmount + "");
        return stringList;
    }

    @Override
    public List<Map<String, Object>> accountsDue() {
        return tWarehousebillsfeesMapper.accountsDue();
    }

    @Override
    public List<QueryMenu> selectQueryMenuList(TWarehousebillsfees tWarehousebillsfees) {
        return tWarehousebillsfeesMapper.selectQueryMenuList(tWarehousebillsfees);
    }

    @Override
    public AjaxResult exportBillSubItemDetails(BillDetailsSubItem billDetailsSubItem) {
        // 创建 workbook，对应一个 excel 文件
        HSSFWorkbook wb = new HSSFWorkbook();
        // 在 workbook 中添加一个sheet，对应 excel 文档中的 sheet
        HSSFSheet sheet = wb.createSheet("分项明细");
        // 获取 cell 样式
        HSSFCellStyle cellTitleStyle = getCellStyle(wb,"center",true);
        HSSFCellStyle cellContentStyle = getCellStyle(wb,"center",true);
        // 创建标题，合并标题单元格
        // 行号
        int rowNum = 2;
        // 第一行
        HSSFRow first = sheet.createRow(rowNum++);
        String[] left = {"序号", "业务类型", "作业类型", "提单号", "货名", "客户", "件数", "重量", "体积", "入库时间","出库时间", "计算天数", "货物堆存费"};
        List<String> middle = tFeesMapper.selectTFeesNameList();
        String[] right = {"金额", "计划员", "计费时间", "结费时间", "仓库", "备注"};

        List<String> all = new ArrayList<>();
        Collections.addAll(all, left);
        all.addAll(middle);
        Collections.addAll(all, right);

        // 创建并获取大标题样式
        /*HSSFCellStyle cellBigTitleStyle = getCellStyle(wb,"center",false);
        CellRangeAddress cBigTitle = new CellRangeAddress(0,0,0,all.size()/4);
        setBigTitle("青岛大木仓配物流有限公司现场收费统计表（仓储业务）",0,sheet,cellBigTitleStyle,cBigTitle);
        setFont(cellBigTitleStyle,wb,"宋体",11,true);*/

        // 创建并获取统计范围时间样式
        HSSFCellStyle cellRangeTimeStyle = getCellStyle(wb,"center",false);
        CellRangeAddress cRangeTimeTitle = new CellRangeAddress(1,1,0,all.size()/9);
        setBigTitle("统计范围：" + billDetailsSubItem.getDateRange(),1,sheet,cellRangeTimeStyle,cRangeTimeTitle);
        setFont(cellRangeTimeStyle,wb,"宋体",11,false);

        int size = all.size();
        for (int i = 0; i < size; i++) {
            HSSFCell tempCell = first.createCell(i);
            if (i > 12 && i < size - 6) {
                tempCell.setCellValue(all.get(i) + "单价");
            } else {
                tempCell.setCellValue(all.get(i));
            }
            tempCell.setCellStyle(cellTitleStyle);
            // 设置第三行标题栏字体
            setFont(cellTitleStyle,wb,"宋体",11,true);
        }

        // 根据客户名称，发货方查询清单数据
        List<BillDetailsSubItem> list = tWarehousebillsfeesMapper.selectBillDetailsSubItem(billDetailsSubItem);
        if (list.size() < 1) {
            return AjaxResult.error("无数据，导出Excel失败");
        }

        int index = 1;
        for (BillDetailsSubItem bd : list) {
            HSSFRow tempRow = sheet.createRow(rowNum++);
            // 循环单元格填入数据
            for (int i = 0; i < size; i++) {
                HSSFCell temCell = tempRow.createCell(i);
                String cellValue = "";
                if (i == 0) {
                    // 序号
                    cellValue = StringUtils.objToStr(index++);
                } else if (i == 1) {
                    // 业务类型
                    cellValue = StringUtils.objToStr(bd.getfBilltype());
                } else if (i == 2) {
                    // 作业类型
                    cellValue = StringUtils.objToStr(bd.getTwlfBusinesstype());
                } else if (i == 3) {
                    // 提单号
                    cellValue = StringUtils.objToStr(bd.getfStatementno());
                } else if (i == 4) {
                    // 货名
                    cellValue = StringUtils.objToStr(bd.getTgfName());
                } else if (i == 5) {
                    // 客户
                    cellValue = StringUtils.objToStr(bd.getTcfName());
                } else if (i == 6) {
                    // 件数
                    cellValue = StringUtils.objToStr(bd.getfQty());
                } else if (i == 7) {
                    // 重量
                    cellValue = StringUtils.objToStr(bd.getfNetweight());
                } else if (i == 8) {
                    // 体积
                    cellValue = StringUtils.objToStr(bd.getfVolumn());
                } else if (i == 9) {
                    // 入库时间
                    cellValue = StringUtils.objToStr(bd.getfOriginalbilldate());
                } else if (i == 10) {
                    // 出库时间
                    cellValue = StringUtils.objToStr(bd.getfBsdate());
                } else if (i == 11) {
                    // 计费天数
                    cellValue = StringUtils.objToStr(bd.getfBillingdays());
                } else if (i == size - 6) {
                    // 金额
                    cellValue = StringUtils.objToStr(bd.getfAmount());
                } else if (i == size - 5) {
                    // 计划员
                    cellValue = StringUtils.objToStr(bd.getCreateBy());
                } else if (i == size - 4) {
                    // 计费时间
                    cellValue = StringUtils.objToStr(bd.getfChargedate());
                } else if (i == size - 3) {
                    // 结费时间
                    cellValue = StringUtils.objToStr(bd.getfStlamountdate());
                } else if (i == size - 2) {
                    // 仓库
                    cellValue = StringUtils.objToStr(bd.getFhName());
                } else if (i == size - 1) {
                    // 备注
                    cellValue = StringUtils.objToStr(bd.getRemark());
                }
                temCell.setCellValue(cellValue);
                temCell.setCellStyle(cellContentStyle);
                setFont(cellContentStyle,wb,"宋体",12,false);
            }
        }

        for (int i = 0; i < size; i++) {
            sheet.autoSizeColumn(i);
            sheet.setColumnWidth(i,sheet.getColumnWidth(i)*17/10);
        }

        // 导出 excel
        String fileName = "账单明细导出分项.xls";
        // 创建导出流
        try {
            OutputStream out = new FileOutputStream(getAbsoluteFile(fileName));
            wb.write(out);
            wb.close();
            out.close();
            return AjaxResult.success(fileName);
        } catch (Exception e) {
            e.printStackTrace();
            return AjaxResult.error("导出Excel失败");
        }
    }

    private String getAbsoluteFile(String fileName) {
        String downloadPath = RuoYiConfig.getDownloadPath() + fileName;
        File desc = new File(downloadPath);
        if (!desc.getParentFile().exists()) {
            desc.getParentFile().mkdirs();
        }
        return downloadPath;
    }

    /**
     * 封装大标题实现复用
     * @param title 标题
     * @param row 所在行
     * @param sheet sheet
     * @param cellStyle 样式
     * @param cellAddresses 合并行参数
     */
    public void setBigTitle(String title,int row,HSSFSheet sheet,HSSFCellStyle cellStyle,CellRangeAddress cellAddresses){
        // 合并参数
        sheet.addMergedRegion(cellAddresses);
        // 大标题部分
        HSSFRow bigTitleRow = sheet.createRow(row);
        HSSFCell cell = bigTitleRow.createCell(0);
        cell.setCellValue(title);
        cell.setCellStyle(cellStyle);
    }

    /**
     * 设置 excel 内内容字体
     * @param style 传入的已设置的 excel 样式
     * @param workbook 工作簿
     * @param fontName 字体名称，例如： "宋体"
     * @param fontSize 字体大小
     * @param isBold 是否加粗，true：加粗，false：不加粗
     */
    public void setFont(HSSFCellStyle style,HSSFWorkbook workbook,String fontName,int fontSize,boolean isBold){
        HSSFFont font = workbook.createFont();
        // 设置字体
        font.setFontName(fontName);
        // 是否加粗
        font.setBold(isBold);
        // 字体大小
        font.setFontHeightInPoints((short) fontSize);
        // 需要设置在谁上
        style.setFont(font);
    }

    /**
     * 获取并设置工作表 excel 样式
     * @param workbook 工作簿
     * @param position 位置参数：left-居左，right-居右，center-居中
     * @param showFrame 是否显示边框，true：显示，false：不显示
     * @return 已设置的 excel 样式
     */
    public HSSFCellStyle getCellStyle(HSSFWorkbook workbook,String position,boolean showFrame){
        // 创建标题的显示样式
        HSSFCellStyle headerStyle = workbook.createCellStyle();
        // 设置水平垂直居中+上下左右边框+边框是否显示
        setHeaderStyle(headerStyle,position,showFrame);
        // 返回
        return headerStyle;
    }

    /**
     * 封装边框以及水平+垂直居中+边框是否显示
     * @param headerStyle 样式
     * @param position 位置参数：left-居左，right-居右，center-居中
     * @param showFrame 是否显示边框，true：显示，false：不显示
     */
    public void setHeaderStyle(HSSFCellStyle headerStyle,String position,boolean showFrame){
        // 水平位置摆放
        switch (position) {
            case "left": // 居左
                headerStyle.setAlignment(HorizontalAlignment.LEFT);
                break;
            case "right": // 居右
                headerStyle.setAlignment(HorizontalAlignment.RIGHT);
                break;
            case "center": // 居中
                headerStyle.setAlignment(HorizontalAlignment.CENTER);
                break;
        }
        // 垂直居中
        headerStyle.setVerticalAlignment(VerticalAlignment.CENTER);
        if (showFrame) {
            // 上边框
            headerStyle.setBorderTop(BorderStyle.THIN);
            // 下边框
            headerStyle.setBorderBottom(BorderStyle.THIN);
            // 左边框
            headerStyle.setBorderLeft(BorderStyle.THIN);
            // 右边框
            headerStyle.setBorderRight(BorderStyle.THIN);
        }
    }
}
