{"id":13858182,"url":"https://github.com/moj-analytical-services/xltabr","last_synced_at":"2025-07-13T23:31:29.350Z","repository":{"id":84738873,"uuid":"94623674","full_name":"moj-analytical-services/xltabr","owner":"moj-analytical-services","description":"xltabr: An R package for writing formatted cross tabulations (contingency tables) to Excel using openxlsx","archived":true,"fork":false,"pushed_at":"2017-11-28T10:40:11.000Z","size":3291,"stargazers_count":33,"open_issues_count":8,"forks_count":6,"subscribers_count":41,"default_branch":"master","last_synced_at":"2024-11-22T16:39:16.158Z","etag":null,"topics":["contingency-table","cran","cross-tabulation","excel","excel-export","excelwriter","formatter","package","pivot-tables","r"],"latest_commit_sha":null,"homepage":"https://moj-analytical-services.github.io/xltabr/","language":"R","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/moj-analytical-services.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null}},"created_at":"2017-06-17T12:54:44.000Z","updated_at":"2024-10-23T09:16:49.000Z","dependencies_parsed_at":null,"dependency_job_id":"0d83f2f1-abc8-44f6-b42a-c82eb57944d1","html_url":"https://github.com/moj-analytical-services/xltabr","commit_stats":null,"previous_names":[],"tags_count":3,"template":false,"template_full_name":null,"purl":"pkg:github/moj-analytical-services/xltabr","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moj-analytical-services%2Fxltabr","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moj-analytical-services%2Fxltabr/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moj-analytical-services%2Fxltabr/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moj-analytical-services%2Fxltabr/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/moj-analytical-services","download_url":"https://codeload.github.com/moj-analytical-services/xltabr/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/moj-analytical-services%2Fxltabr/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":265220371,"owners_count":23729799,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["contingency-table","cran","cross-tabulation","excel","excel-export","excelwriter","formatter","package","pivot-tables","r"],"created_at":"2024-08-05T03:01:59.506Z","updated_at":"2025-07-13T23:31:24.340Z","avatar_url":"https://github.com/moj-analytical-services.png","language":"R","funding_links":[],"categories":["R"],"sub_categories":[],"readme":"[![Coverage Status](https://img.shields.io/codecov/c/github/moj-analytical-services/xltabr/master.svg)](https://codecov.io/github/moj-analytical-services/xltabr?branch=master) [![Build Status](https://travis-ci.org/moj-analytical-services/xltabr.svg?branch=dev)](https://travis-ci.org/moj-analytical-services/xltabr) [![Cran Status](http://www.r-pkg.org/badges/version/xltabr)](https://cran.r-project.org/web/packages/xltabr/index.html) [![Cran Downloads](https://cranlogs.r-pkg.org/badges/xltabr)](https://www.r-pkg.org/pkg/xltabr)\n\n**Warning: `xltabr` is in early development. Please raise an [issue](https://github.com/moj-analytical-services/xltabr/issues) if you find any bugs**\n\nIntroduction\n------------\n\n`xltabr` allows you to write formatted cross tabulations to Excel using [`openxlsx`](https://github.com/awalker89/openxlsx). It has been developed to help automate the process of publishing Official Statistics.\n\nThe package works best when the input dataframe is the output of a crosstabulation performed by `reshape2:dcast`. This allows the package to autorecognise various elements of the cross tabulation, which can be styled accordingly.\n\nFor example, given a crosstabulation `ct` produced by `reshape2`, the following code produces the table shown.\n\n``` r\ntitles = c(\"Breakdown of car statistics\", \"Cross tabulation of drive and age against type*\")\nfooters = \"*age as of January 2015\"\nwb \u003c- xltabr::auto_crosstab_to_wb(ct, titles = titles, footers = footers)\nopenxlsx::openXL(wb)\n```\n\n![image](vignettes/example_1.png?raw=true)\n\nThis readme provides a variety of examples of increasing complexity. It is based on a simulated dataset built into the package, which you can see [here](https://github.com/moj-analytical-services/xltabr/blob/master/inst/extdata/synthetic_data.csv).\n\nGetting started\n---------------\n\nMuch of `xltabr` utility comes from its ability to automatically format cross tabulations which have been produced by `reshape2:dcast`.\n\nThe package provides a core convenience function called `xltabr::auto_crosstab_to_xl`. This wraps more advanced functionality, at the cost of reducing flexibility.\n\nThe following code assumes you've read in the synthetic data as follows:\n\n``` r\n# Read in data \npath \u003c- system.file(\"extdata\", \"synthetic_data.csv\", package=\"xltabr\")\ndf \u003c- read.csv(path, stringsAsFactors = FALSE)\n```\n\n### Example 1: Simple cross tabulation to Excel\n\n``` r\n# Create a cross tabulation using reshape2\nct \u003c- reshape2::dcast(df, drive + age  ~ type, value.var= \"value\", margins=c(\"drive\", \"age\"), fun.aggregate = sum)\nct \u003c- dplyr::arrange(ct, -row_number())\n\n# Use the main convenience function from xltabr to output to excel\ntab \u003c- xltabr::auto_crosstab_to_wb(ct, return_tab = TRUE)  #wb is an openxlsx workbook object\nopenxlsx::openXL(tab$wb)\n```\n\n![image](vignettes/example_2.png?raw=true)\n\n### Example 2: Standard data frame to Excel\n\nThere is also a convenience function to write a standard data.frame to Excel:\n\n``` r\nwb \u003c- xltabr::auto_df_to_wb(mtcars)\nopenxlsx::openXL(wb)\n```\n\n![image](vignettes/example_3.png?raw=true)\n\n### Example 3: Add in titles and footers\n\n``` r\ntitles = c(\"Breakdown of car statistics\", \"Cross tabulation of drive and age against type*\")\nfooters = \"*age as of January 2015\"\nwb \u003c- xltabr::auto_crosstab_to_wb(ct, titles = titles, footers = footers)\nopenxlsx::openXL(wb)\n```\n\n![image](vignettes/example_1.png?raw=true)\n\n### Example 4: Supply custom styles\n\n``` r\npath \u003c- system.file(\"extdata\", \"styles_pub.xlsx\", package = \"xltabr\")\ncell_path \u003c- system.file(\"extdata\", \"style_to_excel_number_format_alt.csv\", package = \"xltabr\")\nxltabr::set_style_path(path)\nxltabr::set_cell_format_path(cell_path)\nwb \u003c- xltabr::auto_crosstab_to_wb(ct)\nopenxlsx::openXL(wb)\n```\n\n![image](vignettes/example_5.png?raw=true)\n\n### Example 5: Output more than one table\n\n``` r\n# Change back to default styles\nxltabr::set_style_path()\nxltabr::set_cell_format_path()\n\n# Create second crosstab\nct2 \u003c- reshape2::dcast(df, drive + age ~ colour, value.var= \"value\", margins=c(\"drive\", \"age\"), fun.aggregate = sum)\nct2 \u003c- dplyr::arrange(ct2, -row_number())\n\ntab \u003c- xltabr::auto_crosstab_to_wb(ct, titles = titles, footers = c(footers, \"\"), return_tab = TRUE)\n\ntitles2 = c(\"Table 2: More car statistics\", \"Cross tabulation of drive and age against colour*\")\nfooters2 = \"*age as of January 2015\"\nwb \u003c- xltabr::auto_crosstab_to_wb(ct2, titles = titles2, footers = footers2, insert_below_tab = tab)\nopenxlsx::openXL(wb)\n```\n\n![image](vignettes/example_4.png?raw=true)\n\n### Example 6: Output more than one table, with different styles\n\n``` r\ntab \u003c- xltabr::auto_crosstab_to_wb(ct, titles = titles, footers = c(footers, \"\"), return_tab = TRUE)\n\nxltabr::set_style_path(path)\nxltabr::set_cell_format_path(cell_path)\n\nwb \u003c- xltabr::auto_crosstab_to_wb(ct2, titles = titles2, footers = footers2, insert_below_tab = tab)\nopenxlsx::openXL(wb)\n\n# Change back to default styles\nxltabr::set_style_path()\nxltabr::set_cell_format_path()\n```\n\n![image](vignettes/example_6.png?raw=true)\n\n### Example 7: Auoindent off\n\n``` r\nct \u003c- reshape2::dcast(df, drive + age  ~ type, value.var= \"value\",  fun.aggregate = sum)\nwb \u003c- xltabr::auto_crosstab_to_wb(ct, titles = titles, footers = c(footers, \"\"), indent = FALSE, left_header_colnames = c(\"drive\", \"age\"))\nopenxlsx::openXL(wb)\n```\n\n![image](vignettes/example_7.png?raw=true)\n\n### auto\\_crosstab\\_to\\_wb options\n\nThe following provides a list of all the options you can provide to `auto_crosstab_to_wb`\n\n    ## Take a cross tabulation produced by 'reshape2::dcast' and output a formatted openxlsx wb object\n    ## \n    ## Description:\n    ## \n    ##      Take a cross tabulation produced by 'reshape2::dcast' and output a formatted openxlsx wb object\n    ## \n    ## Usage:\n    ## \n    ##      auto_crosstab_to_wb(df, auto_number_format = TRUE, top_headers = NULL,\n    ##        titles = NULL, footers = NULL, auto_open = FALSE, indent = TRUE,\n    ##        left_header_colnames = NULL, vertical_border = TRUE, return_tab = FALSE,\n    ##        auto_merge = TRUE, insert_below_tab = NULL, total_text = NULL,\n    ##        include_header_rows = TRUE, wb = NULL, ws_name = NULL,\n    ##        number_format_overrides = list(), fill_non_values_with = list(na = NULL,\n    ##        nan = NULL, inf = NULL, neg_inf = NULL), allcount_to_level_translate = NULL,\n    ##        left_header_col_widths = NULL, body_header_col_widths = NULL)\n    ##      \n    ## Arguments:\n    ## \n    ##       df: A data.frame.  The cross tabulation to convert to Excel\n    ## \n    ## auto_number_format: Whether to automatically detect number format\n    ## \n    ## top_headers: A list.  Custom top headers. See 'add_top_headers()'\n    ## \n    ##   titles: The title.  A character vector.  One element per row of title\n    ## \n    ##  footers: Table footers.  A character vector.  One element per row of footer.\n    ## \n    ## auto_open: Boolean. Automatically open Excel output.\n    ## \n    ##   indent: Automatically detect level of indentation of each row\n    ## \n    ## left_header_colnames: The names of the columns that you want to designate as left headers\n    ## \n    ## vertical_border: Boolean. Do you want a left border?\n    ## \n    ## return_tab: Boolean.  Return a tab object rather than a openxlsx workbook object\n    ## \n    ## auto_merge: Boolean.  Whether to merge cells in the title and footers to width of body\n    ## \n    ## insert_below_tab: A existing tab object.  If provided, this table will be written on the same sheet, below the provided tab.\n    ## \n    ## total_text: The text that is used for the 'grand total' of a cross tabulation\n    ## \n    ## include_header_rows: Boolean - whether to include or omit the header rows\n    ## \n    ##       wb: A existing openxlsx workbook.  If not provided, a new one will be created\n    ## \n    ##  ws_name: The name of the worksheet you want to write to\n    ## \n    ## number_format_overrides: e.g. list(\"colname1\" = \"currency1\") see auto_style_number_formatting\n    ## \n    ## fill_non_values_with: Manually specify a list of strings that will replace non numbers types NA, NaN, Inf and -Inf. e.g. list(na = '*', nan = '', inf = '-', neg_inf = '-'). Note: NaNs are not treated as NAs.\n    ## \n    ## allcount_to_level_translate: Manually specify how to translate summary levels into header formatting\n    ## \n    ## left_header_col_widths: Width of row header columns you wish to set in Excel column width units. If singular, value is applied to all row header columns. If a vector, vector must have length equal to the number of row headers in workbook. Use special case \"auto\" for\n    ##           automatic sizing. Default (NULL) leaves column widths unchanged.\n    ## \n    ## body_header_col_widths: Width of body header columns you wish to set in Excel column width units. If singular, value is applied to all body columns. If a vector, vector must have length equal to the number of body headers in workbook. Use special case \"auto\" for\n    ##           automatic sizing. Default (NULL) leaves column widths unchanged.\n    ## \n    ## Examples:\n    ## \n    ##      crosstab \u003c- read.csv(system.file(\"extdata\", \"example_crosstab.csv\", package=\"xltabr\"))\n    ##      wb \u003c- auto_crosstab_to_wb(crosstab)\n    ## \n\nAdvanced usage\n--------------\n\nThe simple examples above wrap lower-level functions. These functions can be used to customise the output in a number of ways.\n\nThe following example shows the range of functions available.\n\n``` r\ntab \u003c- xltabr::initialise() %\u003e%  #Options here for providing an existing workbook, changing worksheet name, and position of table in wb\n  xltabr::add_title(title_text) %\u003e% # Optional title_style_names allows user to specify formatting\n  xltabr::add_top_headers(h_list) %\u003e% # Optional row_style_names and col_style_names allows custom formatting\n  xltabr::add_body(df) %\u003e%  #Optional left_header_colnames, row_style_names, left_header_style_names col_style names\n  xltabr::add_footer(footer_text) %\u003e% # Optional footer_style_names\n  xltabr::auto_detect_left_headers() %\u003e% # Auto detect left headers through presence of keyword, default = '(all)'\n  xltabr::auto_detect_body_title_level() %\u003e% # Auto detect level of emphasis of each row in body, through presence of keyword\n  xltabr::auto_style_indent() %\u003e% # Consolidate all left headers into a single column, with indentation to signify emphasis level\n  xltabr::auto_merge_title_cells() %\u003e% # merge the cells in the title\n  xltabr::auto_merge_footer_cells() # merge the cells in the footer\n```\n\nThe convenience functions contain further examples of how to build up a tab. See [here](https://github.com/moj-analytical-services/xltabr/blob/dev/R/convenience.R).\n\nImplementation diagrams.\n------------------------\n\nSee [here](https://www.draw.io/?lightbox=1\u0026highlight=0000ff\u0026edit=_blank\u0026layers=1\u0026nav=1\u0026title=xltabr#Uhttps%3A%2F%2Fdrive.google.com%2Fa%2Fdigital.justice.gov.uk%2Fuc%3Fid%3D0BwYwuy7YhhdxY2hGQnVGNFN6QkE%26export%3Ddownload)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmoj-analytical-services%2Fxltabr","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmoj-analytical-services%2Fxltabr","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmoj-analytical-services%2Fxltabr/lists"}