# ooxml - ECMA-376 Office Open XML File Formats

## Project Overview

Pure Tcl extension for ECMA-376 Office Open XML: reads and writes `.xlsx` spreadsheets (Excel 2007+) and creates `.docx` word processing documents. Version 1.13.
Developed by Alexander Schoepe, with contributions by Rolf Ade, Harald Oehlmann and Miguel Bañón. The docx subsystem was developed by Rolf Ade.
Repository hosted on Fossil at https://fossil.sowaswie.de/ooxml (not Git).

## Tech Stack

- **Language:** Tcl 8.6.7+
- **Dependencies:** tdom >= 0.9.0 (the docx writer requires tdom >= 0.9.6). Reading xlsx/docx uses a built-in zip reader based on Tcl's core `zlib` command — no external package needed; Tcl 9 `zipfs`, tcllib `zipfile::decode` or tclvfs `vfs::zip >= 1.0.4` serve only as fallbacks for archives the built-in reader cannot handle (ZIP64, encrypted)
- **Build system:** TEA (Tcl Extension Architecture) via autoconf
- **Documentation:** Pandoc (Markdown -> HTML/man)

## Project Structure

- `ooxml.tcl` — xlsx source (package `ooxml`): all xlsx procs and OO methods, plus the shared zip read/write layer (`::ooxml::Zip*`)
- `ooxml-docx.tcl` / `ooxml-docx-lib.tcl` / `ooxml-docx-math.tcl` — docx writer (packages `ooxml::docx` and `ooxml::docx::lib`, both versioned separately, currently 0.6); the math file holds the OMML methods
- `pkgIndex.tcl.in` — Tcl package index template (`pkgIndex.tcl` is generated by configure)
- `configure.ac` / `Makefile.in` — TEA build configuration; `Makefile`, `pkgIndex.tcl` and `manifest.txt` are regenerated automatically when their sources change
- `doc/ooxml.md` — xlsx reference (Pandoc markdown, complete command/method reference)
- `doc/ooxml-docx.md` — docx reference; `doc/ooxml-docx-dev.md` — developer notes
- `examples/` — `xlsx-*.tcl` and `docx-example*.tcl` example scripts, each annotated with the features it covers
- `tests/` — tcltest suite (28 `.test` files, `xlsx-*` and `docx-*`, ~570 tests + fixtures), entry point `tests/all.tcl`
- `tools/` — Helper scripts; see `tools/BUILD-PACKAGE.md` for the release workflow, `tools/mkversion.tcl` (build info), `tools/archive.sh` (packaging), `tools/createTypeCode.tcl` (XSD enum -> Tcl type check procs)
- `claude/skills/ooxml/SKILL.md` — Claude skill covering both subsystems; keep in sync with API changes
- `uv/` — HTML download templates and locally built release artifacts (not versioned)
- `manifest` / `manifest.uuid` — Fossil SCM manifest (requires `fossil settings manifest on`)

## Key API

xlsx (package `ooxml`):
- `::ooxml::xl_sheets file` — List sheets in an xlsx file
- `::ooxml::xl_read file ?args?` — Read xlsx into a Tcl array
- `::ooxml::xl_write new ?args?` — Create spreadsheet object with methods: `numberformat`, `font`, `fill`, `border`, `style`, `worksheet`, `column`, `row`, `cell`, `autofilter`, `freeze`, `printarea`, `merge`, `rowheight`, `pageSetup`, `pageMargins`, `view`, `presetstyles`, `presetsheets`, `write`
- `::ooxml::tablelist_to_xl` — Export Tk tablelist widget to xlsx
- Helpers: `arrayDeleteSheet`, `RowColumnToString`, `StringToRowColumn`, `Column`, `CalcColumnWidth`, `Default`

docx (package `ooxml::docx`):
- `::ooxml::docx::docx new ?options? ?template.docx?` — Create document object; methods for paragraphs, character/paragraph styles, tables, images, headers/footers, footnotes/endnotes, comments, fields, hyperlinks/bookmarks, numbering, textboxes, OMML math, settings, plus power tools `appendTo`, `addXML`, `replace`, `import`, `xmlparts`, `selectNodes`/`xpath`

## Build, Test & Release

```sh
./configure
make test        # Run tcltest suite
make install     # Install to Tcl lib path (respects ./configure --prefix)
make doc         # Generate HTML + man pages for both references (requires pandoc)
make release     # Build the download packages into uv/ (resolves all prerequisites)
make publish     # Upload the packages to the Fossil unversioned space (fossil uv)
```

Release workflow: see `tools/BUILD-PACKAGE.md`. Version bump = two places: `AC_INIT` in `configure.ac` and `package provide ooxml` in `ooxml.tcl` (the docx subpackage versions live in `ooxml-docx.tcl`, `ooxml-docx-lib.tcl` and `pkgIndex.tcl.in`). Write an `ANNOUNCE` (bilingual EN/DE, changes since the previous release tag from the Fossil timeline).

## Fossil Specifics

- Check-ins: short English commit texts; tickets referenced as `[ticket-id]`, check-ins as `[checkin-id]` (auto-linked)
- Wiki pages (Markdown mimetype): `ooxml` (start page), `man-xlsx` (from `doc/ooxml.md`, strip the Pandoc `%` title line), `man-docx` (from `doc/ooxml-docx.md`), `examples`, `tools` — update via `fossil wiki commit <page> <file> -M markdown`, then `fossil sync` (wiki commits do not reliably autosync)
- Tickets: `fossil ticket show/history/change`; append comments with `+comment` using the `<hr /><i>alex added on <UTC> UTC:</i><br />` header convention
- Release artifacts live in the unversioned space (`fossil uv add <file> --as <plainname>`, `fossil uv sync`); keep only the current version's packages there

## Conventions

- Indices (row, column, sheet) are zero-based throughout the API
- Colors accept named colors, RGB/ARGB hex, or numeric indices 0-65
- Cell references use Excel-style notation (e.g., "A1") convertible via `RowColumnToString`/`StringToRowColumn`
- xlsx changes go into `ooxml.tcl`, docx changes into the `ooxml-docx*.tcl` files
- docx option values are type checked; type check procs for XSD enums are generated with `tools/createTypeCode.tcl`
- After API changes: update `doc/ooxml.md` / `doc/ooxml-docx.md`, the wiki pages and `claude/skills/ooxml/SKILL.md`
- BSD 3-clause license
