Perkelkite lasteles is prasta atidaryto ataskaitos sablono ir sujungtas pavadinimas elgiasi kaip nuotekis. Jusu skaitote A1 ir gaunate "Quarterly Statement"; jusu skaitote B1 iki F1, kurios matomai sedi po tuo paciu baneriui, ir negaunate nieko. Irasyti reiksmen i C1, norėdami taisyti antraste, ir ji niekada neatrodo ekrane. Tinklelis neprarado jusu duomenu. Ji tiksliai daro tai, ka reiskia sujungimas: tiek XLS, tiek XLSX sujungtas staciakampis atvaizduoja vienos lasteles, virsutine-kairioji inkaro, turini ir traktuoja likusias kaip uzdengtą erdve, kurioje yra reiksmes, bet niekada jas nerodomas. Excel vartotojai absorbuoja tai per bandymus ir klaidas. Ataskaitu generatorius turi ji uzkoduoti kaip taisykle, nes generuojamame kode simptomasas yra tuscias regionas be isimties, kurią galima rasti. HotXLS, gimtasis Object Pascal biblioteka, skaitanti ir rasanti abu Excel formatus is Delphi ir C++Builder, atskleidzia sujungimo lentele pakankamai aieskiai, kad galetu programuoti pagal taisykle, o ne atraskit ji parama bilietej.
Viena reiksmė, vienas inkaro
Sujungimas yra rodymo instrukcija, uzslopinta ant tinklelio, kuris nekeicia formos. Kiekviena uzdengta lastele vis tiek egzistuoja faile kaip savo lizdas; sujungimo irasas tik nurodo vartotojui nupiesti inkaro turini per staciakampi. Tas skirtumas varo tris elgesius, vertus internalizuoti pries rasyti bet kuri isdestymo kodą. Skaitymas uzdengtoji lastele grazina jos paties issaugota reiksmen, kuri jusu sukurtam baneriui paprastai yra tuscia, todel bet koks kodas, tikrinantis sujungta antrasite, turi issprusti ir skaityti inkaro. Rasant i uzdengta lastele sekasi failo lygyje ir niekur neatsiranda, kas yra nematomos-antrastes spastinas nuo atidarymo. Ir atjungus regiona, atskleidzia, kas jame saugojosi visu laiku, todel klaidingas irasymas i uzdengta erdve tampa matoma defektu ta diena, kai kas nors panaikina sujungima.
XLSX puseje ta lentele yra pirmos klases objektas. Sheet.MergedCells nesha Add('A1:C1'), FindAt(Row, Col), DeleteAt ir Items, o kvietimas, kurio daznai siekiate, yra FindAt: perduokite ji bet kuriai koordinatei ir jis grazina sujungta regiona, apimanti ta lastele, arba nil, kai lastele stovi viena. Tas vienas paieska yra pagrindas abiem teisingam sujungimo tvarkymui pusems, saugiam skaitymui ir rasymo apsaugai, o abi parodytos toliau.
Du fasadai, du sujungimo idiomiai
HotXLS laiko klasikini BIFF8 .xls varikliu ir OOXML .xlsx varikliu kaip atskirų objekto modelius, ir jie skirtingai raso sujungima, nes skyla nuo skirtingu konvenciju. XLS fasadas seka Excel COM idioma: iimkite diapazona is dvieju argumentu indeksuotos savybes ir istatyti Merge su OleVariant, kurio reiksmė sprendzia geometrija, kuria gausite.
var
Book: IXLSWorkbook; // interface-counted: no manual Free
Sh: IXLSWorksheet;
begin
Book := TXLSWorkbook.Create;
Sh := Book.Sheets[1]; // XLS sheet collection is 1-based
Sh.Range['A1', 'F1'].Merge(False); // False = one merged block
Sh.Cells.Item[1, 1].Value := 'Quarterly Statement';
Sh.Range['A3', 'F4'].Merge(True); // True = merge across: one merge per row
Book.SaveAs('layout.xls');
end;
Argumentas Merge yra dalis, kurią zmones paklaidinami. Dvieju eiluciu diapazono metu Merge(True) sukuria du nepriklausomus vienos eilutes sujungimus, kas yra Excel "Merge Across" ir tiksliai tai, ko norite sujungtam antrascio juostai, kuri turi issaugoti eilutes atskirtas. Merge(False) sujungia visa staciakampi i viena bloka. Diapazonas taip pat pranesha MergeCells kaip busenos poziomi, grazina apimanti regiona per MergeArea ir isivangia Unmerge. XLSX fasadas atskleidzia tas pacias operacijas su skirtingais pavadinimais: Sheet.MergeCells(Row1, Col1, Row2, Col2) ima sveiku skaiciaus ribas, TXLSXRange.Merge priima atitikmeni Across varianta, o MergedCells kolekcija laiko rezultata.
Sabalonas, kuris auga su duomenimis
Tikras ataskaitos sabalonas nera fiksuotas tinklelis. Antraste ir sumos yra fiksuotos, taciau detaliu sekcija tarp ju istriprejo, kokia grazina uzklausą. Schema, kuri laikosi, palieka viena pilnai stilizuota detaliu eilute sabalonate, klonuoja ja vienai kiekvienam irasui, ir tada atidaro tarpa pries sumos bloka, kad viskas, kas yra inkaru zemiaus, slinktu zyn neprarasdama savo formatavimo.
Sheet.Range['A1:F1'].Merge;
Sheet.Cells[1, 1].Value := 'INVOICE #2026-0611'; // value goes to the anchor, A1
Sheet.RowHeight[1] := 28;
TitleFont := Book.Fonts.Add('Calibri', 16, True, False);
Sheet.Cells[1, 1].FontIndex := TitleFont + 1; // pool index 0-based, cell side 1-based
// row 5 is the styled detail template line
for I := 0 to ItemCount - 1 do
Sheet.CopyRange(5, 1, 5, 6, 6 + I, 1); // styles and formulas travel with it
// open a gap above the totals block; content below shifts down
Sheet.InsertRows(6 + ItemCount, 1);
Sheet.Range['A1:F1'].SetBorders(xlsxEdgeOutline, xlsxBorderMedium);
Dvi eilutes gauna antro zvilgsnio. Sriipto priskyrimas nesha perstumta vienetu, kuris tykiai kanda: Fonts.Add grazina 0 pagrinsto baseinu pozicija, o lastele saugo 1 pagrinsto sirifto nuoroda, kur 0 reiskia numatytaji sirIfta, todel praleidus + 1 niekas neiskelkia, tik stilizuoja jusu pavadinima netinkamu rasysenoje. Kita eilute yra CopyRange, kuris kartu su reiksmemis perkelia formatavima ir formules. Tai yra visa priezastis klonuoti ranka sudelius sabalone eilute, o ne atkurti jos isvaizda kode. Dizaineris valdo isvaizdą vieną karta, sablone; generatorius tik pildo duomenis i jos kopijas.
Tas perskyrimas toliau skalvuojamas, kai pakartotinai naudojamas isdestymas gyvena savo darbaknygeje, tarkime lapas antrascio ir apostrofų juostoms, bendrinamu tarp ataskaitu. CopyRangeTo atlieka ta pati klona tarp darbalakio ribu, imdamas tikslo lapu plius paskirties koordinates, todel generatorius gali laikyti vieną priesaikinI sabalone lapu ir stampuoti jo regionus i tiek isvesties lapu, kiek uzduotis reikalauja. Alternatyva, mutavimas sabalo vietoje ir bandymas ji atkurti veliau, yra dalykas, kuris veikia tol, kol vieną diena paleistas nutruksta viduryje.
Ką InsertRows perstumia ir ko ne
Augimo-sabalone schema veikia tik tada, nes XLSX InsertRows yra struktūrinis redagavimas, o ne lasteleiu mainas. Kai jis atidaro tarpa, perstumia sujungtus regionus, eiluciu auksciai, hipernuorodas, komentarus, saldytas juostas, automatinio filtro diapazonus, salyginius formatus, duomenu patvirtinimus, lenteles, apibreztus pavadinimus, vaizdo inkarus ir diagramu inkarus, esancius zemiaus isvesties taskas, o ne tik lasteleiu reiksmes. Tai leidzia sumos blokui atvykti i savo nauja eilute su sujungimais ir skaiciu formatais nesugadintais, o ne atvykti nusisunbus.
Du dokumentuoti apribojimai yra tie, kuriuos reikia projektuoti. Formules koregavimas yra ribojamas redaguojamo lapo: nuorodos to lapo viduje yra perrasytos, ir formule kitame lape, nurodanciam i perstumta zona, taip pat yra perrasyto, taciau koregavimas seka tik nuorodas, nukreiptas i redaguojama lapu, todel bet kuri perziuros darbaknyges nuorodu schema turetu buti pati audituota, o ne aklai patiketa. Antrasis apribojimas yra aisku, ir jis yra XLS puseje. Suvestines lenteles isgyvena atidarymo-issaugojimo ciklus kaip neapdoroti issaugoti irasai, ne kaip modeliuoti objektai, kuriuos HotXLS gali perkelti, todel eiluciu isvestis neperkelias suvestines lenteles ploto. Bet kuris sabalonas, kurį sukuriate .xls formatui, turetu nusodinti savo suvestines lenteles regionus gerokai nutolusi nuo bet kurios juostos, kuri auga.
Atsisakymas rasyt duomenis i isdestymo erdve
Sujungtos-lasteles nesekme, kuri is tikruju pasiekia gamyba, nera kosmetine. Ji yra strukturine: detaliu eilute nukrypsta i sujungta isdestymo juosta, jos reiksmes patenka i uzdengtas lasteles ir tampa nematomos, o stulpelio sumos tykiai nustoja atitikti tai, ka bet kas skaitantis lapu matomas. Kadangi FindAt atsako uzdengiancio-regiono klausima bet kuriai koordinatei, generatorius gali atsisakyti to rasimo ta akimirka, kai jis vyktų, o ne siusti ataskaitą, kuri tykiai sumažina.
// refuse to write detail data into a merged layout region
if Sheet.MergedCells.FindAt(Row, 1) <> nil then
raise Exception.CreateFmt('row %d overlaps a merged layout region', [Row]);
Sheet.Cells[Row, 1].Value := Detail.Description;
Ta pati ribo patikra priklauso bet kuriam, kur vartotojas veliau rusiuos arba filtruos isvestu. Diapazono su sujungimais viduje negali rusiuoti svariai, nes rusiavimas perstumia eilutes nepriklausomai, o sujungimas, apimantis eilutes, neturi vienos eilutes, su kuria keliaut; Excel atsako klaida arba sugadinta isdestymu. Disciplina, issauganti ataskaitas teisingas, yra geografine. Apribokite sujungimus pavadinimo juostoms, skyriaus dalintuvams ir parasu blokams ir laikykite tabelio vidurini lapo plokcia. Sabalo ataskaitu generavimo straipsnis pletoja si isdestymo-pries-duomenis perskyrima i pilna ankstyvo-pagrindu darbo eigą, o salyginio formatavimo ir daznojo teksto straipsnis apima to plokscio duomenu juostos stilizavima.
Kaip sujungimai sumazeja iseinant
Sujungimas yra darbaknyges koncepcija, ir kiekvienas teksto orientuotas eksporto formatas ja gerbia skirtingam laipsnI. Zinat tris elgesius is anksto taupoma KS cikla. HTML eksportas atkuria sujungimus iste, isskirdamas colspan ir rowspan ant vienos lenteles, todel narstykleje pagristos ataskaitos issaugo juostota isvaizdą. RTF eksportas visai nestumia stulpeliu: inkaro tekstas nusistato savo lasteleje, o likusi sujungimo plotis iseinamas kaip tuseios lasteles, kas palieka platu pavadinima vizualiai nustumto kaireje teksto tvarkytuve. CSV neturi sujungimo koncepcijos, todel inkaro reiksmė uzsima viena lauka ir kiekviena uzdengta lastele issenama kaip tuscias laukas. Issavada darbaknygei, kuri taip pat maitina ribotus eksportus, yra laikyti viska svarbu uz sujungtos geometrijos; CSV, TSV ir HTML eksporto straipsnis eina per kiekvieną formata isamiai.
Vienas paguodimas tiems, kurie sveria tai pries failo dydi: sujungimai beveik nieko nekainuoja ataskaitu mastele. Sujungimo lentele yra maziuke greta lasteleiu duomenu, o uzdengtos lasteles skaitymas vis tiek eina per FindAt, o ne skenavima. Nasumas spaudimas didelems darbaknygems ateina is kitur, daugiausia stiliu-baseino augimo ir atminties, kuria saugo issaugojimo kelias, o dideles darbaknyges nasumas straipsnis tai sprendzia tiesiai. Abu sujungimo API, struktūrines redagavimo operacijos ir sabalo demo pristatomi su HotXLS Component.