$('#tutorial').on('click', function () {
  $(document).ready(async function () {
    const driver = new Driver({
      doneBtnText: 'Sair',
      closeBtnText: 'Fechar',
      nextBtnText: 'Próximo',
      prevBtnText: 'Anterior',
      allowClose: false
    })
    driver.defineSteps([
      {
        element: "#tutorial-step1",
        popover: {
          title: "Campos",
          description:
            "Aqui se encontram os campos essenciais para consultar e gravar as informações.",
          position: "bottom",
        },
      },
      {
        element: '#btnVoltar',
        popover: {
          title: 'Voltar',
          description: 'Aqui está o botão para voltar à consulta.',
          position: 'bottom'
        }
      },
      {
        element: '#btnGravar',
        popover: {
          title: 'Gravar',
          description: 'Aqui está o botão para gravar as informações.',
          position: 'bottom'
        }
      }
    ])
    driver.start()
  })
})

$(document).ready(async function () {
  const url = window.location.href
  const numeroEncoded = url.split('/')[url.split('/').length - 1]
  const chave = atob(numeroEncoded)

  if (chave && chave !== 'create') {
    carregarCadastro({ chave })
  } else {
    criarTabelaFornecedores({ data: [] })
    criarTabelaItens({ data: [] })
    criarTabelaMateriais({ data: [] })
    criarTabelaProdutos({ data: [] })
    criarTabelaServicos({ data: [] })
    setTimeout(() => {
      $('#tabelaFornecedores').DataTable().columns.adjust().draw(false)
      $('#tabelaItens').DataTable().columns.adjust().draw(false)
    }, 150)
  }

  $('#txtUsuario').val(getCookie('usuario'))

  const idsItensSolicitacaoSelecionados = new Set()

  $('#txtMaterial').autocompleta(
    1,
    `JSON={ "tabela":"MATERIAL", "camposSelect":["CODIGO CHAVE, DESCRICAO, UNIDADE, UNI_COM"], "where": [] }`,
    ['#txtUnidadeMaterial', '#txtUnidadeCompraMaterial'],
    ['UNIDADE', 'UNI_COM'],
    ['UNIDADE', 'UNI_COM'],
    () => setTimeout(
      () => adicionarFiltrosMaterialInformado({
        codigo: pegaChave('#txtMaterial'),
      }),
      150
    ),
    [true, true]
  )
  $('#btnMaterial').pesquisa_serverside(
    ['#txtMaterial', '#txtUnidadeMaterial', '#txtUnidadeCompraMaterial'],
    ['CODIGO', 'UNIDADE', 'UNI_COM'],
    ['DESCRICAO', 'UNIDADE', 'UNI_COM'],
    '{"tabela":"MATERIAL", "camposSelect":[ "CODIGO", "DESCRICAO", "UNIDADE", "UNI_COM" ], "where": null}',
    'Pesquisa Material',
    () => setTimeout(
      () => adicionarFiltrosMaterialInformado({
        codigo: pegaChave('#txtMaterial'),
      }),
      150
    ),
    [false, true, true]
  )
  $('#btnLimpaMaterial').on('click', function () {
    $('#txtMaterial').val('')
    $('#txtUnidadeMaterial').val('')
    $('#txtUnidadeCompraMaterial').val('')
    $('#txtCorMaterial').val('')
    $('.controleMaterial').prop('disabled', true)
  })

  const retornarFiltrosMaterialInformado = async ({ codigo }) => {
    const response = await requisicao('GET', `/sisplan/cotacao/v1/retornardadosmaterialinformado?`, `&CODIGO=${encodeURIComponent(codigo)}`, '', 3600000)
    const json = await response.json()

    if (json) {
      const { resultado, mensagem } = json
      if (mensagem?.codigo !== 200) {
        throw mensagem?.mensagem
      }
      const { cores } = resultado

      const filtroCores = await formataListas(cores?.toString()) ?? ''

      return {
        cores: filtroCores,
      }
    }
  }

  const adicionarFiltrosMaterialInformado = ({ codigo }) => {
    if (!codigo) return
    retornarFiltrosMaterialInformado({ codigo }).then(({ cores }) => {
      cores && componenteFiltro('cor', false, false, 'CorMaterial', [`COR IN (${cores})`])
      $('.controleMaterial').prop('disabled', false)
    })
  }

  componenteFiltro('solicitacao', false, false, 'SolicitacaoMaterial')
  componenteFiltro('centroCusto', false, false, 'CentroCustoMaterial')
  componenteFiltro('marca', false, false, 'MarcaMaterial')

  $('#txtProduto').autocompleta(
    1,
    `JSON={ "tabela":"PRODUTO", "camposSelect":["CODIGO CHAVE, DESCRICAO, UNIDADE"], "where": [] }`,
    ['#txtUnidadeProduto', '#txtUnidadeCompraProduto'],
    ['UNIDADE', 'UNIDADE'],
    ['UNIDADE', 'UNIDADE'],
    () => setTimeout(
      () => adicionarFiltrosProdutoInformado({
        codigo: pegaChave('#txtProduto'),
      }),
      150
    ),
    [true, true],
  )
  $('#btnProduto').pesquisa_serverside(
    ['#txtProduto', '#txtUnidadeProduto', '#txtUnidadeCompraProduto'],
    ['CODIGO', 'UNIDADE', 'UNIDADE'],
    ['DESCRICAO', 'UNIDADE', 'UNIDADE'],
    '{"tabela":"PRODUTO", "camposSelect":[ "CODIGO", "DESCRICAO", "UNIDADE" ], "where": null}',
    'Pesquisa Produto',
    () => setTimeout(
      () => adicionarFiltrosProdutoInformado({
        codigo: pegaChave('#txtProduto'),
      }),
      150
    ),
    [false, true, true],
  )
  $('#btnLimpaProduto').on('click', function () {
    $('#txtProduto').val('')
    $('#txtUnidadeProduto').val('')
    $('#txtUnidadeCompraProduto').val('')
    $('#txtCorProduto').val('')
    $('#txtTamanhoProduto').val('')
    $('.controleProduto').prop('disabled', true)
  })

  const retornarFiltrosProdutoInformado = async ({ codigo }) => {
    const response = await requisicao('GET', `/sisplan/cotacao/v1/retornardadosprodutoinformado?`, `&CODIGO=${encodeURIComponent(codigo)}`, '', 3600000)
    const json = await response.json()

    if (json) {
      const { resultado, mensagem } = json
      if (mensagem?.codigo !== 200) {
        throw mensagem?.mensagem
      }
      const { cores, tamanhos } = resultado

      const filtroCores = await formataListas(cores?.toString()) ?? ''
      const filtroTamanhos = await formataListas(tamanhos?.toString()) ?? ''

      return {
        cores: filtroCores,
        tamanhos: filtroTamanhos,
      }
    }
  }

  const adicionarFiltrosProdutoInformado = ({ codigo }) => {
    if (!codigo) return
    retornarFiltrosProdutoInformado({ codigo }).then(({ cores, tamanhos }) => {
      cores && componenteFiltro('cor', false, false, 'CorProduto', [`COR IN (${cores})`])
      tamanhos && componenteFiltro('tamanho2', false, false, 'TamanhoProduto', [`TAM IN (${tamanhos})`])
      $('.controleProduto').prop('disabled', false)
    })
  }

  componenteFiltro('solicitacao', false, false, 'SolicitacaoProduto')
  componenteFiltro('centroCusto', false, false, 'CentroCustoProduto')
  componenteFiltro('marca', false, false, 'MarcaProduto')

  $('#txtServico').autocompleta(1, `JSON={ "tabela":"SERVICO", "camposSelect":["CODIGO CHAVE, DESCRICAO, UNIDADE"], "where": [] }`, ['#txtUnidadeServico', '#txtUnidadeCompraServico'], ['UNIDADE', 'UNIDADE'], ['UNIDADE', 'UNIDADE'], undefined, [true, true])
  $('#btnServico').pesquisa_serverside(['#txtServico', '#txtUnidadeServico', '#txtUnidadeCompraServico'], ['CODIGO', 'UNIDADE', 'UNIDADE'], ['DESCRICAO', 'UNIDADE', 'UNIDADE'], '{"tabela":"SERVICO", "camposSelect":[ "CODIGO", "DESCRICAO", "UNIDADE" ], "where": null}', 'Pesquisa Serviço', undefined, [false, true, true])
  $('#btnLimpaServico').on('click', function () {
    $('#txtServico').val('')
    $('#txtUnidadeServico').val('')
    $('#txtUnidadeCompraServico').val('')
  })

  componenteFiltro('solicitacao', false, false, 'SolicitacaoServico')
  componenteFiltro('centroCusto', false, false, 'CentroCustoServico')

  $('.campoFloat').maskMoney({
    decimal: ".",
    thousands: "",
    precision: 5,
  })

  componenteFiltro('entidade', true, true, 'Fornecedor')

  componenteFiltro('marca', false, false, 'MarcaServico')

  componenteFiltro('funcionario', true, true, 'SolicitanteSolicitacoes')
  componenteFiltro('funcionario', true, true, 'CompradorSolicitacoes')
  componenteFiltro('tipo', true, true, 'TipoSolicitacoes')

  async function buscarDados({ chave }) {
    const response = await requisicao('GET', `/sisplan/cotacao/v1/retornardadoscadastro?`, `&CHAVE=${encodeURIComponent(chave)}`, '', 3600000)
    const json = await response.json()

    if (json) {
      const { resultado, mensagem } = json
      if (mensagem?.codigo !== 200) {
        throw mensagem?.mensagem
      }

      return resultado
    }
  }

  function carregarCadastro({ chave }) {
    buscarDados({ chave }).then(({
      numero,
      validade,
      fornecedores,
      ultimasCompras,
      observacaoFornecedor,
      usuario,
      itens,
    }) => {
      $('#txtNumero').val(numero)
      $('#txtValidade').val(validade?.split('T')?.[0])
      $('#txtObservacaoFornecedor').val(observacaoFornecedor)
      $('#txtUsuario').val(usuario)
      criarTabelaFornecedores({ data: fornecedores })
      criarTabelaItens({ data: itens })
      preencherUltimasCompras({ data: ultimasCompras })
      const materiais = []
      const produtos = []
      const servicos = []
      itens.forEach((item) => {
        switch (item.tipo) {
          case 'M':
            materiais.push(item)
            break
          case 'P':
            produtos.push(item)
            break
          case 'S':
            servicos.push(item)
            break
          default:
            break
        }
      })
      criarTabelaMateriais({ data: materiais })
      criarTabelaProdutos({ data: produtos })
      criarTabelaServicos({ data: servicos })
    })
  }

  function criarTabelaFornecedores({ data }) {
    if ($.fn.DataTable.isDataTable('#tabelaFornecedores')) {
      $('#tabelaFornecedores').DataTable().destroy()
      $('#tabelaFornecedores').empty()
    }

    const columns = [
      {
        data: 'codigo',
        title: 'Fornecedor',
        render: function (data) {
          return '<div style="text-align:start;"> ' +
            '    <button class="btn btn-info btn-sm dropdown-toggle btnVerificaOpcoes" id="tutorialTabela" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"> ' +
            '      ' + data + ' ' +
            '    </button> ' +
            '    <div class="dropdown-menu"> ' +
            '    <button class="dropdown-item" type="button" title="Excluir" id="btnExcluir">Excluir</button>  ' +
            '</div>'
        }
      },
      {
        data: 'nome',
        title: 'Nome',
      },
      {
        data: 'emailEnviado',
        title: 'E-mail enviado',
      },
      {
        data: 'numero',
        title: 'Número',
      },
    ]

    $('#tabelaFornecedores').DataTable({
      sort: false,
      paging: true,
      destroy: true,
      lengthChange: false,
      filter: false,
      info: false,
      ordering: false,
      sorting: false,
      order: false,
      autoWidth: true,
      data,
      columns,
      scrollX: true,
      scrollY: '245px',
    })
  }

  $('#tabelaFornecedores').on('click', '#btnExcluir', async function () {
    const datatable = $('#tabelaFornecedores').DataTable()
    const linha = $(this).parents('tr')
    const dados = datatable.row(linha).data()
    if (!dados) return
    excluirFornecedor({ codigo: dados.codigo, tabela: datatable, linha })
  })

  const excluirFornecedor = ({ tabela, codigo, linha }) => {
    tabela.row(linha).remove().draw(false)
  }

  function criarTabelaItens({ data }) {
    if ($.fn.DataTable.isDataTable('#tabelaItens')) {
      $('#tabelaItens').DataTable().destroy()
      $('#tabelaItens').empty()
    }

    const columns = [
      {
        data: 'id',
        title: 'Id',
        visible: false,
      },
      {
        data: 'codigo',
        title: 'Código',
      },
      {
        data: 'descricao',
        title: 'Descrição',
      },
      {
        data: 'unidade',
        title: 'Unidade',
      },
      {
        data: 'unidadeCompra',
        title: 'Unidade Compra',
      },
      {
        data: 'quantidade',
        title: 'Quantidade',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'cor',
        title: 'Cor',
      },
      {
        data: 'descricaoCor',
        title: 'Descrição Cor',
      },
      {
        data: 'tamanho',
        title: 'Tamanho',
        visible: false,
      },
      {
        data: 'tipo',
        title: 'Tipo',
        visible: false,
      },
      {
        data: 'especificacao',
        title: 'Especificação',
      },
      {
        data: 'numero',
        title: 'Número',
      },
      {
        data: 'marca',
        title: 'Marca',
      },
      {
        data: 'centroCusto',
        title: 'Centro de Custo',
      },
      {
        data: 'quantidadeCotada',
        title: 'Quantidade Cotada',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'comprador',
        title: 'Comprador',
      },
      {
        data: 'dataEntregaPrevista',
        title: 'Data Entrega Prevista',
        render(data) {
          return new Intl.DateTimeFormat('pt-BR').format(new Date(`${data.split('T')[0]} 23:59:59`))
        },
      },
    ]

    const table = $('#tabelaItens').DataTable({
      sort: false,
      paging: true,
      destroy: true,
      lengthChange: false,
      filter: false,
      info: false,
      ordering: false,
      sorting: false,
      order: false,
      autoWidth: true,
      data,
      columns,
      scrollX: true,
      scrollY: '200px',
      select: {
        style: 'single',
        toggleable: false,
      },
    })
    table.off('select')
    $('#tabelaItens').DataTable().row(':first').select()
    table.on('select', function (_e, _dt, type, indexes) {
      if (type === 'row') {
        const [data] = table.rows(indexes[0]).data().toArray()
        const { codigo, cor } = data
        retornarUltimasCompras({ codigo, cor })
      }
    })
  }

  const retornarUltimasCompras = ({ codigo, cor }) => {
    $.LoadingOverlay('show')
    requisicao(
      'GET',
      `/sisplan/cotacao/v1/retornarultimascompras?`,
      `&CODIGO=${encodeURIComponent(codigo)}&COR=${encodeURIComponent(cor)}`,
      '',
      3600000
    ).then(async (response) => {
      const json = await response.json()

      if (json) {
        const { resultado, mensagem } = json
        if (mensagem?.codigo !== 200) {
          throw mensagem?.mensagem
        }

        if (!resultado || !resultado.itens) preencherUltimasCompras({ data: [] })
        preencherUltimasCompras({ data: resultado.itens })
      }
    }).catch((error) => {
      console.error(error)
      msgErro('Ocorreu um erro ao buscar as últimas compras do item.')
    }).finally(() => $.LoadingOverlay('hide'))
  }

  function retornarBotaoOpcoes(data) {
    const retorno = '<div style="text-align:start;"> ' +
      '    <button class="btn btn-info btn-sm dropdown-toggle btnVerificaOpcoes" id="tutorialTabela" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"> ' +
      '      ' + data + ' ' +
      '    </button> ' +
      '    <div class="dropdown-menu"> ' +
      '    <button class="dropdown-item" type="button" title="Alterar" id="btnAlterar">Alterar</button>     ' +
      '    <button class="dropdown-item" type="button" title="Excluir" id="btnExcluir">Excluir</button>  ' +
      '</div>'
    return retorno
  }

  function criarTabelaMateriais({ data }) {
    if ($.fn.DataTable.isDataTable('#tabelaMateriais')) {
      $('#tabelaMateriais').DataTable().destroy()
      $('#tabelaMateriais').empty()
    }

    const columns = [
      {
        data: 'id',
        title: 'Id',
        visible: false,
      },
      {
        data: 'codigo',
        title: 'Código',
        render: function (data) {
          return retornarBotaoOpcoes(data)
        }
      },
      {
        data: 'descricao',
        title: 'Descrição',
      },
      {
        data: 'unidade',
        title: 'Unidade',
      },
      {
        data: 'unidadeCompra',
        title: 'Unidade Compra',
      },
      {
        data: 'quantidade',
        title: 'Quantidade',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'cor',
        title: 'Cor',
      },
      {
        data: 'descricaoCor',
        title: 'Descrição Cor',
      },
      {
        data: 'tamanho',
        title: 'Tamanho',
        visible: false,
      },
      {
        data: 'tipo',
        title: 'Tipo',
        visible: false,
      },
      {
        data: 'especificacao',
        title: 'Especificação',
      },
      {
        data: 'numero',
        title: 'Número',
      },
      {
        data: 'marca',
        title: 'Marca',
      },
      {
        data: 'centroCusto',
        title: 'Centro de Custo',
      },
      {
        data: 'quantidadeCotada',
        title: 'Quantidade Cotada',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'comprador',
        title: 'Comprador',
      },
      {
        data: 'dataEntregaPrevista',
        title: 'Data Entrega Prevista',
        render(data) {
          return new Intl.DateTimeFormat('pt-BR').format(new Date(`${data.split('T')[0]} 23:59:59`))
        },
      },
    ]

    $('#tabelaMateriais').DataTable({
      sort: false,
      paging: false,
      destroy: true,
      lengthChange: false,
      filter: false,
      info: false,
      ordering: false,
      sorting: false,
      order: false,
      autoWidth: true,
      data,
      columns,
      scrollX: true,
      scrollY: '210px',
    })
    atualizarQuantidadeTotalItem({ tipo: 'M', tabela: '#tabelaMateriais' })
  }

  function criarTabelaProdutos({ data }) {
    if ($.fn.DataTable.isDataTable('#tabelaProdutos')) {
      $('#tabelaProdutos').DataTable().destroy()
      $('#tabelaProdutos').empty()
    }

    const columns = [
      {
        data: 'id',
        title: 'Id',
        visible: false,
      },
      {
        data: 'codigo',
        title: 'Código',
        render: function (data) {
          return retornarBotaoOpcoes(data)
        }
      },
      {
        data: 'descricao',
        title: 'Descrição',
      },
      {
        data: 'unidade',
        title: 'Unidade',
      },
      {
        data: 'unidadeCompra',
        title: 'Unidade Compra',
      },
      {
        data: 'quantidade',
        title: 'Quantidade',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'cor',
        title: 'Cor',
      },
      {
        data: 'descricaoCor',
        title: 'Descrição Cor',
      },
      {
        data: 'tamanho',
        title: 'Tamanho',
      },
      {
        data: 'tipo',
        title: 'Tipo',
        visible: false,
      },
      {
        data: 'especificacao',
        title: 'Especificação',
      },
      {
        data: 'numero',
        title: 'Número',
      },
      {
        data: 'marca',
        title: 'Marca',
      },
      {
        data: 'centroCusto',
        title: 'Centro de Custo',
      },
      {
        data: 'quantidadeCotada',
        title: 'Quantidade Cotada',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'comprador',
        title: 'Comprador',
      },
      {
        data: 'dataEntregaPrevista',
        title: 'Data Entrega Prevista',
        render(data) {
          return new Intl.DateTimeFormat('pt-BR').format(new Date(`${data.split('T')[0]} 23:59:59`))
        },
      },
    ]

    $('#tabelaProdutos').DataTable({
      sort: false,
      paging: false,
      destroy: true,
      lengthChange: false,
      filter: false,
      info: false,
      ordering: false,
      sorting: false,
      order: false,
      autoWidth: true,
      data,
      columns,
      scrollX: true,
      scrollY: '210px',
    })
    atualizarQuantidadeTotalItem({ tipo: 'P', tabela: '#tabelaProdutos' })
  }

  function criarTabelaServicos({ data }) {
    if ($.fn.DataTable.isDataTable('#tabelaServicos')) {
      $('#tabelaServicos').DataTable().destroy()
      $('#tabelaServicos').empty()
    }

    const columns = [
      {
        data: 'id',
        title: 'Id',
        visible: false,
      },
      {
        data: 'codigo',
        title: 'Código',
        render: function (data) {
          return retornarBotaoOpcoes(data)
        }
      },
      {
        data: 'descricao',
        title: 'Descrição',
      },
      {
        data: 'unidade',
        title: 'Unidade',
      },
      {
        data: 'unidadeCompra',
        title: 'Unidade Compra',
      },
      {
        data: 'quantidade',
        title: 'Quantidade',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'cor',
        title: 'Cor',
        visible: false,
      },
      {
        data: 'descricaoCor',
        title: 'Descrição Cor',
        visible: false,
      },
      {
        data: 'tamanho',
        title: 'Tamanho',
        visible: false,
      },
      {
        data: 'tipo',
        title: 'Tipo',
        visible: false,
      },
      {
        data: 'especificacao',
        title: 'Especificação',
      },
      {
        data: 'numero',
        title: 'Número',
      },
      {
        data: 'marca',
        title: 'Marca',
      },
      {
        data: 'centroCusto',
        title: 'Centro de Custo',
      },
      {
        data: 'quantidadeCotada',
        title: 'Quantidade Cotada',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'comprador',
        title: 'Comprador',
      },
      {
        data: 'dataEntregaPrevista',
        title: 'Data Entrega Prevista',
        render(data) {
          return new Intl.DateTimeFormat('pt-BR').format(new Date(`${data.split('T')[0]} 23:59:59`))
        },
      },
    ]

    $('#tabelaServicos').DataTable({
      sort: false,
      paging: false,
      destroy: true,
      lengthChange: false,
      filter: false,
      info: false,
      ordering: false,
      sorting: false,
      order: false,
      autoWidth: true,
      data,
      columns,
      scrollX: true,
      scrollY: '210px',
    })
    atualizarQuantidadeTotalItem({ tipo: 'S', tabela: '#tabelaServicos' })
  }

  const preencherUltimasCompras = ({ data }) => {
    $('#containerUltimasCompras').empty()
    data?.forEach((item) => {
      $('#containerUltimasCompras').append(`
        <div style="border: 1px solid var(--font-color); border-radius: 4px; padding: 0.5rem;">
          <div class="col-12 flex">
            <span>Fornecedor: <span style="font-weight: 600">${item.fornecedor}</span></span>
          </div>
          <div class="flex flex-wrap">
            <div class="col-3">
              <span>Preço: <span style="font-weight: 600">${item.preco?.toLocaleString('pt-BR', { minimumFractionDigits: 4, maximumFractionDigits: 4 })}</span></span>
            </div>
            <div class="col-3">
              <span>Quantidade: <span style="font-weight: 600">${item.quantidade?.toLocaleString('pt-BR')}</span></span>
            </div>
            <div class="col-3">
              <span>Data: <span style="font-weight: 600">${new Intl.DateTimeFormat('pt-BR').format(new Date(`${item.data?.split('T')[0]} 23:59:59`))}</span></span>
            </div>
            <div class="col-3">
              <span>Preço Estoque: <span style="font-weight: 600">${item.precoEstoque?.toLocaleString('pt-BR', { minimumFractionDigits: 4, maximumFractionDigits: 4 })}</span></span>
            </div>
          </div>
        </div>
        `)
    })
  }


  function avancar() {
    const validator = $("#form").validate()
    const erros = validator.numberOfInvalids()
    if (erros) {
      return
    }

    currentFs = $('#fieldset1')
    const nextFs = $('#fieldset2')
    $('#payment').addClass('active')
    nextFs.show()
    currentFs.animate({
      opacity: 0,
    }, {
      step(now) {
        opacity = 1 - now
        currentFs.css({
          display: 'none',
          position: 'relative',
        })
        nextFs.css({
          opacity,
        })
      },
      duration: 600,
    })
  }

  $('#abaMaterial').on('click', () => setTimeout(
    () => $('#tabelaMateriais').DataTable().columns.adjust().draw(false),
    150,
  ))

  $('#abaProduto').on('click', () => setTimeout(
    () => $('#tabelaProdutos').DataTable().columns.adjust().draw(false),
    150,
  ))

  $('#abaServico').on('click', () => setTimeout(
    () => $('#tabelaServicos').DataTable().columns.adjust().draw(false),
    150,
  ))

  function voltar() {
    currentFs = $('#fieldset2')
    previousFs = $('#fieldset1')
    $('#payment').removeClass('active')
    $('#account').addClass('active')
    $('#progressbar li').eq($('fieldset').index(currentFs)).removeClass('active')
    previousFs.show()
    currentFs.animate({
      opacity: 0,
    }, {
      step(now) {
        opacity = 1 - now

        currentFs.css({
          display: "none",
          position: "relative",
        })
        previousFs.css({
          opacity,
        })
      },
      duration: 600,
    })
  }

  $('#form').validate({
    rules: {
      numero: {
        required: true,
      },
      validade: {
        required: true,
      }
    },
    messages: {
      numero: 'Número é obrigatório.',
      validade: 'Data de validade é obrigatória.',
    },
    errorElement: 'span',
    errorPlacement(error, element) {
      error.addClass('invalid-feedback')
      element.closest('.form-group').append(error)
    },
    highlight(element) {
      $(element).addClass('is-invalid')
    },
    unhighlight(element) {
      $(element).removeClass('is-invalid')
    },
    submitHandler: async (_form, event) => {
      event.preventDefault()
      const quantidadeFornecedores = $('#tabelaFornecedores').DataTable().data().toArray().length
      if (!quantidadeFornecedores || quantidadeFornecedores === 0) {
        msgErro('Nenhum fornecedor informado, impossível continuar.')
        return
      }
      avancar()
    }
  })

  $('#formMaterial').validate({
    rules: {
      material: {
        required: true,
      },
      cor: {
        required: true,
      },
      quantidade: {
        required: true,
      },
      entrega: {
        required: true,
      },
    },
    messages: {
      material: 'Material é obrigatório.',
      cor: 'Cor é obrigatória.',
      quantidade: 'Quantidade é obrigatória.',
      entrega: 'Data de entrega é obrigatória.',
    },
    errorElement: 'span',
    errorPlacement(error, element) {
      error.addClass('invalid-feedback')
      element.closest('.form-group').append(error)
    },
    highlight(element) {
      $(element).addClass('is-invalid')
    },
    unhighlight(element) {
      $(element).removeClass('is-invalid')
    },
    submitHandler: async (_form, event) => {
      event.preventDefault()
      const data = retornarDadosMaterial()
      const edicao = $('#tabelaMateriais tbody tr.selected').length > 0
      if (!validarAdicionarMaterialSolicitacao({
        codigo: data.codigo,
        cor: data.cor,
        entrega: data.dataEntregaPrevista,
      })) return
      if (!edicao)
        adicionarMaterial({ data })
      else
        editarMaterial({ data })
      limparCamposMaterial()
      $('#tabelaMateriais tbody tr').removeClass('selected')
      $('#txtMaterial').prop('disabled', false)
      $('#btnMaterial').prop('disabled', false)
      $('#btnLimpaMaterial').prop('disabled', false)
      $('.controleMaterial').prop('disabled', true)
    }
  })

  const retornarDadosMaterial = () => {
    const id = 0
    const codigo = pegaChave('#txtMaterial')
    const descricao = pegaDescricao('#txtMaterial')
    const unidade = $('#txtUnidadeMaterial').val()
    const unidadeCompra = $('#txtUnidadeCompraMaterial').val()
    const quantidade = parseFloat($('#txtQuantidadeMaterial').val())
    const cor = pegaChave('#txtCorMaterial')
    const descricaoCor = pegaDescricao('#txtCorMaterial')
    const tamanho = ''
    const tipo = 'M'
    const especificacao = $('#txtEspecificacaoMaterial').val()
    const numero = pegaChave('#txtSolicitacaoMaterial')
    const marca = pegaChave('#txtMarcaMaterial')
    const centroCusto = pegaChave('#txtCentroCustoMaterial')
    const quantidadeCotada = 0
    const comprador = ''
    const dataEntregaPrevista = $('#txtEntregaMaterial').val()

    return {
      id,
      codigo,
      descricao,
      unidade,
      unidadeCompra,
      quantidade,
      cor,
      descricaoCor,
      tamanho,
      tipo,
      especificacao,
      numero,
      marca,
      centroCusto,
      quantidadeCotada,
      comprador,
      dataEntregaPrevista,
    }
  }

  const adicionarMaterial = ({ data }) => {
    try {
      $('#tabelaMateriais').DataTable().row.add(data).draw(false)
      atualizarQuantidadeTotalItem({ tipo: 'M', tabela: '#tabelaMateriais' })
    } catch (error) {
      console.error(error)
      msgErro('Ocorreu um erro ao adicionar o item.')
    }
  }

  const limparCamposMaterial = () => $('#formMaterial input').val('')

  $('#tabelaMateriais').on('click', '#btnAlterar', async function () {
    $('#tabelaMateriais tbody tr').removeClass('selected')
    $(this).closest('tr').addClass('selected')
    const data = $('#tabelaMateriais').DataTable().row($(this).parents('tr')).data()
    if (!data) return
    preencherCamposMaterial({ data })
    $('#txtMaterial').prop('disabled', true)
    $('#btnMaterial').prop('disabled', true)
    $('#btnLimpaMaterial').prop('disabled', true)
    adicionarFiltrosMaterialInformado({ codigo: data.codigo })
  })

  const preencherCamposMaterial = ({ data }) => {
    insereValor('#txtMaterial', data.codigo, data.descricao)
    insereValor('#txtCorMaterial', data.cor, data.descricaoCor)
    insereValor('#txtSolicitacaoMaterial', data.numero, { tabela: 'SOL_COMPRA', campoBusca: 'SOLICITANTE', campoWhere: 'NUMERO', valorWhere: data.numero })
    insereValor('#txtCentroCustoMaterial', data.centroCusto, { tabela: 'CENTROCUSTO', campoBusca: 'DESCRICAO', campoWhere: 'CODIGO', valorWhere: data.centroCusto })
    insereValor('#txtMarcaMaterial', data.marca, { tabela: 'MARCA', campoBusca: 'DESCRICAO', campoWhere: 'CODIGO', valorWhere: data.marca })
    insereValor('#txtUnidadeMaterial', data.unidade)
    insereValor('#txtUnidadeCompraMaterial', data.unidadeCompra)
    insereValor('#txtQuantidadeMaterial', parseFloat(data.quantidade).toFixed(5))
    insereValor('#txtQuantidadeCotadaMaterial', parseFloat(data.quantidadeCotada).toFixed(5))
    insereValor('#txtEntregaMaterial', data.dataEntregaPrevista?.split('T')?.[0])
    insereValor('#txtEspecificacaoMaterial', data.especificacao)
  }

  const editarMaterial = ({ data }) => {
    try {
      const tabela = $('#tabelaMateriais').DataTable()
      const [linhaSelecionada] = $('#tabelaMateriais tbody tr.selected').toArray()
      if (!linhaSelecionada) return
      const dadosTabela = tabela.row(linhaSelecionada).data()

      const dadosAtualizados = {
        ...data,
        id: dadosTabela.id,
        quantidadeCotada: dadosTabela.quantidadeCotada,
        comprador: dadosTabela.comprador,
      }

      tabela.row(linhaSelecionada).data(dadosAtualizados).draw(false)
    } catch (error) {
      console.error(error)
      msgErro('Ocorreu um erro ao editar o item.')
    }
  }

  $('#formProduto').validate({
    rules: {
      produto: {
        required: true,
      },
      tamanho: {
        required: true,
      },
      cor: {
        required: true,
      },
      quantidade: {
        required: true,
      },
      entrega: {
        required: true,
      },
    },
    messages: {
      produto: 'Produto é obrigatório.',
      cor: 'Cor é obrigatória.',
      tamanho: 'Tamanho é obrigatório.',
      quantidade: 'Quantidade é obrigatória.',
      entrega: 'Data de entrega é obrigatória.',
    },
    errorElement: 'span',
    errorPlacement(error, element) {
      error.addClass('invalid-feedback')
      element.closest('.form-group').append(error)
    },
    highlight(element) {
      $(element).addClass('is-invalid')
    },
    unhighlight(element) {
      $(element).removeClass('is-invalid')
    },
    submitHandler: async (_form, event) => {
      event.preventDefault()
      const data = retornarDadosProduto()
      const edicao = $('#tabelaProdutos tbody tr.selected').length > 0
      if (!validarAdicionarProdutoSolicitacao({
        codigo: data.codigo,
        cor: data.cor,
        tamanho: data.tamanho,
        entrega: data.dataEntregaPrevista,
      })) return
      if (!edicao)
        adicionarProduto({ data })
      else
        editarProduto({ data })
      limparCamposProduto()
      $('#tabelaProdutos tbody tr').removeClass('selected')
      $('#txtProduto').prop('disabled', false)
      $('#btnProduto').prop('disabled', false)
      $('#btnLimpaProduto').prop('disabled', false)
      $('.controleProduto').prop('disabled', true)
    }
  })

  const retornarDadosProduto = () => {
    const id = 0
    const codigo = pegaChave('#txtProduto')
    const descricao = pegaDescricao('#txtProduto')
    const unidade = $('#txtUnidadeProduto').val()
    const unidadeCompra = $('#txtUnidadeCompraProduto').val()
    const quantidade = parseFloat($('#txtQuantidadeProduto').val())
    const cor = pegaChave('#txtCorProduto')
    const descricaoCor = pegaDescricao('#txtCorProduto')
    const tamanho = pegaChave('#txtTamanhoProduto')
    const tipo = 'P'
    const especificacao = $('#txtEspecificacaoProduto').val()
    const numero = pegaChave('#txtSolicitacaoProduto')
    const marca = pegaChave('#txtMarcaProduto')
    const centroCusto = pegaChave('#txtCentroCustoProduto')
    const quantidadeCotada = 0
    const comprador = ''
    const dataEntregaPrevista = $('#txtEntregaProduto').val()

    return {
      id,
      codigo,
      descricao,
      unidade,
      unidadeCompra,
      quantidade,
      cor,
      descricaoCor,
      tamanho,
      tipo,
      especificacao,
      numero,
      marca,
      centroCusto,
      quantidadeCotada,
      comprador,
      dataEntregaPrevista,
    }
  }

  const adicionarProduto = ({ data }) => {
    try {
      $('#tabelaProdutos').DataTable().row.add(data).draw(false)
      atualizarQuantidadeTotalItem({ tipo: 'P', tabela: '#tabelaProdutos' })
    } catch (error) {
      console.error(error)
      msgErro('Ocorreu um erro ao adicionar o item.')
    }
  }

  const limparCamposProduto = () => $('#formProduto input').val('')

  $('#tabelaProdutos').on('click', '#btnAlterar', async function () {
    $('#tabelaProdutos tbody tr').removeClass('selected')
    $(this).closest('tr').addClass('selected')
    const data = $('#tabelaProdutos').DataTable().row($(this).parents('tr')).data()
    if (!data) return
    preencherCamposProduto({ data })
    $('#txtProduto').prop('disabled', true)
    $('#btnProduto').prop('disabled', true)
    $('#btnLimpaProduto').prop('disabled', true)
    adicionarFiltrosProdutoInformado({ codigo: data.codigo })
  })

  const preencherCamposProduto = ({ data }) => {
    insereValor('#txtProduto', data.codigo, data.descricao)
    insereValor('#txtCorProduto', data.cor, data.descricaoCor)
    insereValor('#txtTamanhoProduto', data.tamanho, { tabela: 'TABTAM', campoBusca: 'ACRESCIMO', campoWhere: 'TAM', valorWhere: data.tamanho })
    insereValor('#txtSolicitacaoProduto', data.numero, { tabela: 'SOL_COMPRA', campoBusca: 'SOLICITANTE', campoWhere: 'NUMERO', valorWhere: data.numero })
    insereValor('#txtCentroCustoProduto', data.centroCusto, { tabela: 'CENTROCUSTO', campoBusca: 'DESCRICAO', campoWhere: 'CODIGO', valorWhere: data.centroCusto })
    insereValor('#txtMarcaProduto', data.marca, { tabela: 'MARCA', campoBusca: 'DESCRICAO', campoWhere: 'CODIGO', valorWhere: data.marca })
    insereValor('#txtUnidadeProduto', data.unidade)
    insereValor('#txtUnidadeCompraProduto', data.unidadeCompra)
    insereValor('#txtQuantidadeProduto', parseFloat(data.quantidade).toFixed(5))
    insereValor('#txtQuantidadeCotadaProduto', parseFloat(data.quantidadeCotada).toFixed(5))
    insereValor('#txtEntregaProduto', data.dataEntregaPrevista?.split('T')?.[0])
    insereValor('#txtEspecificacaoProduto', data.especificacao)
  }

  const editarProduto = ({ data }) => {
    try {
      const tabela = $('#tabelaProdutos').DataTable()
      const [linhaSelecionada] = $('#tabelaProdutos tbody tr.selected').toArray()
      if (!linhaSelecionada) return
      const dadosTabela = tabela.row(linhaSelecionada).data()

      const dadosAtualizados = {
        ...data,
        id: dadosTabela.id,
        quantidadeCotada: dadosTabela.quantidadeCotada,
        comprador: dadosTabela.comprador,
      }

      tabela.row(linhaSelecionada).data(dadosAtualizados).draw(false)
    } catch (error) {
      console.error(error)
      msgErro('Ocorreu um erro ao editar o item.')
    }
  }

  $('#formServico').validate({
    rules: {
      servico: {
        required: true,
      },
      quantidade: {
        required: true,
      },
      entrega: {
        required: true,
      },
    },
    messages: {
      produto: 'Produto é obrigatório.',
      quantidade: 'Quantidade é obrigatória.',
      entrega: 'Data de entrega é obrigatória.',
    },
    errorElement: 'span',
    errorPlacement(error, element) {
      error.addClass('invalid-feedback')
      element.closest('.form-group').append(error)
    },
    highlight(element) {
      $(element).addClass('is-invalid')
    },
    unhighlight(element) {
      $(element).removeClass('is-invalid')
    },
    submitHandler: async (_form, event) => {
      event.preventDefault()
      const data = retornarDadosServico()
      const edicao = $('#tabelaServicos tbody tr.selected').length > 0
      if (!validarAdicionarServicoSolicitacao({
        codigo: data.codigo,
        entrega: data.dataEntregaPrevista,
      })) return
      if (!edicao)
        adicionarServico({ data })
      else
        editarServico({ data })
      limparCamposServico()
      $('#tabelaServicos tbody tr').removeClass('selected')
      $('#txtServico').prop('disabled', false)
      $('#btnServico').prop('disabled', false)
      $('#btnLimpaServico').prop('disabled', false)
    }
  })

  const retornarDadosServico = () => {
    const id = 0
    const codigo = pegaChave('#txtServico')
    const descricao = pegaDescricao('#txtServico')
    const unidade = $('#txtUnidadeServico').val()
    const unidadeCompra = $('#txtUnidadeCompraServico').val()
    const quantidade = parseFloat($('#txtQuantidadeServico').val())
    const cor = ''
    const descricaoCor = ''
    const tamanho = ''
    const tipo = 'S'
    const especificacao = $('#txtEspecificacaoServico').val()
    const numero = pegaChave('#txtSolicitacaoServico')
    const marca = pegaChave('#txtMarcaServico')
    const centroCusto = pegaChave('#txtCentroCustoServico')
    const quantidadeCotada = 0
    const comprador = ''
    const dataEntregaPrevista = $('#txtEntregaServico').val()

    return {
      id,
      codigo,
      descricao,
      unidade,
      unidadeCompra,
      quantidade,
      cor,
      descricaoCor,
      tamanho,
      tipo,
      especificacao,
      numero,
      marca,
      centroCusto,
      quantidadeCotada,
      comprador,
      dataEntregaPrevista,
    }
  }

  const adicionarServico = ({ data }) => {
    try {
      $('#tabelaServicos').DataTable().row.add(data).draw(false)
      atualizarQuantidadeTotalItem({ tipo: 'S', tabela: '#tabelaServicos' })
    } catch (error) {
      console.error(error)
      msgErro('Ocorreu um erro ao adicionar o item.')
    }
  }

  const limparCamposServico = () => $('#formServico input').val('')

  $('#tabelaServicos').on('click', '#btnAlterar', async function () {
    $('#tabelaServicos tbody tr').removeClass('selected')
    $(this).closest('tr').addClass('selected')
    const data = $('#tabelaServicos').DataTable().row($(this).parents('tr')).data()
    if (!data) return
    preencherCamposServico({ data })
    $('#txtServico').prop('disabled', true)
    $('#btnServico').prop('disabled', true)
    $('#btnLimpaServico').prop('disabled', true)
  })

  const preencherCamposServico = ({ data }) => {
    insereValor('#txtServico', data.codigo, data.descricao)
    insereValor('#txtSolicitacaoServico', data.numero, { tabela: 'SOL_COMPRA', campoBusca: 'SOLICITANTE', campoWhere: 'NUMERO', valorWhere: data.numero })
    insereValor('#txtCentroCustoServico', data.centroCusto, { tabela: 'CENTROCUSTO', campoBusca: 'DESCRICAO', campoWhere: 'CODIGO', valorWhere: data.centroCusto })
    insereValor('#txtMarcaServico', data.marca, { tabela: 'MARCA', campoBusca: 'DESCRICAO', campoWhere: 'CODIGO', valorWhere: data.marca })
    insereValor('#txtUnidadeServico', data.unidade)
    insereValor('#txtUnidadeCompraServico', data.unidadeCompra)
    insereValor('#txtQuantidadeServico', parseFloat(data.quantidade).toFixed(5))
    insereValor('#txtQuantidadeCotadaServico', parseFloat(data.quantidadeCotada).toFixed(5))
    insereValor('#txtEntregaServico', data.dataEntregaPrevista?.split('T')?.[0])
    insereValor('#txtEspecificacaoServico', data.especificacao)
  }

  const editarServico = ({ data }) => {
    try {
      const tabela = $('#tabelaServicos').DataTable()
      const [linhaSelecionada] = $('#tabelaServicos tbody tr.selected').toArray()
      if (!linhaSelecionada) return
      const dadosTabela = tabela.row(linhaSelecionada).data()

      const dadosAtualizados = {
        ...data,
        id: dadosTabela.id,
        quantidadeCotada: dadosTabela.quantidadeCotada,
        comprador: dadosTabela.comprador,
      }

      tabela.row(linhaSelecionada).data(dadosAtualizados).draw(false)
    } catch (error) {
      console.error(error)
      msgErro('Ocorreu um erro ao editar o item.')
    }
  }

  $('#btnGravar').on('click', () => gravar())
  const retornarDadosGravar = () => {
    const numero = $('#txtNumero').val()
    const validade = $('#txtValidade').val()
    const usuario = $('#txtUsuario').val()
    const fornecedores = $('#tabelaFornecedores').DataTable().data().toArray()
    const materiais = $('#tabelaMateriais').DataTable().data().toArray()
    const produtos = $('#tabelaProdutos').DataTable().data().toArray()
    const servicos = $('#tabelaServicos').DataTable().data().toArray()
    const itens = [
      ...materiais,
      ...produtos,
      ...servicos,
    ]

    return {
      numero,
      validade,
      usuario,
      fornecedores,
      itens,
    }
  }

  const gravar = () => {
    $.LoadingOverlay('show')
    const dados = retornarDadosGravar()
    enviarDadosGravar({ dados })
      .then(() => {
        toastr.success("Dados gravados com sucesso!", "Confirmação", {
          toastClass: "alert",
          iconClasses: {
            error: "alert-error",
            info: "alert-info",
            success: "alert-success",
            warning: "alert-warning",
          },
          positionClass: "toast-top-center",
          progressBar: true,
          timeOut: 1000,
          fadeOut: 1000,
          onHidden() {
            window.location.href = `${BASE_URI}/cotacao`
          },
        }).css({
          "margin-top": "20%",
          width: "500px",
          "max-width": "500px",
        })
      })
      .catch((error) => {
        console.error(error)
        msgErro('Ocorreu um erro ao gravar os dados.')
      })
      .finally(() => $.LoadingOverlay('hide'))
  }

  const enviarDadosGravar = async ({ dados }) => {
    const response = await requisicao('POST', `/sisplan/cotacao/v1/gravar?`, '', JSON.stringify(dados), 3600000)
    const json = await response.json()

    if (json) {
      const { mensagem } = json
      if (mensagem?.codigo !== 200) {
        throw mensagem?.mensagem
      }
    }
  }

  $('#tabelaMateriais').on('click', '#btnExcluir', async function () {
    const datatable = $('#tabelaMateriais').DataTable()
    const linha = $(this).parents('tr')
    const dados = datatable.row(linha).data()
    if (!dados) return
    excluirItem({ tipo: 'M', tabela: datatable, linha })
  })

  $('#tabelaProdutos').on('click', '#btnExcluir', async function () {
    const datatable = $('#tabelaProdutos').DataTable()
    const linha = $(this).parents('tr')
    const dados = datatable.row(linha).data()
    if (!dados) return
    excluirItem({ tipo: 'P', tabela: datatable, linha })
  })

  $('#tabelaServicos').on('click', '#btnExcluir', async function () {
    const datatable = $('#tabelaServicos').DataTable()
    const linha = $(this).parents('tr')
    const dados = datatable.row(linha).data()
    if (!dados) return
    excluirItem({ tipo: 'S', tabela: datatable, linha })
  })

  const excluirItem = ({ tipo, tabela, linha }) => {
    tabela.row(linha).remove().draw(false)
    let tabelaAtualizar = ''
    switch (tipo) {
      case 'M':
        tabelaAtualizar = '#tabelaMateriais'
        break
      case 'P':
        tabelaAtualizar = '#tabelaProdutos'
        break
      case 'S':
        tabelaAtualizar = '#tabelaServicos'
        break
      default:
        break
    }
    if (!tabelaAtualizar) return
    atualizarQuantidadeTotalItem({ tipo, tabela: tabelaAtualizar })
  }

  $('#formFornecedor').validate({
    rules: {
      fornecedor: {
        required: true,
      },
    },
    messages: {
      fornecedor: 'Fornecedor é obrigatório.',
    },
    errorElement: 'span',
    errorPlacement(error, element) {
      error.addClass('invalid-feedback')
      element.closest('.form-group').append(error)
    },
    highlight(element) {
      $(element).addClass('is-invalid')
    },
    unhighlight(element) {
      $(element).removeClass('is-invalid')
    },
    submitHandler: async (_form, event) => {
      event.preventDefault()
      const filtros = await retornarFiltrosFornecedores()
      if (!validarFiltrosFornecedores({ filtros })) return
      adicionarFornecedor({ filtros })
    }
  })

  const adicionarFornecedor = async ({ filtros }) => {
    $.LoadingOverlay('show')
    retornarDadosFornecedor({ codigosFornecedores: filtros.fornecedores }).then(({ fornecedores }) => {
      if (!fornecedores) return
      const datatable = $('#tabelaFornecedores').DataTable()
      fornecedores.forEach((item) => datatable.row.add(item))
      datatable.draw(false)
      $('#txtFornecedor').empty().trigger('change')
    }).catch((error) => {
      console.error(error)
      msgErro('Ocorreu um erro ao adicionar o(s) fornecedor(es).')
    }).finally(() => $.LoadingOverlay('hide'))
  }

  const retornarFiltrosFornecedores = async () => {
    const datatable = $('#tabelaFornecedores').DataTable()
    const codigos = $('#txtFornecedor').val()
    const fornecedoresJaExistentes = datatable.data().toArray().map((item) => item.codigo)
    const fornecedoresNaoExistentes = codigos.filter((item) => !fornecedoresJaExistentes.includes(item))
    const filtroFornecedores = await formataListas(fornecedoresNaoExistentes.toString())

    return {
      fornecedores: filtroFornecedores,
    }
  }

  const validarFiltrosFornecedores = ({ filtros }) => {
    if (!filtros.fornecedores) {
      msgErro('Todos os fornecedores informados já existem para essa cotação, impossível continuar.')
      return false
    }
    return true
  }

  const retornarDadosFornecedor = async ({ codigosFornecedores }) => {
    const response = await requisicao('POST', `/sisplan/cotacao/v1/retornardadosfornecedor?`, '', JSON.stringify({ codigosFornecedores }), 3600000)
    const json = await response.json()

    if (json) {
      const { resultado, mensagem } = json
      if (mensagem?.codigo !== 200) {
        throw mensagem?.mensagem
      }

      return resultado
    }
  }

  function criarTabelaItensSolicitacoes({ filtros }) {
    if ($.fn.DataTable.isDataTable('#tabelaItensSolicitacoes')) {
      $('#tabelaItensSolicitacoes').DataTable().destroy()
      $('#tabelaItensSolicitacoes').empty()
    }

    if (!filtros) filtros = {}

    const columns = [
      {
        data: 'id',
        title: 'Id',
        visible: false,
      },
      {
        data: 'numero',
        title: 'Número',
      },
      {
        data: 'codigo',
        title: 'Código',
      },
      {
        data: 'descricao',
        title: 'Descrição',
      },
      {
        data: 'unidade',
        title: 'Unidade',
      },
      {
        data: 'unidadeCompra',
        title: 'Unidade Compra',
      },
      {
        data: 'cor',
        title: 'Cor',
      },
      {
        data: 'descricaoCor',
        title: 'Descrição Cor',
      },
      {
        data: 'tamanho',
        title: 'Tamanho',
        visible: false,
      },
      {
        data: 'quantidade',
        title: 'Quantidade',
        className: 'text-right',
        render: function (data) {
          if (!data) {
            return '0.00000'
          }
          return parseFloat(data).toFixed(5)
        }
      },
      {
        data: 'ordem',
        title: 'Ordem',
      },
      {
        data: 'especificacao',
        title: 'Especificação',
      },
      {
        data: 'marca',
        title: 'Marca',
      },
      {
        data: 'solicitante',
        title: 'Solicitante',
      },
      {
        data: 'nome',
        title: 'Nome',
      },
      {
        data: 'emissao',
        title: 'Emissão',
        render(data) {
          return new Intl.DateTimeFormat('pt-BR').format(new Date(`${data?.split('T')?.[0]} 23:59:59` ?? 0))
        },
      },
      {
        data: 'entrega',
        title: 'Entrega',
        render(data) {
          const date = `${data?.split('T')?.[0]} 23:59:59`
          return new Intl.DateTimeFormat('pt-BR').format(new Date(date ?? 0))
        },
      },
      {
        data: 'tipo',
        title: 'Tipo',
      },
      {
        data: 'comprador',
        title: 'Comprador',
      },
      {
        data: 'centroCusto',
        title: 'Centro de Custo',
      },
    ]

    $('#tabelaItensSolicitacoes').DataTable({
      sort: false,
      paging: true,
      destroy: true,
      lengthChange: false,
      filter: false,
      info: false,
      ordering: false,
      sorting: false,
      order: false,
      pageLength: 12,
      serverSide: true,
      ajax: {
        url: `${getCookie('protocolo')}://${getCookie('ip_api')}/sisplan/cotacao/v1/retornaritenssolicitacao`,
        type: "POST",
        headers: {
          'Authorization': getCookie('accessToken') ? 'Bearer ' + getCookie('accessToken') : '',
        },
        data: function (data) {
          const { start, length, draw } = data;
          return JSON.stringify({
            filtros,
            paginacao: {
              quantidadeMaximaRegistros: length,
              quantidadeRegistrosPular: start,
              contadorRequisicoes: draw,
            },
            empresa: getCookie('empresa'),
          })
        },
        cache: true,
        beforeSend: function () {
          $.LoadingOverlay('show')
        },
        complete: function () {
          $.LoadingOverlay('hide')
        },
        dataSrc: function (json) {
          if (!json || !json.data) {
            return []
          }
          return json.data
        }
      },
      autoWidth: true,
      columns,
      scrollX: true,
      scrollY: '375px',
    })
  }

  const retornarFiltrosItensSolicitacao = async () => {
    const solicitacaoDe = $('#txtSolicitacaoDeSolicitacoes').val()
    const solicitacaoAte = $('#txtSolicitacaoAteSolicitacoes').val()
    const emissaoDe = $('#txtEmissaoDeSolicitacoes').val()
    const emissaoAte = $('#txtEmissaoAteSolicitacoes').val()
    const entregaDe = $('#txtEntregaDeSolicitacoes').val()
    const entregaAte = $('#txtEntregaAteSolicitacoes').val()
    const tipoItem = $('#selectTipoItemSolicitacoes').val()
    const especificacao = $('#txtEspecificacaoSolicitacoes').val()
    const solicitante = await formataListas($('#txtSolicitanteSolicitacoes').val().toString())
    const comprador = await formataListas($('#txtCompradorSolicitacoes').val().toString())
    const tipo = await formataListas($('#txtTipoSolicitacoes').val().toString())
    const idsAdicionados = await formataListas([...idsItensSolicitacaoSelecionados].toString())

    return {
      solicitacaoDe,
      solicitacaoAte,
      emissaoDe,
      emissaoAte,
      entregaDe,
      entregaAte,
      tipoItem,
      especificacao,
      solicitante,
      comprador,
      tipo,
      idsAdicionados,
    }
  }

  $('#btnSolicitacoes').on('click', async () => {
    $('#modalSolicitacoes').modal('show')
    const filtros = await retornarFiltrosItensSolicitacao()
    criarTabelaItensSolicitacoes({ filtros })
  })

  $('#btnConsultarSolicitacoes').on('click', async () => {
    const filtros = await retornarFiltrosItensSolicitacao()
    criarTabelaItensSolicitacoes({ filtros })
    idsItensSolicitacaoSelecionados.clear()
  })

  $('#btnLimparFiltrosSolicitacoes').on('click', () => limparFiltrosSolicitacoes())

  const limparFiltrosSolicitacoes = () => {
    $('#txtSolicitacaoDeSolicitacoes').val('')
    $('#txtSolicitacaoAteSolicitacoes').val('')
    $('#txtEmissaoDeSolicitacoes').val('1200-01-01')
    $('#txtEmissaoAteSolicitacoes').val('2500-12-31')
    $('#txtEntregaDeSolicitacoes').val('1200-01-01')
    $('#txtEntregaAteSolicitacoes').val('2500-12-31')
    $('#selectTipoItemSolicitacoes').val('')
    $('#txtEspecificacaoSolicitacoes').val('')
    $('#txtSolicitanteSolicitacoes').empty().trigger('change')
    $('#txtCompradorSolicitacoes').empty().trigger('change')
    $('#txtTipoSolicitacoes').empty().trigger('change')
  }

  $('#tabelaItensSolicitacoes').on('dblclick', 'tr', function () {
    cotarItem({ row: $(this) })
  })

  const cotarItem = async ({ row }) => {
    const datatable = $('#tabelaItensSolicitacoes').DataTable()
    const data = datatable.row(row).data()
    if (!data || !data.id) return
    const { id, codigo, cor, tamanho, entrega, tipo } = data
    switch (tipo) {
      case 'M':
        {
          if (!validarAdicionarMaterialSolicitacao({ codigo, cor, entrega })) return
          const {
            ordem,
            solicitante,
            nome,
            emissao,
            entrega: r,
            ...dadosAdicionar
          } = data

          adicionarMaterial({
            data: {
              ...dadosAdicionar,
              id: 0,
              dataEntregaPrevista: data.entrega,
            }
          })
          break
        }
      case 'P':
        {
          if (!validarAdicionarProdutoSolicitacao({ codigo, cor, tamanho, entrega })) return
          const {
            ordem,
            solicitante,
            nome,
            emissao,
            entrega: r,
            ...dadosAdicionar
          } = data

          adicionarProduto({
            data: {
              ...dadosAdicionar,
              id: 0,
              dataEntregaPrevista: data.entrega,
            }
          })
          break
        }
      case 'S': {
        if (!validarAdicionarServicoSolicitacao({ codigo, entrega })) return
        const {
          ordem,
          solicitante,
          nome,
          emissao,
          entrega: r,
          ...dadosAdicionar
        } = data

        adicionarServico({
          data: {
            ...dadosAdicionar,
            id: 0,
            dataEntregaPrevista: data.entrega,
          }
        })
        break
      }
    }
    idsItensSolicitacaoSelecionados.add(id)
    const filtros = await retornarFiltrosItensSolicitacao()
    criarTabelaItensSolicitacoes({ filtros })
  }

  const validarAdicionarMaterialSolicitacao = ({ codigo, cor, entrega }) => {
    const tabela = $('#tabelaMateriais').DataTable()
    const [linhaSelecionada] = $('#tabelaMateriais tbody tr.selected').toArray()

    let material
    if (!linhaSelecionada) {
      material = tabela.data().toArray().some((item) => {
        const dataItemAdicionado = new Date(item.dataEntregaPrevista.split('T')?.[0])
        const dataItemAdicionar = new Date(entrega.split('T')?.[0])
        return item.codigo === codigo && item.cor === cor && dataItemAdicionado.getTime() === dataItemAdicionar.getTime()
      })
    } else {
      const dadosTabela = tabela.data().toArray().filter((_, index) => tabela.row(linhaSelecionada).index() !== index)
      material = dadosTabela.some((item) => {
        const dataItemAdicionado = new Date(item.dataEntregaPrevista.split('T')?.[0])
        const dataItemAdicionar = new Date(entrega.split('T')?.[0])
        return item.codigo === codigo && item.cor === cor && dataItemAdicionado.getTime() === dataItemAdicionar.getTime()
      })
    }

    if (material) {
      msgErro('Material selecionado já existe para essa cotação, impossível continuar.')
    }

    return !material
  }

  const validarAdicionarProdutoSolicitacao = ({ codigo, cor, tamanho, entrega }) => {
    const tabela = $('#tabelaProdutos').DataTable()
    const [linhaSelecionada] = $('#tabelaProdutos tbody tr.selected').toArray()

    let produto
    if (!linhaSelecionada) {
      produto = tabela.data().toArray().some((item) => {
        const dataItemAdicionado = new Date(item.dataEntregaPrevista.split('T')?.[0])
        const dataItemAdicionar = new Date(entrega.split('T')?.[0])
        return item.codigo === codigo && item.cor === cor && item.tamanho === tamanho && dataItemAdicionado.getTime() === dataItemAdicionar.getTime()
      })
    } else {
      const dadosTabela = tabela.data().toArray().filter((_, index) => tabela.row(linhaSelecionada).index() !== index)
      produto = dadosTabela.some((item) => {
        const dataItemAdicionado = new Date(item.dataEntregaPrevista.split('T')?.[0])
        const dataItemAdicionar = new Date(entrega.split('T')?.[0])
        return item.codigo === codigo && item.cor === cor && item.tamanho === tamanho && dataItemAdicionado.getTime() === dataItemAdicionar.getTime()
      })
    }

    if (produto) {
      msgErro('Produto selecionado já existe para essa cotação, impossível continuar.')
    }

    return !produto
  }

  const validarAdicionarServicoSolicitacao = ({ codigo, entrega }) => {
    const tabela = $('#tabelaServicos').DataTable()
    const [linhaSelecionada] = $('#tabelaServicos tbody tr.selected').toArray()

    let servico
    if (!linhaSelecionada) {
      servico = tabela.data().toArray().some((item) => {
        const dataItemAdicionado = new Date(item.dataEntregaPrevista.split('T')?.[0])
        const dataItemAdicionar = new Date(entrega.split('T')?.[0])
        return item.codigo === codigo && dataItemAdicionado.getTime() === dataItemAdicionar.getTime()
      })
    } else {
      const dadosTabela = tabela.data().toArray().filter((_, index) => tabela.row(linhaSelecionada).index() !== index)
      servico = dadosTabela.some((item) => {
        const dataItemAdicionado = new Date(item.dataEntregaPrevista.split('T')?.[0])
        const dataItemAdicionar = new Date(entrega.split('T')?.[0])
        return item.codigo === codigo && dataItemAdicionado.getTime() === dataItemAdicionar.getTime()
      })
    }

    if (servico) {
      msgErro('Serviço selecionado já existe para essa cotação, impossível continuar.')
    }

    return !servico
  }

  $('#modalSolicitacoes').on('show.bs.modal', () => {
    $('#tabelaMateriais tbody tr').removeClass('selected')
    $('#tabelaProdutos tbody tr').removeClass('selected')
    $('#tabelaServicos tbody tr').removeClass('selected')
    limparCamposMaterial()
    limparCamposProduto()
    limparCamposServico()
  })

  $('#modalSolicitacoes').on('hide.bs.modal', () => {
    idsItensSolicitacaoSelecionados.clear()
    limparFiltrosSolicitacoes()
  })

  function atualizarQuantidadeTotalItem({ tipo, tabela }) {
    let span = null
    switch (tipo) {
      case 'M':
        span = '#quantidadeMateriais'
        break
      case 'P':
        span = '#quantidadeProdutos'
        break
      case 'S':
        span = '#quantidadeServicos'
        break
      default:
        break
    }

    if (!span) return
    const quantidade = parseInt($(tabela)?.DataTable()?.rows()?.count())

    $(span).html(`(${quantidade ?? 0})`)
  }

  $('#btnVoltar2').on('click', function () {
    voltar()
  })

  $('#btnVoltar').on('click', function () {
    window.location.href = `${BASE_URI}/cotacao`
  })
})