use crate::cells::{page_of, push_identity, push_money};
use crate::error::FormsError;
use crate::map::{Schedule1Map, Schedule2Map, Schedule3Map};
use crate::pdf;
use crate::verify::{verify_flat, FlatPlacement};
use btctax_core::tax::packet::ReturnHeader;
use btctax_core::tax::printed::{Schedule1Lines, Schedule2Lines, Schedule3Lines};
use btctax_core::Usd;
const SCH_CLUSTERS: &[(f32, f32)] = &[(410.0, 482.0), (504.0, 576.0)];
const COL_MID: usize = 0;
const COL_AMOUNT: usize = 1;
pub fn fill_schedule_2_with_map(
lines: &Schedule2Lines,
header: &ReturnHeader,
map: &Schedule2Map,
) -> Result<Vec<u8>, FormsError> {
let mut writes: Vec<(String, pdf::FieldValue)> = Vec::new();
let mut placements: Vec<FlatPlacement> = Vec::new();
let plan: [Usd; 4] = [lines.line4, lines.line11, lines.line12, lines.line21];
let mut ord_on_page = [0u32; 2];
for (cell, value) in map.lines().iter().zip(plan) {
let page = page_of(cell.fields()[0]) as u32;
let ord = ord_on_page[page as usize];
ord_on_page[page as usize] += 1;
push_money(
&mut writes,
&mut placements,
cell,
value,
COL_AMOUNT,
Some((page, ord)),
);
}
let mut doc = pdf::load(pdf::schedule_2_pdf(map.year)?)?;
let blank_fields = pdf::collect_fields(&doc)?;
push_identity(
&mut writes,
&mut placements,
&map.identity,
&header.name_line,
&header.taxpayer.ssn,
&blank_fields,
)?;
let index = pdf::index(&blank_fields);
pdf::drop_xfa_and_set_needappearances(&mut doc)?;
pdf::apply_writes(&mut doc, &index, &writes)?;
pdf::strip_nondeterminism(&mut doc);
let bytes = pdf::save(&mut doc)?;
let check = pdf::load(&bytes)?;
let fields = pdf::collect_fields(&check)?;
verify_flat(&check, &fields, &placements, SCH_CLUSTERS)?;
Ok(bytes)
}
pub fn fill_schedule_3_with_map(
lines: &Schedule3Lines,
header: &ReturnHeader,
map: &Schedule3Map,
) -> Result<Vec<u8>, FormsError> {
let mut writes: Vec<(String, pdf::FieldValue)> = Vec::new();
let mut placements: Vec<FlatPlacement> = Vec::new();
let plan: [Usd; 5] = [
lines.line1,
lines.line8,
lines.line10,
lines.line11,
lines.line15,
];
for (ord, (cell, value)) in map.lines().iter().zip(plan).enumerate() {
push_money(
&mut writes,
&mut placements,
cell,
value,
COL_AMOUNT,
Some((0, ord as u32)),
);
}
let mut doc = pdf::load(pdf::schedule_3_pdf(map.year)?)?;
let blank_fields = pdf::collect_fields(&doc)?;
push_identity(
&mut writes,
&mut placements,
&map.identity,
&header.name_line,
&header.taxpayer.ssn,
&blank_fields,
)?;
let index = pdf::index(&blank_fields);
pdf::drop_xfa_and_set_needappearances(&mut doc)?;
pdf::apply_writes(&mut doc, &index, &writes)?;
pdf::strip_nondeterminism(&mut doc);
let bytes = pdf::save(&mut doc)?;
let check = pdf::load(&bytes)?;
let fields = pdf::collect_fields(&check)?;
verify_flat(&check, &fields, &placements, SCH_CLUSTERS)?;
Ok(bytes)
}
pub fn fill_schedule_1_with_map(
lines: &Schedule1Lines,
header: &ReturnHeader,
map: &Schedule1Map,
) -> Result<Vec<u8>, FormsError> {
let mut writes: Vec<(String, pdf::FieldValue)> = Vec::new();
let mut placements: Vec<FlatPlacement> = Vec::new();
let plan: [(Usd, usize); 10] = [
(lines.line1, COL_AMOUNT), (lines.line3, COL_AMOUNT), (lines.line7, COL_AMOUNT), (lines.line8v, COL_MID), (lines.line9, COL_AMOUNT), (lines.line10, COL_AMOUNT), (lines.line15, COL_AMOUNT), (lines.line18, COL_AMOUNT), (lines.line21, COL_AMOUNT), (lines.line26, COL_AMOUNT), ];
let mut ord_on_page = [0u32; 2];
for (cell, (value, col)) in map.lines().iter().zip(plan) {
let page = page_of(cell.fields()[0]) as u32;
let ord = ord_on_page[page as usize];
ord_on_page[page as usize] += 1;
push_money(
&mut writes,
&mut placements,
cell,
value,
col,
Some((page, ord)),
);
}
let mut doc = pdf::load(pdf::schedule_1_pdf(map.year)?)?;
let blank_fields = pdf::collect_fields(&doc)?;
push_identity(
&mut writes,
&mut placements,
&map.identity,
&header.name_line,
&header.taxpayer.ssn,
&blank_fields,
)?;
let index = pdf::index(&blank_fields);
pdf::drop_xfa_and_set_needappearances(&mut doc)?;
pdf::apply_writes(&mut doc, &index, &writes)?;
pdf::strip_nondeterminism(&mut doc);
let bytes = pdf::save(&mut doc)?;
let check = pdf::load(&bytes)?;
let fields = pdf::collect_fields(&check)?;
verify_flat(&check, &fields, &placements, SCH_CLUSTERS)?;
Ok(bytes)
}