diff --git a/.github/workflows/build-msvs2022.yml b/.github/workflows/build-msvs2022.yml index d4e7cdf7..4dedf96e 100644 --- a/.github/workflows/build-msvs2022.yml +++ b/.github/workflows/build-msvs2022.yml @@ -10,7 +10,6 @@ on: - '.github/workflows/build-online-docs.yml' - 'build/vcpkg/**' - 'docs/**' - - 'util/**' - 'ReadMe.md' pull_request: branches: @@ -21,7 +20,6 @@ on: - '.github/workflows/build-online-docs.yml' - 'build/vcpkg/**' - 'docs/**' - - 'util/**' - 'ReadMe.md' workflow_dispatch: diff --git a/.github/workflows/build-msvs2026-wxmaster.yml b/.github/workflows/build-msvs2026-wxmaster.yml index 93ebc868..49a69cd5 100644 --- a/.github/workflows/build-msvs2026-wxmaster.yml +++ b/.github/workflows/build-msvs2026-wxmaster.yml @@ -10,7 +10,6 @@ on: - '.github/workflows/build-online-docs.yml' - 'build/vcpkg/**' - 'docs/**' - - 'util/**' - 'ReadMe.md' pull_request: branches: @@ -21,7 +20,6 @@ on: - '.github/workflows/build-online-docs.yml' - 'build/vcpkg/**' - 'docs/**' - - 'util/**' - 'ReadMe.md' workflow_dispatch: diff --git a/.github/workflows/build-msys2.yml b/.github/workflows/build-msys2.yml index 917636e7..d72cd4b6 100644 --- a/.github/workflows/build-msys2.yml +++ b/.github/workflows/build-msys2.yml @@ -10,7 +10,6 @@ on: - '.github/workflows/build-online-docs.yml' - 'build/vcpkg/**' - 'docs/**' - - 'util/**' - 'ReadMe.md' pull_request: branches: @@ -21,7 +20,6 @@ on: - '.github/workflows/build-online-docs.yml' - 'build/vcpkg/**' - 'docs/**' - - 'util/**' - 'ReadMe.md' workflow_dispatch: diff --git a/docs/changelog.md b/docs/changelog.md index e685c3d9..7bf2a7a4 100644 --- a/docs/changelog.md +++ b/docs/changelog.md @@ -2,9 +2,66 @@ Changes that can break building existing code are marked **[breaks build]**, changes that alter the behavior of existing code are marked **[behavior change]**. -The changes in versions 2.1, 2.2, 2.3, 2.4, and 2.5, as well as this changelog, were made by +The changes in versions 2.1, 2.2, 2.3, 2.4, 2.5, and 2.6, as well as this changelog, were made by Claude Opus 5.5 (Anthropic) under the direction of PB. +## 2.6.0 - 2026-10-25 + +### General + +- **[breaks build]** The library names now contain version 2.6, e.g. + *wxAutoExcel26* instead of *wxAutoExcel25*, so build scripts referring to + the library by name must be updated. + +### Added + +- `wxExcelSeries::ErrorBar()` overloads taking the amounts as `wxExcelRange` + or `wxVariant`, as custom error bars need a range, an array, or a string + with an array constant or a reference. +- `wxExcelChartFillFormat GetFill()` of the chart elements with the Fill + property: `wxExcelChartArea`, `wxExcelPlotArea`, `wxExcelChartTitle`, + `wxExcelAxisTitle`, `wxExcelDisplayUnitLabel`, `wxExcelLegend`, + `wxExcelLegendKey`, `wxExcelSeries`, `wxExcelPoint`, `wxExcelDataLabel`, + `wxExcelDataLabels`, `wxExcelFloor`, `wxExcelWalls`, `wxExcelUpBars`, and + `wxExcelDownBars`, as `wxExcelChartFillFormat` and + `wxExcelChartColorFormat` could not be obtained. Also + `wxExcelChartColorFormat::SetSchemeColor()`. +- `wxExcelGradientStops` and `wxExcelGradientStop`, and + `wxExcelFillFormat::GetGradientStops()`, which was commented out. +- `wxExcelWorkbook::GetIconSets()` without an argument, returning the + `wxExcelIconSets` collection, which could not be obtained. +- `wxExcelAllowEditRange::SetRange()`. +- `wxExcelListColumn::GetListDataFormat()`, as `wxExcelListDataFormat` could + not be obtained. +- `xl3Symbols2`, `xl3Stars`, `xl3Triangles`, `xl5Boxes`, and `xlCustomSet` + enumerators of `XlIconSet`. + +### Fixed wrappers + +- `wxExcelSeries::ErrorBar()` returned false even when it succeeded. +- **[breaks build]** `wxExcelWorksheetView::GetSheet()` always failed, as it + obtained the worksheet as a string. It now returns `wxExcelWorksheet`. +- **[breaks build]** `wxExcelIconSetCondition::GetIconSet()` and + `SetIconSet()` used `wxExcelIconSets` instead of `wxExcelIconSet`, so the + methods of the returned object failed or returned icons as icon sets. +- **[breaks build]** `wxExcelWorkbook::GetIconSets(XlIconSet)` returned + `wxExcelIconSets` instead of `wxExcelIconSet`. +- **[breaks build]** `wxExcelChart::FullSeriesCollection()` returned + `wxExcelSeriesCollection` instead of `wxExcelFullSeriesCollection`, which + also contains the filtered series. +- **[behavior change]** The values of the `XlIconSet` enumerators from + `xl4Arrows` on were off by one, as they were taken from the VBA + documentation, which omits `xl3Symbols2`, so they selected a different + icon set than named. +- **[behavior change]** `wxExcelRange::ApplyNames()` did not pass the names + to Excel, so all the names were applied instead of the given ones, and + passed False as IgnoreRelativeAbsolute by default instead of leaving Excel + use its default, which is True. +- **[breaks build]** `wxExcelOLEObjects::Add()` had the height as the third + argument instead of the last one and no top, so the position of the added + object could not be given. The arguments are now in the order of Excel, + as in `wxExcelShapes::AddOLEObject()`. + ## 2.5.1 - 2026-10-24 ### General diff --git a/docs/doxygen/Doxyfile b/docs/doxygen/Doxyfile index 250d11f0..a709b8e3 100644 --- a/docs/doxygen/Doxyfile +++ b/docs/doxygen/Doxyfile @@ -38,7 +38,7 @@ PROJECT_NAME = wxAutoExcel # could be handy for archiving the generated documentation or if some version # control system is used. -PROJECT_NUMBER = 2.5.1 +PROJECT_NUMBER = 2.6.0 # Using the PROJECT_BRIEF tag one can provide an optional one line description # for a project that appears at the top of each page and should give viewer a diff --git a/docs/install.md b/docs/install.md index 1ec1efc8..2f775ab0 100644 --- a/docs/install.md +++ b/docs/install.md @@ -90,13 +90,13 @@ wxWidgets dependency transitively, so wxWidgets does not need to be repeated in # ..... find_package(wxWidgets REQUIRED COMPONENTS core base) - find_package(wxAutoExcel 2.5 REQUIRED CONFIG) + find_package(wxAutoExcel 2.6 REQUIRED CONFIG) # ..... target_link_libraries(${PROJECT_NAME} PRIVATE wxAutoExcel::wxAutoExcel) The version is optional. A package of wxAutoExcel is used only for the same major and -minor version, e.g. version 2.5 is found for `find_package(wxAutoExcel 2.5)` but not for -`find_package(wxAutoExcel 2.4)`, as the versions are not compatible. +minor version, e.g. version 2.6 is found for `find_package(wxAutoExcel 2.6)` but not for +`find_package(wxAutoExcel 2.5)`, as the versions are not compatible. If you did not install wxAutoExcel to a location known to CMake, you may need to tell CMake where to find it. There are many ways to do that, perhaps the easiest one may be setting CMake variable `wxAutoExcel_ROOT` @@ -132,7 +132,7 @@ For example, your application CMakeLists.txt may look like this FetchContent_Declare( wxAutoExcel GIT_REPOSITORY https://github.com/PBfordev/wxAutoExcel - GIT_TAG v2.5.1 # or the tag of another version + GIT_TAG v2.6.0 # or the tag of another version ) # maybe set some of wxAutoExcel_BUILD options here.... FetchContent_MakeAvailable(wxAutoExcel) diff --git a/include/wx/wxAutoExcel.h b/include/wx/wxAutoExcel.h index 4dbb99eb..15222c12 100644 --- a/include/wx/wxAutoExcel.h +++ b/include/wx/wxAutoExcel.h @@ -80,6 +80,7 @@ #include "wx/wxAutoExcelConnectorFormat.h" #include "wx/wxAutoExcelControlFormat.h" #include "wx/wxAutoExcelFillFormat.h" +#include "wx/wxAutoExcelGradientStops.h" #include "wx/wxAutoExcelGlowFormat.h" #include "wx/wxAutoExcelLineFormat.h" #include "wx/wxAutoExcelLinkFormat.h" diff --git a/include/wx/wxAutoExcelAllowEditRanges.h b/include/wx/wxAutoExcelAllowEditRanges.h index 27f277a5..f67d34f2 100644 --- a/include/wx/wxAutoExcelAllowEditRanges.h +++ b/include/wx/wxAutoExcelAllowEditRanges.h @@ -52,6 +52,13 @@ class WXDLLIMPEXP_WXAUTOEXCEL wxExcelAllowEditRange : public wxExcelObject */ wxExcelRange GetRange(); + /** + Sets the range of cells that can be edited on a protected worksheet. + + [Excel VBA documentation for AllowEditRange.Range](https://learn.microsoft.com/en-us/office/vba/api/excel.alloweditrange.range) + */ + void SetRange(const wxExcelRange& range); + /** Returns the title of the range of cells that can edited on a protected sheet. diff --git a/include/wx/wxAutoExcelAxisTitle.h b/include/wx/wxAutoExcelAxisTitle.h index f658899f..4a05e20e 100644 --- a/include/wx/wxAutoExcelAxisTitle.h +++ b/include/wx/wxAutoExcelAxisTitle.h @@ -77,6 +77,13 @@ namespace wxAutoExcel { */ wxExcelCharacters GetCharacters(long start = 1, long* length = NULL); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for AxisTitle.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.axistitle.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelChart.h b/include/wx/wxAutoExcelChart.h index e7c11b3d..06d8f8c1 100644 --- a/include/wx/wxAutoExcelChart.h +++ b/include/wx/wxAutoExcelChart.h @@ -158,11 +158,11 @@ namespace wxAutoExcel { //@{ /** - Returns an object that represents either a single series (a Series object) or a collection of all the series (a SeriesCollection collection) in the chart or chart group. + Returns an object that represents either a single series (a Series object) or a collection of all the series (a FullSeriesCollection collection) in the chart, including the filtered ones. Since Excel 2013. [MSDN documentation for Chart.FullSeriesCollection](https://learn.microsoft.com/en-us/office/vba/api/excel.chart.fullseriescollection). */ - wxExcelSeriesCollection FullSeriesCollection(); + wxExcelFullSeriesCollection FullSeriesCollection(); wxExcelSeries FullSeriesCollection(long index); //@} diff --git a/include/wx/wxAutoExcelChartArea.h b/include/wx/wxAutoExcelChartArea.h index d04f882a..f475f6d8 100644 --- a/include/wx/wxAutoExcelChartArea.h +++ b/include/wx/wxAutoExcelChartArea.h @@ -75,6 +75,13 @@ namespace wxAutoExcel { */ void SetAutoScaleFont(bool autoScaleFont); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for ChartArea.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.chartarea.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object Since Excel 2007. diff --git a/include/wx/wxAutoExcelChartColorFormat.h b/include/wx/wxAutoExcelChartColorFormat.h index d9cb6fcd..bff560cc 100644 --- a/include/wx/wxAutoExcelChartColorFormat.h +++ b/include/wx/wxAutoExcelChartColorFormat.h @@ -39,6 +39,13 @@ namespace wxAutoExcel { */ long GetSchemeColor(); + /** + Sets the color of a Color object, as an index in the current color scheme. + + [MSDN documentation for ChartColorFormat.SchemeColor](https://learn.microsoft.com/en-us/previous-versions/office/developer/office-2007/bb148845%28v=office.12%29). + */ + void SetSchemeColor(long schemeColor); + /** Returns a Long value that that represents the color format type. diff --git a/include/wx/wxAutoExcelChartTitle.h b/include/wx/wxAutoExcelChartTitle.h index cf90c908..b634c050 100644 --- a/include/wx/wxAutoExcelChartTitle.h +++ b/include/wx/wxAutoExcelChartTitle.h @@ -76,6 +76,13 @@ namespace wxAutoExcel { */ wxExcelCharacters GetCharacters(long start = 1, long* length = NULL); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for ChartTitle.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.charttitle.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelDataLabels.h b/include/wx/wxAutoExcelDataLabels.h index d4456f17..7c9b66cf 100644 --- a/include/wx/wxAutoExcelDataLabels.h +++ b/include/wx/wxAutoExcelDataLabels.h @@ -92,6 +92,13 @@ namespace wxAutoExcel { */ wxExcelCharacters GetCharacters(long start = 1, long* length = NULL); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for DataLabel.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.datalabel.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. @@ -479,6 +486,13 @@ namespace wxAutoExcel { */ long GetCount(); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for DataLabels.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.datalabels.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelDisplayUnitLabel.h b/include/wx/wxAutoExcelDisplayUnitLabel.h index bb14a12f..37e0525a 100644 --- a/include/wx/wxAutoExcelDisplayUnitLabel.h +++ b/include/wx/wxAutoExcelDisplayUnitLabel.h @@ -76,6 +76,13 @@ namespace wxAutoExcel { */ wxExcelCharacters GetCharacters(long start = 1, long* length = NULL); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for DisplayUnitLabel.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.displayunitlabel.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelDownBars.h b/include/wx/wxAutoExcelDownBars.h index 32a674b3..5796f151 100644 --- a/include/wx/wxAutoExcelDownBars.h +++ b/include/wx/wxAutoExcelDownBars.h @@ -40,6 +40,13 @@ namespace wxAutoExcel { // ***** PROPERTIES ***** + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for DownBars.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.downbars.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelFillFormat.h b/include/wx/wxAutoExcelFillFormat.h index c7314743..82a93c4a 100644 --- a/include/wx/wxAutoExcelFillFormat.h +++ b/include/wx/wxAutoExcelFillFormat.h @@ -113,11 +113,11 @@ namespace wxAutoExcel { double GetGradientDegree(); /** - Since Excel 2007. + Returns the GradientStops collection of the stops of a gradient fill. Since Excel 2007. [MSDN documentation for FillFormat.GradientStops](https://learn.microsoft.com/en-us/office/vba/api/excel.fillformat.gradientstops). */ - // wxExcelGradientStops GetGradientStops(); + wxExcelGradientStops GetGradientStops(); /** Returns the gradient style for the specified fill. Read-only MsoGradientStyle. diff --git a/include/wx/wxAutoExcelFloor.h b/include/wx/wxAutoExcelFloor.h index dc572a3c..4cf8dab3 100644 --- a/include/wx/wxAutoExcelFloor.h +++ b/include/wx/wxAutoExcelFloor.h @@ -48,6 +48,13 @@ namespace wxAutoExcel { // ***** PROPERTIES ***** + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for Floor.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.floor.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelGradientStops.h b/include/wx/wxAutoExcelGradientStops.h new file mode 100644 index 00000000..5f730738 --- /dev/null +++ b/include/wx/wxAutoExcelGradientStops.h @@ -0,0 +1,146 @@ +///////////////////////////////////////////////////////////////////////////// +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + + +#ifndef _WXAUTOEXCEL_GRADIENTSTOPS_H +#define _WXAUTOEXCEL_GRADIENTSTOPS_H + +#include "wx/wxAutoExcel_defs.h" + +#if WXAUTOEXCEL_USE_SHAPES || WXAUTOEXCEL_USE_CHARTS + +#include "wx/wxAutoExcel_object.h" + +class WXDLLIMPEXP_FWD_CORE wxColour; + +namespace wxAutoExcel { + + /** + @brief Represents Microsoft Office GradientStop object, one of the stops of a gradient fill. + */ + class WXDLLIMPEXP_WXAUTOEXCEL wxExcelGradientStop : public wxExcelObject + { + public: + // ***** PROPERTIES ***** + + /** + Returns a ColorFormat object that represents the color of the gradient stop. + + [MSDN documentation for GradientStop.Color](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstop.color). + */ + wxExcelColorFormat GetColor(); + + /** + Returns the position of the stop within the gradient, from 0 to 1. + + [MSDN documentation for GradientStop.Position](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstop.position). + */ + double GetPosition(); + + /** + Sets the position of the stop within the gradient, from 0 to 1. + + [MSDN documentation for GradientStop.Position](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstop.position). + */ + void SetPosition(double position); + + /** + Returns the opacity of the stop color, from 0 (opaque) to 1 (clear). + + [MSDN documentation for GradientStop.Transparency](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstop.transparency). + */ + double GetTransparency(); + + /** + Sets the opacity of the stop color, from 0 (opaque) to 1 (clear). + + [MSDN documentation for GradientStop.Transparency](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstop.transparency). + */ + void SetTransparency(double transparency); + + /** + Returns "GradientStop". + */ + virtual wxString GetAutoExcelObjectName_() const { return wxS("GradientStop"); } + }; + + + /** + @brief Represents Microsoft Office GradientStops collection, the stops of a gradient fill. + */ + class WXDLLIMPEXP_WXAUTOEXCEL wxExcelGradientStops : public wxExcelObject + { + public: + // ***** METHODS ***** + + /** + Removes the gradient stop at @a index, or the last one when @a index is -1. + + [MSDN documentation for GradientStops.Delete](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstops.delete). + */ + void Delete(long index = -1); + + /** + Adds a stop of @a color at @a position, from 0 to 1, with the given @a transparency, + at @a index of the stops, or after the last one when @a index is -1. + + [MSDN documentation for GradientStops.Insert](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstops.insert). + */ + void Insert(const wxColour& color, double position, double transparency = 0, long index = -1); + + /** + Like Insert(), also setting the @a brightness of the stop, from -1 (darkest) to 1 (lightest). + + [MSDN documentation for GradientStops.Insert2](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstops.insert2). + */ + void Insert2(const wxColour& color, double position, double transparency = 0, long index = -1, + double brightness = 0); + + // ***** PROPERTIES ***** + + /** + Returns the number of gradient stops. + + [MSDN documentation for GradientStops.Count](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstops.count). + */ + long GetCount(); + + //@{ + /** + Returns the gradient stop at @a index. + + [MSDN documentation for GradientStops.Item](https://learn.microsoft.com/en-us/office/vba/api/office.gradientstops.item). + */ + wxExcelGradientStop GetItem(long index); + wxExcelGradientStop operator[](long index); + //@} + + /** + The iterator over the items, see wxExcelCollectionIterator. + */ + typedef wxExcelCollectionIterator iterator; + + //@{ + /** + Returns the iterator referring to the first item, or past the last item, + which allows iterating over the items with a range-based for loop, + see wxExcelCollectionIterator. + */ + iterator begin() { return iterator(this, 1); } + iterator end() { return iterator(this, GetCount() + 1); } + //@} + + /** + Returns "GradientStops". + */ + virtual wxString GetAutoExcelObjectName_() const { return wxS("GradientStops"); } + }; + +} // namespace wxAutoExcel + +#endif // #if WXAUTOEXCEL_USE_SHAPES || WXAUTOEXCEL_USE_CHARTS + +#endif //_WXAUTOEXCEL_GRADIENTSTOPS_H diff --git a/include/wx/wxAutoExcelIconSetCondition.h b/include/wx/wxAutoExcelIconSetCondition.h index 0db2b25d..61cc6424 100644 --- a/include/wx/wxAutoExcelIconSetCondition.h +++ b/include/wx/wxAutoExcelIconSetCondition.h @@ -83,18 +83,18 @@ namespace wxAutoExcel { wxExcelIconCriteria GetIconCriteria(); /** - Returns an IconSets collection which specifies the icon set used in the conditional format. Since Excel 2007. + Returns an IconSet object which specifies the icon set used in the conditional format. Since Excel 2007. [MSDN documentation for IconSetCondition.IconSet](https://learn.microsoft.com/en-us/office/vba/api/excel.iconsetcondition.iconset). */ - wxExcelIconSets GetIconSet(); + wxExcelIconSet GetIconSet(); /** - Sets an IconSets collection which specifies the icon set used in the conditional format. Since Excel 2007. + Sets an IconSet object which specifies the icon set used in the conditional format. Since Excel 2007. [MSDN documentation for IconSetCondition.IconSet](https://learn.microsoft.com/en-us/office/vba/api/excel.iconsetcondition.iconset). */ - void SetIconSet(const wxExcelIconSets& iconSet); + void SetIconSet(const wxExcelIconSet& iconSet); /** Returns a Boolean value indicating if the thresholds for an icon set conditional format are determined using percentiles. Since Excel 2007. diff --git a/include/wx/wxAutoExcelLegend.h b/include/wx/wxAutoExcelLegend.h index 2878dab9..bcd3f86c 100644 --- a/include/wx/wxAutoExcelLegend.h +++ b/include/wx/wxAutoExcelLegend.h @@ -68,6 +68,13 @@ namespace wxAutoExcel { */ void SetAutoScaleFont(bool autoScaleFont); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for Legend.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.legend.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelLegendKey.h b/include/wx/wxAutoExcelLegendKey.h index 1dc76b0a..aa1cf748 100644 --- a/include/wx/wxAutoExcelLegendKey.h +++ b/include/wx/wxAutoExcelLegendKey.h @@ -41,6 +41,13 @@ namespace wxAutoExcel { // ***** PROPERTIES ***** + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for LegendKey.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.legendkey.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelListColumn.h b/include/wx/wxAutoExcelListColumn.h index 88a29886..e25f3aeb 100644 --- a/include/wx/wxAutoExcelListColumn.h +++ b/include/wx/wxAutoExcelListColumn.h @@ -45,6 +45,13 @@ class WXDLLIMPEXP_WXAUTOEXCEL wxExcelListColumn : public wxExcelObject */ long GetIndex(); + /** + Returns a ListDataFormat object that contains the data type properties of the column. + + [MSDN documentation for ListColumn.ListDataFormat](https://learn.microsoft.com/en-us/office/vba/api/excel.listcolumn.listdataformat) + */ + wxExcelListDataFormat GetListDataFormat(); + /** Returns a String value that represents the name of the list column. diff --git a/include/wx/wxAutoExcelOLEObjects.h b/include/wx/wxAutoExcelOLEObjects.h index 8a6513f6..a1b53c08 100644 --- a/include/wx/wxAutoExcelOLEObjects.h +++ b/include/wx/wxAutoExcelOLEObjects.h @@ -406,9 +406,10 @@ namespace wxAutoExcel { [MSDN documentation for OLEObjects.Add](https://learn.microsoft.com/en-us/office/vba/api/excel.oleobjects.add). */ wxExcelOLEObject Add(const wxString& classType = wxEmptyString, const wxString& filename = wxEmptyString, - double* height = NULL, wxXlTribool link = wxDefaultXlTribool, wxXlTribool displayAsIcon = wxDefaultXlTribool, + wxXlTribool link = wxDefaultXlTribool, wxXlTribool displayAsIcon = wxDefaultXlTribool, const wxString& iconFileName = wxEmptyString, long* iconIndex = NULL, - const wxString& iconLabel = wxEmptyString, double* left = NULL, double* width = NULL); + const wxString& iconLabel = wxEmptyString, + double* left = NULL, double* top = NULL, double* width = NULL, double* height = NULL); //@{ /** diff --git a/include/wx/wxAutoExcelPlotArea.h b/include/wx/wxAutoExcelPlotArea.h index ff11d885..1a742d9e 100644 --- a/include/wx/wxAutoExcelPlotArea.h +++ b/include/wx/wxAutoExcelPlotArea.h @@ -40,6 +40,13 @@ namespace wxAutoExcel { // ***** PROPERTIES ***** + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for PlotArea.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.plotarea.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelPoints.h b/include/wx/wxAutoExcelPoints.h index cb3c0015..f8512707 100644 --- a/include/wx/wxAutoExcelPoints.h +++ b/include/wx/wxAutoExcelPoints.h @@ -138,6 +138,13 @@ namespace wxAutoExcel { */ void SetExplosion(long explosion); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for Point.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.point.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelRange.h b/include/wx/wxAutoExcelRange.h index 6be94179..626bf550 100644 --- a/include/wx/wxAutoExcelRange.h +++ b/include/wx/wxAutoExcelRange.h @@ -67,7 +67,7 @@ namespace wxAutoExcel { [MSDN documentation for Range.ApplyNames](https://learn.microsoft.com/en-us/office/vba/api/excel.range.applynames). */ void ApplyNames(wxArrayString* names = NULL, - wxXlTribool ignoreRelativeAbsolute = NULL, wxXlTribool useRowColumnNames = wxDefaultXlTribool, + wxXlTribool ignoreRelativeAbsolute = wxDefaultXlTribool, wxXlTribool useRowColumnNames = wxDefaultXlTribool, wxXlTribool omitColumn = wxDefaultXlTribool, wxXlTribool omitRow = wxDefaultXlTribool, XlApplyNamesOrder* order = NULL, wxXlTribool appendLast = wxDefaultXlTribool); diff --git a/include/wx/wxAutoExcelSeries.h b/include/wx/wxAutoExcelSeries.h index c2f98b39..05ba6f76 100644 --- a/include/wx/wxAutoExcelSeries.h +++ b/include/wx/wxAutoExcelSeries.h @@ -65,13 +65,27 @@ namespace wxAutoExcel { */ bool Delete(); + //@{ /** - Applies error bars to the series. Variant. + Applies error bars to the series. Returns true on success. + + The error amounts are needed for some types only, e.g., not for xlErrorBarTypeStError. + For xlErrorBarTypeCustom, Excel requires both @a amount and @a minusValues, + which can then also be a Range, an array of numbers, or a string with an array constant + or a reference, such as "={1,2,3}" or "=Sheet1!$D$2:$D$5". Use the overload taking a wxVariant + for an array or a string, and the one taking a Range for ranges. A Range passed to the + overload taking a wxVariant is converted to its values, so the error bars do not + change with the cells then. [MSDN documentation for Series.ErrorBar](https://learn.microsoft.com/en-us/office/vba/api/excel.series.errorbar). */ bool ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude include, XlErrorBarType type, double* amount = NULL, double* minusValues = NULL); + bool ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude include, XlErrorBarType type, + wxExcelRange amount, wxExcelRange minusValues); + bool ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude include, XlErrorBarType type, + const wxVariant& amount, const wxVariant& minusValues); + //@} /** Pastes a picture from the Clipboard as the marker on the selected series. @@ -225,6 +239,13 @@ namespace wxAutoExcel { */ void SetExplosion(long explosion); + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for Series.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.series.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelUpBars.h b/include/wx/wxAutoExcelUpBars.h index 649c404f..0da0ccbb 100644 --- a/include/wx/wxAutoExcelUpBars.h +++ b/include/wx/wxAutoExcelUpBars.h @@ -40,6 +40,13 @@ namespace wxAutoExcel { // ***** PROPERTIES ***** + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for UpBars.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.upbars.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelWalls.h b/include/wx/wxAutoExcelWalls.h index 43f600a7..b6406c30 100644 --- a/include/wx/wxAutoExcelWalls.h +++ b/include/wx/wxAutoExcelWalls.h @@ -49,6 +49,13 @@ namespace wxAutoExcel { // ***** PROPERTIES ***** + /** + Returns a ChartFillFormat object that contains fill formatting properties for the object. + + [MSDN documentation for Walls.Fill](https://learn.microsoft.com/en-us/office/vba/api/excel.walls.fill). + */ + wxExcelChartFillFormat GetFill(); + /** Returns the ChartFormat object. Since Excel 2007. diff --git a/include/wx/wxAutoExcelWorkbook.h b/include/wx/wxAutoExcelWorkbook.h index 2bbc08a8..10718fb8 100644 --- a/include/wx/wxAutoExcelWorkbook.h +++ b/include/wx/wxAutoExcelWorkbook.h @@ -698,12 +698,16 @@ namespace wxAutoExcel { void SetHighlightChangesOnScreen(bool highlightChangesOnScreen); #if WXAUTOEXCEL_USE_CONDFORMAT + //@{ /** - This property is used to filter data in a workbook based on a cell icon from the IconSet collection. + Returns the IconSets collection of all the icon sets, or the icon set given by @a index, + e.g., to set it to an icon set conditional format. Since Excel 2007. [MSDN documentation for Workbook.IconSets](https://learn.microsoft.com/en-us/office/vba/api/excel.workbook.iconsets). */ - wxExcelIconSets GetIconSets(XlIconSet index); + wxExcelIconSets GetIconSets(); + wxExcelIconSet GetIconSets(XlIconSet index); + //@} #endif // #if WXAUTOEXCEL_USE_CONDFORMAT /** diff --git a/include/wx/wxAutoExcelWorksheetView.h b/include/wx/wxAutoExcelWorksheetView.h index 33f03dc9..d9c5c043 100644 --- a/include/wx/wxAutoExcelWorksheetView.h +++ b/include/wx/wxAutoExcelWorksheetView.h @@ -94,11 +94,11 @@ namespace wxAutoExcel { /** - Returns name of the sheet. Since Excel 2007. + Returns the worksheet of the view. Since Excel 2007. [MSDN documentation for WorksheetView.Sheet](https://learn.microsoft.com/en-us/office/vba/api/excel.worksheetview.sheet). */ - wxString GetSheet(); + wxExcelWorksheet GetSheet(); /** Returns "WorksheetView". diff --git a/include/wx/wxAutoExcel_enums.h b/include/wx/wxAutoExcel_enums.h index f41a11bb..2ac82fdc 100644 --- a/include/wx/wxAutoExcel_enums.h +++ b/include/wx/wxAutoExcel_enums.h @@ -2349,22 +2349,27 @@ Specifies the type of icon set. */ enum XlIconSet { + xlCustomSet = -1, /*!< Custom set */ xl3Arrows = 1, /*!< 3 Arrows */ xl3ArrowsGray = 2, /*!< 3 Arrows Gray */ xl3Flags = 3, /*!< 3 Flags */ xl3Signs = 6, /*!< 3 Signs */ + xl3Stars = 18, /*!< 3 Stars */ xl3Symbols = 7, /*!< 3 Symbols */ + xl3Symbols2 = 8, /*!< 3 Symbols 2 */ xl3TrafficLights1 = 4, /*!< 3 Traffic Lights 1 */ xl3TrafficLights2 = 5, /*!< 3 Traffic Lights 2 */ - xl4Arrows = 8, /*!< 4 Arrows */ - xl4ArrowsGray = 9, /*!< 4 Arrows Gray */ - xl4CRV = 11, /*!< 4 CRV */ - xl4RedToBlack = 10, /*!< 4 Red To Black */ - xl4TrafficLights = 12, /*!< 4 Traffic Lights */ - xl5Arrows = 13, /*!< 5 Arrows */ - xl5ArrowsGray = 14, /*!< 5 Arrows Gray */ - xl5CRV = 15, /*!< 5 CRV */ - xl5Quarters = 16, /*!< 5 Quarters */ + xl3Triangles = 19, /*!< 3 Triangles */ + xl4Arrows = 9, /*!< 4 Arrows */ + xl4ArrowsGray = 10, /*!< 4 Arrows Gray */ + xl4CRV = 12, /*!< 4 CRV */ + xl4RedToBlack = 11, /*!< 4 Red To Black */ + xl4TrafficLights = 13, /*!< 4 Traffic Lights */ + xl5Arrows = 14, /*!< 5 Arrows */ + xl5ArrowsGray = 15, /*!< 5 Arrows Gray */ + xl5Boxes = 20, /*!< 5 Boxes */ + xl5CRV = 16, /*!< 5 CRV */ + xl5Quarters = 17, /*!< 5 Quarters */ }; /** diff --git a/include/wx/wxAutoExcel_fwd.h b/include/wx/wxAutoExcel_fwd.h index d87f5906..e82862b2 100644 --- a/include/wx/wxAutoExcel_fwd.h +++ b/include/wx/wxAutoExcel_fwd.h @@ -130,6 +130,8 @@ class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelModel3DFormat; class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelColorFormat; class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelFillFormat; +class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelGradientStop; +class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelGradientStops; class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelGlowFormat; class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelLineFormat; class WXDLLIMPEXP_FWD_WXAUTOEXCEL wxExcelOLEFormat; diff --git a/include/wx/wxAutoExcel_version.h b/include/wx/wxAutoExcel_version.h index d1465e78..8bc473cc 100644 --- a/include/wx/wxAutoExcel_version.h +++ b/include/wx/wxAutoExcel_version.h @@ -9,8 +9,8 @@ #define _WXAUTOEXCEL_VERSION_H #define WXAUTOEXCEL_MAJOR_VERSION 2 -#define WXAUTOEXCEL_MINOR_VERSION 5 -#define WXAUTOEXCEL_RELEASE_NUMBER 1 +#define WXAUTOEXCEL_MINOR_VERSION 6 +#define WXAUTOEXCEL_RELEASE_NUMBER 0 #define WXAUTOEXCEL_SUBRELEASE_NUMBER 0 diff --git a/src/wxAutoExcelAllowEditRanges.cpp b/src/wxAutoExcelAllowEditRanges.cpp index 1fe9d85b..3faeb97a 100644 --- a/src/wxAutoExcelAllowEditRanges.cpp +++ b/src/wxAutoExcelAllowEditRanges.cpp @@ -40,6 +40,16 @@ wxExcelRange wxExcelAllowEditRange::GetRange() WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Range", range); } +void wxExcelAllowEditRange::SetRange(const wxExcelRange& range) +{ + wxVariant vRange; + + if ( ObjectToVariant(&range, vRange) ) + { + InvokePutRefProperty(wxS("Range"), vRange); + } +} + wxString wxExcelAllowEditRange::GetTitle() { WXAUTOEXCEL_PROPERTY_STRING_GET0("Title"); diff --git a/src/wxAutoExcelAxes.cpp b/src/wxAutoExcelAxes.cpp index 11c0f9b3..b9b4aea5 100644 --- a/src/wxAutoExcelAxes.cpp +++ b/src/wxAutoExcelAxes.cpp @@ -111,7 +111,8 @@ wxArrayString wxExcelAxis::GetCategoryNames() } } else if ( type == wxS("void*" ) ) { - //@FIXME maybe can also return a Range - test it? + // Excel returns the names as an array of strings also when they + // were set to a Range, so this should not happen wxExcelRange range; VariantToObject(vResult, &range); // make sure we don't leave a reference hanging wxFAIL; diff --git a/src/wxAutoExcelAxisTitle.cpp b/src/wxAutoExcelAxisTitle.cpp index f8693f5f..e77ef97b 100644 --- a/src/wxAutoExcelAxisTitle.cpp +++ b/src/wxAutoExcelAxisTitle.cpp @@ -12,6 +12,7 @@ #if WXAUTOEXCEL_USE_CHARTS #include "wx/wxAutoExcelCharacters.h" +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -60,6 +61,13 @@ wxExcelCharacters wxExcelAxisTitle::GetCharacters(long start, long* length) WXAUTOEXCEL_PROPERTY_OBJECT_GET2("Characters", start, vLength, characters); } +wxExcelChartFillFormat wxExcelAxisTitle::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelAxisTitle::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelChart.cpp b/src/wxAutoExcelChart.cpp index e9273f7e..12824f3b 100644 --- a/src/wxAutoExcelChart.cpp +++ b/src/wxAutoExcelChart.cpp @@ -242,9 +242,9 @@ bool wxExcelChart::Export(const wxString& fileName, const wxString& filterName, return vResult.GetBool(); } -wxExcelSeriesCollection wxExcelChart::FullSeriesCollection() +wxExcelFullSeriesCollection wxExcelChart::FullSeriesCollection() { - wxExcelSeriesCollection series; + wxExcelFullSeriesCollection series; WXAUTOEXCEL_CALL_METHOD0_OBJECT("FullSeriesCollection", series); } diff --git a/src/wxAutoExcelChartArea.cpp b/src/wxAutoExcelChartArea.cpp index 9cdda273..426077b0 100644 --- a/src/wxAutoExcelChartArea.cpp +++ b/src/wxAutoExcelChartArea.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -55,6 +56,13 @@ void wxExcelChartArea::SetAutoScaleFont(bool autoScaleFont) InvokePutProperty(wxS("AutoScaleFont"), autoScaleFont); } +wxExcelChartFillFormat wxExcelChartArea::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelChartArea::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelChartColorFormat.cpp b/src/wxAutoExcelChartColorFormat.cpp index a7dc9f5f..a466fe88 100644 --- a/src/wxAutoExcelChartColorFormat.cpp +++ b/src/wxAutoExcelChartColorFormat.cpp @@ -27,6 +27,11 @@ long wxExcelChartColorFormat::GetSchemeColor() WXAUTOEXCEL_PROPERTY_LONG_GET0("SchemeColor"); } +void wxExcelChartColorFormat::SetSchemeColor(long schemeColor) +{ + InvokePutProperty(wxS("SchemeColor"), schemeColor); +} + MsoColorType wxExcelChartColorFormat::GetType() { WXAUTOEXCEL_PROPERTY_ENUM_GET0("Type", MsoColorType, msoColorTypeRGB); diff --git a/src/wxAutoExcelChartTitle.cpp b/src/wxAutoExcelChartTitle.cpp index 2ffb102a..f074da38 100644 --- a/src/wxAutoExcelChartTitle.cpp +++ b/src/wxAutoExcelChartTitle.cpp @@ -12,6 +12,7 @@ #if WXAUTOEXCEL_USE_CHARTS #include "wx/wxAutoExcelCharacters.h" +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -59,6 +60,13 @@ wxExcelCharacters wxExcelChartTitle::GetCharacters(long start, long* length) WXAUTOEXCEL_PROPERTY_OBJECT_GET2("Characters", start, vLength, characters); } +wxExcelChartFillFormat wxExcelChartTitle::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelChartTitle::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelDataLabels.cpp b/src/wxAutoExcelDataLabels.cpp index 8788499e..daea5876 100644 --- a/src/wxAutoExcelDataLabels.cpp +++ b/src/wxAutoExcelDataLabels.cpp @@ -12,6 +12,7 @@ #if WXAUTOEXCEL_USE_CHARTS #include "wx/wxAutoExcelCharacters.h" +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -77,6 +78,13 @@ wxExcelCharacters wxExcelDataLabel::GetCharacters(long start, long* length) WXAUTOEXCEL_PROPERTY_OBJECT_GET2("Characters", start, vLength, characters); } +wxExcelChartFillFormat wxExcelDataLabel::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelDataLabel::GetFormat() { wxExcelChartFormat chartFormat; @@ -354,6 +362,13 @@ long wxExcelDataLabels::GetCount() WXAUTOEXCEL_PROPERTY_LONG_GET0("Count"); } +wxExcelChartFillFormat wxExcelDataLabels::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelDataLabels::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelDisplayUnitLabel.cpp b/src/wxAutoExcelDisplayUnitLabel.cpp index 24f2b143..377884ca 100644 --- a/src/wxAutoExcelDisplayUnitLabel.cpp +++ b/src/wxAutoExcelDisplayUnitLabel.cpp @@ -12,6 +12,7 @@ #if WXAUTOEXCEL_USE_CHARTS #include "wx/wxAutoExcelCharacters.h" +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -58,6 +59,13 @@ wxExcelCharacters wxExcelDisplayUnitLabel::GetCharacters(long start, long* lengt WXAUTOEXCEL_PROPERTY_OBJECT_GET2("Characters", start, vLength, characters); } +wxExcelChartFillFormat wxExcelDisplayUnitLabel::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelDisplayUnitLabel::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelDownBars.cpp b/src/wxAutoExcelDownBars.cpp index b1282d07..24be830e 100644 --- a/src/wxAutoExcelDownBars.cpp +++ b/src/wxAutoExcelDownBars.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -32,6 +33,13 @@ bool wxExcelDownBars::Select() // ***** class wxExcelDownBars PROPERTIES ***** +wxExcelChartFillFormat wxExcelDownBars::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelDownBars::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelFillFormat.cpp b/src/wxAutoExcelFillFormat.cpp index 72ccf7a2..11e6fd84 100644 --- a/src/wxAutoExcelFillFormat.cpp +++ b/src/wxAutoExcelFillFormat.cpp @@ -12,6 +12,7 @@ #if WXAUTOEXCEL_USE_SHAPES || WXAUTOEXCEL_USE_CHARTS #include "wx/wxAutoExcelColorFormat.h" +#include "wx/wxAutoExcelGradientStops.h" #include "wx/wxAutoExcel_private.h" @@ -85,13 +86,12 @@ double wxExcelFillFormat::GetGradientDegree() WXAUTOEXCEL_PROPERTY_DOUBLE_GET0("GradientDegree"); } -//wxExcelGradientStops wxExcelFillFormat::GetGradientStops() -//{ -// wxExcelGradientStops gradientStops; -// -// WXAUTOEXCEL_PROPERTY_OBJECT_GET0("GradientStops", gradientStops); -// -//} +wxExcelGradientStops wxExcelFillFormat::GetGradientStops() +{ + wxExcelGradientStops gradientStops; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("GradientStops", gradientStops); +} MsoGradientStyle wxExcelFillFormat::GetGradientStyle() { diff --git a/src/wxAutoExcelFloor.cpp b/src/wxAutoExcelFloor.cpp index e18aa8a5..6d94aa1f 100644 --- a/src/wxAutoExcelFloor.cpp +++ b/src/wxAutoExcelFloor.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -37,6 +38,13 @@ bool wxExcelFloor::Select() // ***** class wxExcelFloor PROPERTIES ***** +wxExcelChartFillFormat wxExcelFloor::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelFloor::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelGradientStops.cpp b/src/wxAutoExcelGradientStops.cpp new file mode 100644 index 00000000..80184197 --- /dev/null +++ b/src/wxAutoExcelGradientStops.cpp @@ -0,0 +1,107 @@ +///////////////////////////////////////////////////////////////////////////// +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + + +#include "wx/wxAutoExcel_prec.h" + +#include "wx/wxAutoExcelGradientStops.h" + +#if WXAUTOEXCEL_USE_SHAPES || WXAUTOEXCEL_USE_CHARTS + +#include + +#include "wx/wxAutoExcelColorFormat.h" + +#include "wx/wxAutoExcel_private.h" + +namespace wxAutoExcel { + +// ***** class wxExcelGradientStop PROPERTIES ***** + +wxExcelColorFormat wxExcelGradientStop::GetColor() +{ + wxExcelColorFormat colorFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Color", colorFormat); +} + +double wxExcelGradientStop::GetPosition() +{ + WXAUTOEXCEL_PROPERTY_DOUBLE_GET0("Position"); +} + +void wxExcelGradientStop::SetPosition(double position) +{ + InvokePutProperty(wxS("Position"), position); +} + +double wxExcelGradientStop::GetTransparency() +{ + WXAUTOEXCEL_PROPERTY_DOUBLE_GET0("Transparency"); +} + +void wxExcelGradientStop::SetTransparency(double transparency) +{ + InvokePutProperty(wxS("Transparency"), transparency); +} + + +// ***** class wxExcelGradientStops METHODS ***** + +void wxExcelGradientStops::Delete(long index) +{ + wxVariant vIndex(index, wxS("Index")); + + WXAUTOEXCEL_CALL_METHOD1_RET("Delete", vIndex, "null"); +} + +void wxExcelGradientStops::Insert(const wxColour& color, double position, double transparency, long index) +{ + wxVariant vRGB((long)color.GetRGB(), wxS("RGB")); + wxVariant vPosition(position, wxS("Position")); + wxVariant vTransparency(transparency, wxS("Transparency")); + wxVariant vIndex(index, wxS("Index")); + + WXAUTOEXCEL_CALL_METHOD4_RET("Insert", vRGB, vPosition, vTransparency, vIndex, "null"); +} + +void wxExcelGradientStops::Insert2(const wxColour& color, double position, double transparency, long index, + double brightness) +{ + wxVariant vRGB((long)color.GetRGB(), wxS("RGB")); + wxVariant vPosition(position, wxS("Position")); + wxVariant vTransparency(transparency, wxS("Transparency")); + wxVariant vIndex(index, wxS("Index")); + wxVariant vBrightness(brightness, wxS("Brightness")); + + WXAUTOEXCEL_CALL_METHOD5_RET("Insert2", vRGB, vPosition, vTransparency, vIndex, vBrightness, "null"); +} + + +// ***** class wxExcelGradientStops PROPERTIES ***** + +long wxExcelGradientStops::GetCount() +{ + WXAUTOEXCEL_PROPERTY_LONG_GET0("Count"); +} + +wxExcelGradientStop wxExcelGradientStops::GetItem(long index) +{ + wxASSERT( index > 0 ); + + wxExcelGradientStop gradientStop; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET1("Item", index, gradientStop); +} + +wxExcelGradientStop wxExcelGradientStops::operator[](long index) +{ + return GetItem(index); +} + +} // namespace wxAutoExcel + +#endif // #if WXAUTOEXCEL_USE_SHAPES || WXAUTOEXCEL_USE_CHARTS diff --git a/src/wxAutoExcelIconSetCondition.cpp b/src/wxAutoExcelIconSetCondition.cpp index 17c63c06..57ead903 100644 --- a/src/wxAutoExcelIconSetCondition.cpp +++ b/src/wxAutoExcelIconSetCondition.cpp @@ -72,14 +72,14 @@ wxExcelIconCriteria wxExcelIconSetCondition::GetIconCriteria() WXAUTOEXCEL_PROPERTY_OBJECT_GET0("IconCriteria", iconCriteria); } -wxExcelIconSets wxExcelIconSetCondition::GetIconSet() +wxExcelIconSet wxExcelIconSetCondition::GetIconSet() { - wxExcelIconSets iconSets; + wxExcelIconSet iconSet; - WXAUTOEXCEL_PROPERTY_OBJECT_GET0("IconSet", iconSets); + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("IconSet", iconSet); } -void wxExcelIconSetCondition::SetIconSet(const wxExcelIconSets& iconSet) +void wxExcelIconSetCondition::SetIconSet(const wxExcelIconSet& iconSet) { wxVariant vIconSet; diff --git a/src/wxAutoExcelLegend.cpp b/src/wxAutoExcelLegend.cpp index eff1a2a5..d7f81297 100644 --- a/src/wxAutoExcelLegend.cpp +++ b/src/wxAutoExcelLegend.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcelLegendEntries.h" @@ -53,6 +54,13 @@ void wxExcelLegend::SetAutoScaleFont(bool autoScaleFont) InvokePutProperty(wxS("AutoScaleFont"), autoScaleFont); } +wxExcelChartFillFormat wxExcelLegend::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelLegend::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelLegendKey.cpp b/src/wxAutoExcelLegendKey.cpp index 8fefbd50..98c7a450 100644 --- a/src/wxAutoExcelLegendKey.cpp +++ b/src/wxAutoExcelLegendKey.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -31,6 +32,13 @@ bool wxExcelLegendKey::Delete() // ***** class wxExcelLegendKey PROPERTIES ***** +wxExcelChartFillFormat wxExcelLegendKey::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelLegendKey::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelListColumn.cpp b/src/wxAutoExcelListColumn.cpp index dddc135b..cc8ba697 100644 --- a/src/wxAutoExcelListColumn.cpp +++ b/src/wxAutoExcelListColumn.cpp @@ -8,6 +8,7 @@ #include "wx/wxAutoExcelListColumn.h" +#include "wx/wxAutoExcelListDataFormat.h" #include "wx/wxAutoExcelRange.h" #include "wx/wxAutoExcel_private.h" @@ -30,6 +31,13 @@ wxExcelRange wxExcelListColumn::GetDataBodyRange() WXAUTOEXCEL_PROPERTY_OBJECT_GET0("DataBodyRange", range); } +wxExcelListDataFormat wxExcelListColumn::GetListDataFormat() +{ + wxExcelListDataFormat listDataFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("ListDataFormat", listDataFormat); +} + long wxExcelListColumn::GetIndex() { WXAUTOEXCEL_PROPERTY_LONG_GET0("Index"); diff --git a/src/wxAutoExcelOLEObjects.cpp b/src/wxAutoExcelOLEObjects.cpp index 6d6e5b37..eca03610 100644 --- a/src/wxAutoExcelOLEObjects.cpp +++ b/src/wxAutoExcelOLEObjects.cpp @@ -304,24 +304,23 @@ long wxExcelOLEObject::GetZOrder() // ***** class wxExcelOLEObjects METHODS ***** wxExcelOLEObject wxExcelOLEObjects::Add(const wxString& classType, const wxString& filename, - double* height, wxXlTribool link, wxXlTribool displayAsIcon, - const wxString& iconFileName, long* iconIndex, const wxString& iconLabel, - double* left, double* width) + wxXlTribool link, wxXlTribool displayAsIcon, + const wxString& iconFileName, long* iconIndex, const wxString& iconLabel, + double* left, double* top, double* width, double* height) { wxVariantVector args; WXAUTOEXCEL_OPTIONALCPPSTR_TO_OPTIONALVARIANT_NAME_VECTOR(ClassType, classType, args); WXAUTOEXCEL_OPTIONALCPPSTR_TO_OPTIONALVARIANT_NAME_VECTOR(Filename, filename, args); - WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME_VECTOR(Height, height, args); - WXAUTOEXCEL_OPTIONALCPPTBOOL_TO_OPTIONALVARIANT_NAME_VECTOR(Link, link, args); WXAUTOEXCEL_OPTIONALCPPTBOOL_TO_OPTIONALVARIANT_NAME_VECTOR(DisplayAsIcon, displayAsIcon, args); WXAUTOEXCEL_OPTIONALCPPSTR_TO_OPTIONALVARIANT_NAME_VECTOR(IconFileName, iconFileName, args); WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME_VECTOR(IconIndex, iconIndex, args); WXAUTOEXCEL_OPTIONALCPPSTR_TO_OPTIONALVARIANT_NAME_VECTOR(IconLabel, iconLabel, args); WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME_VECTOR(Left, left, args); + WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME_VECTOR(Top, top, args); WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME_VECTOR(Width, width, args); - + WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME_VECTOR(Height, height, args); wxExcelOLEObject object; diff --git a/src/wxAutoExcelPlotArea.cpp b/src/wxAutoExcelPlotArea.cpp index 3964fa76..3894ee31 100644 --- a/src/wxAutoExcelPlotArea.cpp +++ b/src/wxAutoExcelPlotArea.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -34,6 +35,13 @@ bool wxExcelPlotArea::Select() // ***** class wxExcelPlotArea PROPERTIES ***** +wxExcelChartFillFormat wxExcelPlotArea::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelPlotArea::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelPoints.cpp b/src/wxAutoExcelPoints.cpp index c889b331..a8de3ddd 100644 --- a/src/wxAutoExcelPoints.cpp +++ b/src/wxAutoExcelPoints.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcelDataLabels.h" @@ -117,6 +118,13 @@ void wxExcelPoint::SetExplosion(long explosion) InvokePutProperty(wxS("Explosion"), explosion); } +wxExcelChartFillFormat wxExcelPoint::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelPoint::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelRange.cpp b/src/wxAutoExcelRange.cpp index 51e9b293..92cd1026 100644 --- a/src/wxAutoExcelRange.cpp +++ b/src/wxAutoExcelRange.cpp @@ -98,11 +98,13 @@ void wxExcelRange::ApplyNames(wxArrayString* names, { wxVariantVector args; - wxVariant vNames; + if ( names && !names->empty() ) { + wxVariant vNames(*names); + vNames.SetName(wxS("Names")); - vNames = *names; + args.push_back(vNames); } WXAUTOEXCEL_OPTIONALCPPTBOOL_TO_OPTIONALVARIANT_NAME_VECTOR(IgnoreRelativeAbsolute, ignoreRelativeAbsolute, args); WXAUTOEXCEL_OPTIONALCPPTBOOL_TO_OPTIONALVARIANT_NAME_VECTOR(UseRowColumnNames, useRowColumnNames, args); diff --git a/src/wxAutoExcelSeries.cpp b/src/wxAutoExcelSeries.cpp index 6f635355..00b7a3b6 100644 --- a/src/wxAutoExcelSeries.cpp +++ b/src/wxAutoExcelSeries.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcelDataLabels.h" #include "wx/wxAutoExcelErrorBars.h" @@ -68,7 +69,6 @@ bool wxExcelSeries::Delete() WXAUTOEXCEL_CALL_METHOD0_BOOL("Delete"); } -//@FIXME check if amount and minusValues are scalars or not! bool wxExcelSeries::ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude include, XlErrorBarType type, double* amount, double* minusValues) { @@ -78,10 +78,42 @@ bool wxExcelSeries::ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude in WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME(Amount, amount); WXAUTOEXCEL_OPTIONALCPP_TO_OPTIONALVARIANT_NAME(MinusValues, minusValues); - WXAUTOEXCEL_CALL_METHOD5("ErrorBar", vDirection, vInclude, vType, vAmount, vMinusValues, "bool", false); + // Excel returns Empty on success + WXAUTOEXCEL_CALL_METHOD5("ErrorBar", vDirection, vInclude, vType, vAmount, vMinusValues, "null", false); - //@FIXME check if it returns bool or ErrorBar object! - return vResult.GetBool(); + return true; +} + +bool wxExcelSeries::ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude include, XlErrorBarType type, + wxExcelRange amount, wxExcelRange minusValues) +{ + wxVariant vAmount, vMinusValues; + + if ( !ObjectToVariant(&amount, vAmount, wxS("Amount")) + || !ObjectToVariant(&minusValues, vMinusValues, wxS("MinusValues")) ) + { + return false; + } + + return ErrorBar(direction, include, type, vAmount, vMinusValues); +} + +bool wxExcelSeries::ErrorBar(XlErrorBarDirection direction, XlErrorBarInclude include, XlErrorBarType type, + const wxVariant& amount, const wxVariant& minusValues) +{ + wxVariant vDirection((long)direction, wxS("Direction")); + wxVariant vInclude((long)include, wxS("Include")); + wxVariant vType((long)type, wxS("Type")); + wxVariant vAmount(amount); + wxVariant vMinusValues(minusValues); + + vAmount.SetName(wxS("Amount")); + vMinusValues.SetName(wxS("MinusValues")); + + // Excel returns Empty on success + WXAUTOEXCEL_CALL_METHOD5("ErrorBar", vDirection, vInclude, vType, vAmount, vMinusValues, "null", false); + + return true; } bool wxExcelSeries::Paste() @@ -202,6 +234,13 @@ void wxExcelSeries::SetExplosion(long explosion) InvokePutProperty(wxS("Explosion"), explosion); } +wxExcelChartFillFormat wxExcelSeries::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelSeries::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelUpBars.cpp b/src/wxAutoExcelUpBars.cpp index 270a11ee..05e9607c 100644 --- a/src/wxAutoExcelUpBars.cpp +++ b/src/wxAutoExcelUpBars.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -31,6 +32,13 @@ bool wxExcelUpBars::Select() // ***** class wxExcelUpBars PROPERTIES ***** +wxExcelChartFillFormat wxExcelUpBars::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelUpBars::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelWalls.cpp b/src/wxAutoExcelWalls.cpp index d7bbf5a6..72734e34 100644 --- a/src/wxAutoExcelWalls.cpp +++ b/src/wxAutoExcelWalls.cpp @@ -11,6 +11,7 @@ #if WXAUTOEXCEL_USE_CHARTS +#include "wx/wxAutoExcelChartFillFormat.h" #include "wx/wxAutoExcelChartFormat.h" #include "wx/wxAutoExcel_private.h" @@ -38,6 +39,13 @@ bool wxExcelWalls::Select() // ***** class wxExcelWalls PROPERTIES ***** +wxExcelChartFillFormat wxExcelWalls::GetFill() +{ + wxExcelChartFillFormat chartFillFormat; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Fill", chartFillFormat); +} + wxExcelChartFormat wxExcelWalls::GetFormat() { wxExcelChartFormat chartFormat; diff --git a/src/wxAutoExcelWorkbook.cpp b/src/wxAutoExcelWorkbook.cpp index 9ec275ac..24c996e3 100644 --- a/src/wxAutoExcelWorkbook.cpp +++ b/src/wxAutoExcelWorkbook.cpp @@ -727,11 +727,18 @@ void wxExcelWorkbook::SetHighlightChangesOnScreen(bool highlightChangesOnScreen) #if WXAUTOEXCEL_USE_CONDFORMAT -wxExcelIconSets wxExcelWorkbook::GetIconSets(XlIconSet index) +wxExcelIconSets wxExcelWorkbook::GetIconSets() { wxExcelIconSets sets; - WXAUTOEXCEL_PROPERTY_OBJECT_GET1("IconSets", index, sets); + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("IconSets", sets); +} + +wxExcelIconSet wxExcelWorkbook::GetIconSets(XlIconSet index) +{ + wxExcelIconSet set; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET1("IconSets", index, set); } #endif // #if WXAUTOEXCEL_USE_CONDFORMAT diff --git a/src/wxAutoExcelWorksheetView.cpp b/src/wxAutoExcelWorksheetView.cpp index a214a7c2..35c20370 100644 --- a/src/wxAutoExcelWorksheetView.cpp +++ b/src/wxAutoExcelWorksheetView.cpp @@ -9,6 +9,8 @@ #include "wx/wxAutoExcelWorksheetView.h" +#include "wx/wxAutoExcelWorksheet.h" + #include "wx/wxAutoExcel_private.h" namespace wxAutoExcel { @@ -68,9 +70,11 @@ void wxExcelWorksheetView::SetDisplayZeros(bool displayZeros) } -wxString wxExcelWorksheetView::GetSheet() +wxExcelWorksheet wxExcelWorksheetView::GetSheet() { - WXAUTOEXCEL_PROPERTY_STRING_GET0("Sheet"); + wxExcelWorksheet worksheet; + + WXAUTOEXCEL_PROPERTY_OBJECT_GET0("Sheet", worksheet); } diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index 645abcd8..4f6821d3 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -26,29 +26,36 @@ add_executable(wxAutoExcel_tests catch_wx_string_makers.h excel_test_fixture.h getter_lists.h + temp_files.h wxExcel_getters.cpp wxExcel_iterators.cpp wxExcel_setters.cpp wxExcelApplication.cpp wxExcelChart.cpp + wxExcelFillFormat.cpp wxExcelFormatConditions.cpp wxExcelListObject.cpp wxExcelNames.cpp wxExcelObject_errors.cpp wxExcelPageSetup.cpp + wxExcelProtection.cpp wxExcelRange_access.cpp wxExcelRange_find.cpp wxExcelRange_formula.cpp wxExcelRange_format.cpp wxExcelRange_merge.cpp + wxExcelRange_methods.cpp wxExcelRange_objects.cpp wxExcelRange_operations.cpp wxExcelRangeData.cpp wxExcelRange_value.cpp wxExcelShape.cpp + wxExcelShape_formats.cpp wxExcelSheets.cpp wxExcelSortFilter.cpp wxExcelWorkbook.cpp + wxExcelWorkbook_objects.cpp + wxExcelWindow.cpp wxExcelWorksheet.cpp tests.rc ) diff --git a/tests/README.md b/tests/README.md index 2f610f95..318bc2b7 100644 --- a/tests/README.md +++ b/tests/README.md @@ -22,20 +22,23 @@ The test executable creates one hidden Excel instance and reuses it for the entire run. Each test case receives a new temporary unsaved workbook, which is closed when that test case finishes. The tests cover scalar and rectangular range values, range acquisition and relative addressing, formulas, range -formatting, merged ranges, worksheet creation, ordering, naming, copying, and -deletion, chart sheets, workbooks saved and opened again in a temporary folder, -workbook protection, document properties, tables, names, sorting and -filtering, validation, hyperlinks, comments, page setup, conditional -formatting, charts, shapes, transferring the values and formulas of all -cells at once, finding and replacing, and iterating over collections and -ranges. They are registered as serial tests to avoid concurrent Excel -automation. +formatting and gradients, borders, data series, names, outlines, merged +ranges, worksheet creation, ordering, naming, copying, and deletion, chart +sheets, workbooks saved and opened again in a temporary folder, links between +workbooks, workbook and worksheet protection, ranges editable on protected +worksheets, document and custom properties, cell errors, tables and table +styles, sorting and filtering, validation, hyperlinks, comments, page setup, +conditional formatting, charts, error bars, trendlines, shapes of all kinds +and their formats, form controls, OLE objects, windows and their panes, +calculation, custom lists, transferring the values and formulas of all cells +at once, finding and replacing, and iterating over collections and ranges. +They are registered as serial tests to avoid concurrent Excel automation. ## Getter and setter smoke tests -*wxExcel_getters.cpp* creates objects of about 85 classes (charts, shapes, -tables, conditional formats, ranges with different values in their cells, -page setup, and more) and calls every getter which takes no arguments, +*wxExcel_getters.cpp* creates objects of about 170 classes (charts and +their elements, sparklines, shapes, tables, conditional formats, ranges with +different values in their cells, windows, protection, page setup, and more) and calls every getter which takes no arguments, checking only that the call succeeds. Then it sets every property which has such a getter to the value the getter returned. This finds wrappers using a wrong member name, result type, or argument, which make the getter or the diff --git a/tests/getter_lists.h b/tests/getter_lists.h index f9ff8b0a..f15090bc 100644 --- a/tests/getter_lists.h +++ b/tests/getter_lists.h @@ -265,6 +265,14 @@ #define WXAUTOEXCEL_GETTERS_wxExcelWorkbook_1(CHECK, object) #endif +#if WXAUTOEXCEL_USE_CONDFORMAT +#define WXAUTOEXCEL_GETTERS_wxExcelWorkbook_2(CHECK, object) \ + CHECK(object, GetIconSets) \ + /* end */ +#else +#define WXAUTOEXCEL_GETTERS_wxExcelWorkbook_2(CHECK, object) +#endif + #define WXAUTOEXCEL_GETTERS_wxExcelWorkbook(CHECK, object) \ CHECK(object, GetActiveSheet) \ CHECK(object, GetAccuracyVersion) \ @@ -333,7 +341,8 @@ CHECK(object, GetWriteReserved) \ CHECK(object, GetWriteReservedBy) \ WXAUTOEXCEL_GETTERS_wxExcelWorkbook_1(CHECK, object) \ - /* 68 getters */ + WXAUTOEXCEL_GETTERS_wxExcelWorkbook_2(CHECK, object) \ + /* 69 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelWorkbook(CHECK, object) \ CHECK(object, AccuracyVersion) \ @@ -603,6 +612,359 @@ CHECK(object, WrapText) \ /* 18 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelCustomProperties(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelCustomProperties(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelCustomProperty(CHECK, object) \ + CHECK(object, GetName) \ + CHECK(object, GetValue) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelCustomProperty(CHECK, object) \ + /* SetName: Excel fails setting the value it returns */ \ + CHECK(object, Value) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelErrors(CHECK, object) \ + /* 0 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelErrors(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelError(CHECK, object) \ + CHECK(object, GetIgnore) \ + CHECK(object, GetValue) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelError(CHECK, object) \ + CHECK(object, Ignore) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelErrorCheckingOptions(CHECK, object) \ + CHECK(object, GetBackgroundChecking) \ + CHECK(object, GetEmptyCellReferences) \ + CHECK(object, GetEvaluateToError) \ + CHECK(object, GetInconsistentFormula) \ + CHECK(object, GetInconsistentTableFormula) \ + CHECK(object, GetIndicatorColorIndex) \ + CHECK(object, GetListDataValidation) \ + CHECK(object, GetNumberAsText) \ + CHECK(object, GetOmittedCells) \ + CHECK(object, GetTextDate) \ + CHECK(object, GetUnlockedFormulaCells) \ + /* 11 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelErrorCheckingOptions(CHECK, object) \ + CHECK(object, BackgroundChecking) \ + CHECK(object, EmptyCellReferences) \ + CHECK(object, EvaluateToError) \ + CHECK(object, InconsistentFormula) \ + CHECK(object, InconsistentTableFormula) \ + CHECK(object, IndicatorColorIndex) \ + CHECK(object, ListDataValidation) \ + CHECK(object, NumberAsText) \ + CHECK(object, OmittedCells) \ + CHECK(object, TextDate) \ + CHECK(object, UnlockedFormulaCells) \ + /* 11 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelMultiThreadedCalculation(CHECK, object) \ + CHECK(object, GetEnabled) \ + CHECK(object, GetThreadCount) \ + CHECK(object, GetThreadMode) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelMultiThreadedCalculation(CHECK, object) \ + CHECK(object, Enabled) \ + CHECK(object, ThreadMode) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTableStyles(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTableStyles(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTableStyleElements(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTableStyleElements(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTableStyleElement(CHECK, object) \ + CHECK(object, GetBorders) \ + CHECK(object, GetFont) \ + CHECK(object, GetHasFormat) \ + CHECK(object, GetInterior) \ + /* GetStripeSize: fails for the elements of a custom table style */ \ + /* 5 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTableStyleElement(CHECK, object) \ + /* SetStripeSize: the getter is excluded */ \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelOLEObjects(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelOLEObjects(CHECK, object) \ + /* 0 setters */ + +#if WXAUTOEXCEL_USE_SHAPES +#define WXAUTOEXCEL_GETTERS_wxExcelOLEObject_1(CHECK, object) \ + CHECK(object, GetShapeRange) \ + /* end */ +#else +#define WXAUTOEXCEL_GETTERS_wxExcelOLEObject_1(CHECK, object) +#endif + +#define WXAUTOEXCEL_GETTERS_wxExcelOLEObject(CHECK, object) \ + CHECK(object, GetAutoLoad) \ + /* GetAutoUpdate: only for linked OLE objects, the test embeds a file */ \ + CHECK(object, GetBorder) \ + CHECK(object, GetBottomRightCell) \ + CHECK(object, GetEnabled) \ + CHECK(object, GetHeight) \ + CHECK(object, GetIndex) \ + CHECK(object, GetInterior) \ + CHECK(object, GetLeft) \ + /* GetLinkedCell: only for ActiveX controls, the test embeds a file */ \ + /* GetListFillRange: only for ActiveX controls, the test embeds a file */ \ + CHECK(object, GetLocked) \ + CHECK(object, GetName) \ + CHECK(object, GetOLEType) \ + CHECK(object, GetPlacement) \ + CHECK(object, GetPrintObject) \ + CHECK(object, GetprogID) \ + CHECK(object, GetShadow) \ + /* GetSourceName: only for linked OLE objects, the test embeds a file */ \ + CHECK(object, GetTop) \ + CHECK(object, GetTopLeftCell) \ + CHECK(object, GetVisible) \ + CHECK(object, GetWidth) \ + CHECK(object, GetZOrder) \ + WXAUTOEXCEL_GETTERS_wxExcelOLEObject_1(CHECK, object) \ + /* 25 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelOLEObject(CHECK, object) \ + CHECK(object, AutoLoad) \ + CHECK(object, Enabled) \ + CHECK(object, Height) \ + CHECK(object, Left) \ + /* SetLinkedCell: the getter is excluded */ \ + /* SetListFillRange: the getter is excluded */ \ + CHECK(object, Locked) \ + CHECK(object, Name) \ + CHECK(object, Placement) \ + CHECK(object, PrintObject) \ + CHECK(object, Shadow) \ + /* SetSourceName: the getter is excluded */ \ + CHECK(object, Top) \ + CHECK(object, Visible) \ + CHECK(object, Width) \ + /* 15 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelWindows(CHECK, object) \ + CHECK(object, GetCount) \ + CHECK(object, GetSyncScrollingSideBySide) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelWindows(CHECK, object) \ + CHECK(object, SyncScrollingSideBySide) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelWindow(CHECK, object) \ + CHECK(object, GetActiveCell) \ + CHECK(object, GetActivePane) \ + CHECK(object, GetActiveSheet) \ + CHECK(object, GetAutoFilterDateGrouping) \ + CHECK(object, GetCaption) \ + CHECK(object, GetDisplayFormulas) \ + CHECK(object, GetDisplayGridlines) \ + CHECK(object, GetDisplayHeadings) \ + CHECK(object, GetDisplayHorizontalScrollBar) \ + CHECK(object, GetDisplayOutline) \ + CHECK(object, GetDisplayRightToLeft) \ + CHECK(object, GetDisplayRuler) \ + CHECK(object, GetDisplayVerticalScrollBar) \ + CHECK(object, GetDisplayWhitespace) \ + CHECK(object, GetDisplayWorkbookTabs) \ + CHECK(object, GetDisplayZeros) \ + CHECK(object, GetEnableResize) \ + CHECK(object, GetFreezePanes) \ + CHECK(object, GetGridlineColor) \ + CHECK(object, GetGridlineColorIndex) \ + CHECK(object, GetHeight) \ + CHECK(object, GetIndex) \ + CHECK(object, GetLeft) \ + CHECK(object, GetPanes) \ + CHECK(object, GetRangeSelection) \ + CHECK(object, GetScrollColumn) \ + CHECK(object, GetScrollRow) \ + CHECK(object, GetSelectedSheets) \ + CHECK(object, GetSheetViews) \ + CHECK(object, GetSplit) \ + CHECK(object, GetSplitColumn) \ + CHECK(object, GetSplitHorizontal) \ + CHECK(object, GetSplitRow) \ + CHECK(object, GetSplitVertical) \ + CHECK(object, GetTabRatio) \ + CHECK(object, GetTop) \ + CHECK(object, GetType) \ + CHECK(object, GetUsableHeight) \ + CHECK(object, GetUsableWidth) \ + CHECK(object, GetView) \ + CHECK(object, GetVisible) \ + CHECK(object, GetVisibleRange) \ + CHECK(object, GetWidth) \ + CHECK(object, GetWindowNumber) \ + CHECK(object, GetWindowState) \ + CHECK(object, GetZoom) \ + /* 46 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelWindow(CHECK, object) \ + CHECK(object, AutoFilterDateGrouping) \ + CHECK(object, Caption) \ + CHECK(object, DisplayFormulas) \ + CHECK(object, DisplayGridlines) \ + CHECK(object, DisplayHeadings) \ + CHECK(object, DisplayHorizontalScrollBar) \ + CHECK(object, DisplayOutline) \ + CHECK(object, DisplayRightToLeft) \ + CHECK(object, DisplayRuler) \ + CHECK(object, DisplayVerticalScrollBar) \ + CHECK(object, DisplayWhitespace) \ + CHECK(object, DisplayWorkbookTabs) \ + CHECK(object, DisplayZeros) \ + CHECK(object, EnableResize) \ + CHECK(object, FreezePanes) \ + CHECK(object, GridlineColor) \ + CHECK(object, GridlineColorIndex) \ + CHECK(object, Height) \ + CHECK(object, Left) \ + CHECK(object, ScrollColumn) \ + CHECK(object, ScrollRow) \ + CHECK(object, Split) \ + CHECK(object, SplitColumn) \ + CHECK(object, SplitHorizontal) \ + CHECK(object, SplitRow) \ + CHECK(object, SplitVertical) \ + CHECK(object, TabRatio) \ + CHECK(object, Top) \ + CHECK(object, View) \ + CHECK(object, Visible) \ + CHECK(object, Width) \ + CHECK(object, WindowState) \ + CHECK(object, Zoom) \ + /* 33 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelPanes(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelPanes(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelPane(CHECK, object) \ + CHECK(object, GetIndex) \ + CHECK(object, GetScrollColumn) \ + CHECK(object, GetScrollRow) \ + CHECK(object, GetVisibleRange) \ + /* 4 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelPane(CHECK, object) \ + CHECK(object, ScrollColumn) \ + CHECK(object, ScrollRow) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSheetViews(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSheetViews(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSheetView(CHECK, object) \ + /* 0 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSheetView(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelWorksheetView(CHECK, object) \ + CHECK(object, GetDisplayFormulas) \ + CHECK(object, GetDisplayGridlines) \ + CHECK(object, GetDisplayHeadings) \ + CHECK(object, GetDisplayOutline) \ + CHECK(object, GetDisplayZeros) \ + CHECK(object, GetSheet) \ + /* 6 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelWorksheetView(CHECK, object) \ + CHECK(object, DisplayFormulas) \ + CHECK(object, DisplayGridlines) \ + CHECK(object, DisplayHeadings) \ + CHECK(object, DisplayOutline) \ + CHECK(object, DisplayZeros) \ + /* 5 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelProtection(CHECK, object) \ + CHECK(object, GetAllowDeletingColumns) \ + CHECK(object, GetAllowDeletingRows) \ + CHECK(object, GetAllowEditRanges) \ + CHECK(object, GetAllowFiltering) \ + CHECK(object, GetAllowFormattingCells) \ + CHECK(object, GetAllowFormattingColumns) \ + CHECK(object, GetAllowFormattingRows) \ + CHECK(object, GetAllowInsertingColumns) \ + CHECK(object, GetAllowInsertingHyperlinks) \ + CHECK(object, GetAllowInsertingRows) \ + CHECK(object, GetAllowSorting) \ + CHECK(object, GetAllowUsingPivotTables) \ + /* 12 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelProtection(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelAllowEditRanges(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelAllowEditRanges(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelAllowEditRange(CHECK, object) \ + CHECK(object, GetRange) \ + CHECK(object, GetTitle) \ + CHECK(object, GetUsers) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelAllowEditRange(CHECK, object) \ + CHECK(object, Range) \ + /* SetTitle: fails setting the title the range already has */ \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelUserAccessList(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelUserAccessList(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelUserAccess(CHECK, object) \ + CHECK(object, GetAllowEdit) \ + CHECK(object, GetName) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelUserAccess(CHECK, object) \ + CHECK(object, AllowEdit) \ + /* 1 setters */ + #if WXAUTOEXCEL_USE_CHARTS && WXAUTOEXCEL_USE_SHAPES #define WXAUTOEXCEL_GETTERS_wxExcelChartObjects_1(CHECK, object) \ CHECK(object, GetShapeRange) \ @@ -768,6 +1130,7 @@ #define WXAUTOEXCEL_GETTERS_wxExcelChartArea(CHECK, object) \ CHECK(object, GetAutoScaleFont) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetHeight) \ CHECK(object, GetLeft) \ @@ -776,7 +1139,7 @@ CHECK(object, GetShadow) \ CHECK(object, GetTop) \ CHECK(object, GetWidth) \ - /* 9 getters */ + /* 10 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelChartArea(CHECK, object) \ CHECK(object, AutoScaleFont) \ @@ -792,6 +1155,7 @@ CHECK(object, GetAutoScaleFont) \ CHECK(object, GetCaption) \ CHECK(object, GetCharacters) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetFormula) \ CHECK(object, GetFormulaLocal) \ @@ -810,7 +1174,7 @@ CHECK(object, GetTop) \ CHECK(object, GetVerticalAlignment) \ CHECK(object, GetWidth) \ - /* 21 getters */ + /* 22 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelChartTitle(CHECK, object) \ CHECK(object, AutoScaleFont) \ @@ -902,6 +1266,7 @@ /* 25 setters */ #define WXAUTOEXCEL_GETTERS_wxExcelPlotArea(CHECK, object) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetHeight) \ CHECK(object, GetInsideHeight) \ @@ -913,7 +1278,7 @@ CHECK(object, GetPosition) \ CHECK(object, GetTop) \ CHECK(object, GetWidth) \ - /* 11 getters */ + /* 12 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelPlotArea(CHECK, object) \ CHECK(object, Height) \ @@ -929,6 +1294,7 @@ #define WXAUTOEXCEL_GETTERS_wxExcelLegend(CHECK, object) \ CHECK(object, GetAutoScaleFont) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetHeight) \ CHECK(object, GetIncludeInLayout) \ @@ -938,7 +1304,7 @@ CHECK(object, GetShadow) \ CHECK(object, GetTop) \ CHECK(object, GetWidth) \ - /* 10 getters */ + /* 11 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelLegend(CHECK, object) \ CHECK(object, AutoScaleFont) \ @@ -1044,6 +1410,7 @@ CHECK(object, GetAutoScaleFont) \ CHECK(object, GetCaption) \ CHECK(object, GetCharacters) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetFormula) \ CHECK(object, GetFormulaLocal) \ @@ -1061,7 +1428,7 @@ CHECK(object, GetTop) \ CHECK(object, GetVerticalAlignment) \ CHECK(object, GetWidth) \ - /* 20 getters */ + /* 21 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelAxisTitle(CHECK, object) \ CHECK(object, AutoScaleFont) \ @@ -1089,6 +1456,13 @@ #define WXAUTOEXCEL_SETTERS_wxExcelSeriesCollection(CHECK, object) \ /* 0 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelFullSeriesCollection(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelFullSeriesCollection(CHECK, object) \ + /* 0 setters */ + #define WXAUTOEXCEL_GETTERS_wxExcelSeries(CHECK, object) \ /* GetApplyPictToEnd: only for picture fills */ \ /* GetApplyPictToFront: only for picture fills */ \ @@ -1099,6 +1473,7 @@ CHECK(object, GetChartType) \ /* GetErrorBars: only for series with error bars */ \ CHECK(object, GetExplosion) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetFormula) \ CHECK(object, GetFormulaLocal) \ @@ -1129,7 +1504,7 @@ CHECK(object, GetShadow) \ /* GetSmooth: only for line and scatter charts */ \ CHECK(object, GetType) \ - /* 39 getters */ + /* 40 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelSeries(CHECK, object) \ /* SetApplyPictToEnd: the getter is excluded */ \ @@ -1183,6 +1558,7 @@ /* GetApplyPictToSides: only for picture fills */ \ CHECK(object, GetDataLabel) \ CHECK(object, GetExplosion) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetHas3DEffect) \ CHECK(object, GetHasDataLabel) \ @@ -1199,7 +1575,7 @@ CHECK(object, GetPictureUnit2) \ /* GetSecondaryPlot: only for pie of pie and bar of pie charts */ \ CHECK(object, GetShadow) \ - /* 21 getters */ + /* 22 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelPoint(CHECK, object) \ /* SetApplyPictToEnd: the getter is excluded */ \ @@ -1227,6 +1603,7 @@ CHECK(object, GetAutoScaleFont) \ CHECK(object, GetAutoText) \ CHECK(object, GetCount) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetHorizontalAlignment) \ CHECK(object, GetName) \ @@ -1246,7 +1623,7 @@ CHECK(object, GetShowSeriesName) \ CHECK(object, GetShowValue) \ CHECK(object, GetVerticalAlignment) \ - /* 22 getters */ + /* 23 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelDataLabels(CHECK, object) \ CHECK(object, AutoScaleFont) \ @@ -1275,6 +1652,7 @@ CHECK(object, GetAutoText) \ CHECK(object, GetCaption) \ CHECK(object, GetCharacters) \ + CHECK(object, GetFill) \ CHECK(object, GetFormat) \ CHECK(object, GetHorizontalAlignment) \ CHECK(object, GetLeft) \ @@ -1297,7 +1675,7 @@ CHECK(object, GetText) \ CHECK(object, GetTop) \ CHECK(object, GetVerticalAlignment) \ - /* 26 getters */ + /* 27 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelDataLabel(CHECK, object) \ CHECK(object, AutoScaleFont) \ @@ -1325,72 +1703,515 @@ CHECK(object, VerticalAlignment) \ /* 23 setters */ -#define WXAUTOEXCEL_GETTERS_wxExcelShapes(CHECK, object) \ - CHECK(object, GetCount) \ - /* 1 getters */ - -#define WXAUTOEXCEL_SETTERS_wxExcelShapes(CHECK, object) \ - /* 0 setters */ - -#if WXAUTOEXCEL_USE_SHAPES && WXAUTOEXCEL_USE_CHARTS -#define WXAUTOEXCEL_GETTERS_wxExcelShape_1(CHECK, object) \ - /* GetChart: only for chart shapes */ \ - /* end */ -#else -#define WXAUTOEXCEL_GETTERS_wxExcelShape_1(CHECK, object) -#endif - -#define WXAUTOEXCEL_GETTERS_wxExcelShape(CHECK, object) \ - CHECK(object, GetAdjustments) \ - CHECK(object, GetAlternativeText) \ - CHECK(object, GetAutoShapeType) \ - CHECK(object, GetBackgroundStyle) \ - CHECK(object, GetBlackWhiteMode) \ - CHECK(object, GetBottomRightCell) \ - CHECK(object, GetCallout) \ - CHECK(object, GetChild) \ - CHECK(object, GetConnectionSiteCount) \ - CHECK(object, GetConnector) \ - CHECK(object, GetConnectorFormat) \ - CHECK(object, GetControlFormat) \ +#define WXAUTOEXCEL_GETTERS_wxExcelChartFormat(CHECK, object) \ + /* GetAdjustments: only for shapes, the test uses the format of a series */ \ + /* GetAutoShapeType: only for shapes, the test uses the format of a series */ \ CHECK(object, GetFill) \ - /* GetFormControlType: only for form controls */ \ CHECK(object, GetGlow) \ - CHECK(object, GetGraphicStyle) \ - /* GetGroupItems: only for groups */ \ - CHECK(object, GetHasChart) \ - CHECK(object, GetHeight) \ - CHECK(object, GetHorizontalFlip) \ - /* GetHyperlink: fails when the shape has no hyperlink */ \ - CHECK(object, GetID) \ - CHECK(object, GetLeft) \ CHECK(object, GetLine) \ - CHECK(object, GetLinkFormat) \ - CHECK(object, GetLockAspectRatio) \ - CHECK(object, GetLocked) \ - CHECK(object, GetModel3D) \ - CHECK(object, GetName) \ - CHECK(object, GetNodes) \ - CHECK(object, GetOLEFormat) \ - CHECK(object, GetOnAction) \ - /* GetParentGroup: only for shapes in a group */ \ CHECK(object, GetPictureFormat) \ - CHECK(object, GetPlacement) \ - CHECK(object, GetReflection) \ - CHECK(object, GetRotation) \ CHECK(object, GetShadow) \ - CHECK(object, GetShapeStyle) \ CHECK(object, GetSoftEdge) \ - CHECK(object, GetTextEffect) \ - CHECK(object, GetTextFrame) \ - CHECK(object, GetTextFrame2) \ + /* GetTextFrame2: only for shapes, the test uses the format of a series */ \ CHECK(object, GetThreeD) \ - CHECK(object, GetTop) \ - CHECK(object, GetTopLeftCell) \ - CHECK(object, GetType) \ - CHECK(object, GetVerticalFlip) \ - CHECK(object, GetVertices) \ - CHECK(object, GetVisible) \ + /* 10 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelChartFormat(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelChartFillFormat(CHECK, object) \ + CHECK(object, GetBackColor) \ + CHECK(object, GetForeColor) \ + CHECK(object, GetGradientColorType) \ + /* GetGradientDegree: only for gradient fills */ \ + CHECK(object, GetGradientStyle) \ + CHECK(object, GetGradientVariant) \ + CHECK(object, GetPattern) \ + CHECK(object, GetPresetGradientType) \ + CHECK(object, GetPresetTexture) \ + /* GetTextureName: only for texture fills */ \ + CHECK(object, GetTextureType) \ + CHECK(object, GetType) \ + CHECK(object, GetVisible) \ + /* 13 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelChartFillFormat(CHECK, object) \ + CHECK(object, Visible) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelChartColorFormat(CHECK, object) \ + CHECK(object, GetRGB) \ + CHECK(object, GetSchemeColor) \ + CHECK(object, GetType) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelChartColorFormat(CHECK, object) \ + CHECK(object, SchemeColor) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelErrorBars(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetEndStyle) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 4 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelErrorBars(CHECK, object) \ + CHECK(object, EndStyle) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTrendlines(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTrendlines(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTrendline(CHECK, object) \ + CHECK(object, GetBackward) \ + CHECK(object, GetBackward2) \ + CHECK(object, GetBorder) \ + CHECK(object, GetDataLabel) \ + CHECK(object, GetDisplayEquation) \ + CHECK(object, GetDisplayRSquared) \ + CHECK(object, GetFormat) \ + CHECK(object, GetForward) \ + CHECK(object, GetForward2) \ + CHECK(object, GetIndex) \ + CHECK(object, GetIntercept) \ + CHECK(object, GetInterceptIsAuto) \ + CHECK(object, GetName) \ + CHECK(object, GetNameIsAuto) \ + CHECK(object, GetOrder) \ + CHECK(object, GetPeriod) \ + CHECK(object, GetType) \ + /* 17 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTrendline(CHECK, object) \ + CHECK(object, Backward) \ + CHECK(object, Backward2) \ + CHECK(object, DisplayEquation) \ + CHECK(object, DisplayRSquared) \ + CHECK(object, Forward) \ + CHECK(object, Forward2) \ + CHECK(object, Intercept) \ + CHECK(object, InterceptIsAuto) \ + CHECK(object, Name) \ + CHECK(object, NameIsAuto) \ + CHECK(object, Order) \ + /* SetPeriod: only for moving average trendlines, the test uses a linear one */ \ + CHECK(object, Type) \ + /* 13 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTickLabels(CHECK, object) \ + /* GetAlignment: only for category axes, the test uses the value axis */ \ + CHECK(object, GetAutoScaleFont) \ + CHECK(object, GetDepth) \ + CHECK(object, GetFont) \ + CHECK(object, GetFormat) \ + /* GetMultiLevel: only for category axes, the test uses the value axis */ \ + CHECK(object, GetName) \ + CHECK(object, GetNumberformat) \ + CHECK(object, GetNumberFormatLinked) \ + CHECK(object, GetNumberformatLocal) \ + CHECK(object, GetOffset) \ + CHECK(object, GetOrientation) \ + CHECK(object, GetReadingOrder) \ + /* 13 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTickLabels(CHECK, object) \ + /* SetAlignment: the getter is excluded */ \ + CHECK(object, AutoScaleFont) \ + /* SetMultiLevel: the getter is excluded */ \ + CHECK(object, Numberformat) \ + CHECK(object, NumberFormatLinked) \ + CHECK(object, NumberformatLocal) \ + CHECK(object, Offset) \ + CHECK(object, Orientation) \ + CHECK(object, ReadingOrder) \ + /* 9 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelGridlines(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelGridlines(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelLegendEntries(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelLegendEntries(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelLegendEntry(CHECK, object) \ + CHECK(object, GetAutoScaleFont) \ + CHECK(object, GetFont) \ + CHECK(object, GetFormat) \ + CHECK(object, GetHeight) \ + CHECK(object, GetIndex) \ + CHECK(object, GetLeft) \ + CHECK(object, GetLegendKey) \ + CHECK(object, GetTop) \ + CHECK(object, GetWidth) \ + /* 9 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelLegendEntry(CHECK, object) \ + CHECK(object, AutoScaleFont) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelLegendKey(CHECK, object) \ + CHECK(object, GetFill) \ + CHECK(object, GetFormat) \ + CHECK(object, GetHeight) \ + CHECK(object, GetInvertIfNegative) \ + CHECK(object, GetLeft) \ + /* GetMarkerBackgroundColor: only for chart types with markers */ \ + /* GetMarkerBackgroundColorIndex: only for chart types with markers */ \ + /* GetMarkerForegroundColor: only for chart types with markers */ \ + /* GetMarkerForegroundColorIndex: only for chart types with markers */ \ + CHECK(object, GetMarkerSize) \ + CHECK(object, GetMarkerStyle) \ + CHECK(object, GetPictureType) \ + CHECK(object, GetPictureUnit) \ + CHECK(object, GetPictureUnit2) \ + CHECK(object, GetShadow) \ + /* GetSmooth: only for line and scatter charts */ \ + CHECK(object, GetTop) \ + CHECK(object, GetWidth) \ + /* 18 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelLegendKey(CHECK, object) \ + CHECK(object, InvertIfNegative) \ + /* SetMarkerBackgroundColor: the getter is excluded */ \ + /* SetMarkerBackgroundColorIndex: the getter is excluded */ \ + /* SetMarkerForegroundColor: the getter is excluded */ \ + /* SetMarkerForegroundColorIndex: the getter is excluded */ \ + CHECK(object, MarkerSize) \ + CHECK(object, MarkerStyle) \ + /* SetPictureType: only for picture fills */ \ + /* SetPictureUnit: only for picture fills */ \ + /* SetPictureUnit2: only for picture fills */ \ + CHECK(object, Shadow) \ + /* SetSmooth: the getter is excluded */ \ + /* 12 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelDataTable(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetFont) \ + CHECK(object, GetFormat) \ + CHECK(object, GetHasBorderHorizontal) \ + CHECK(object, GetHasBorderOutline) \ + CHECK(object, GetHasBorderVertical) \ + CHECK(object, GetShowLegendKey) \ + /* 7 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelDataTable(CHECK, object) \ + CHECK(object, HasBorderHorizontal) \ + CHECK(object, HasBorderOutline) \ + CHECK(object, HasBorderVertical) \ + CHECK(object, ShowLegendKey) \ + /* 4 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelDisplayUnitLabel(CHECK, object) \ + CHECK(object, GetAutoScaleFont) \ + CHECK(object, GetCaption) \ + CHECK(object, GetCharacters) \ + CHECK(object, GetFill) \ + CHECK(object, GetFormat) \ + CHECK(object, GetHorizontalAlignment) \ + CHECK(object, GetLeft) \ + CHECK(object, GetName) \ + CHECK(object, GetOrientation) \ + CHECK(object, GetPosition) \ + CHECK(object, GetReadingOrder) \ + CHECK(object, GetShadow) \ + CHECK(object, GetText) \ + CHECK(object, GetTop) \ + CHECK(object, GetVerticalAlignment) \ + /* 15 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelDisplayUnitLabel(CHECK, object) \ + CHECK(object, AutoScaleFont) \ + CHECK(object, Caption) \ + CHECK(object, HorizontalAlignment) \ + CHECK(object, Left) \ + CHECK(object, Orientation) \ + CHECK(object, Position) \ + CHECK(object, ReadingOrder) \ + CHECK(object, Shadow) \ + CHECK(object, Text) \ + CHECK(object, Top) \ + CHECK(object, VerticalAlignment) \ + /* 11 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelFloor(CHECK, object) \ + CHECK(object, GetFill) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + CHECK(object, GetPictureType) \ + CHECK(object, GetThickness) \ + /* 5 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelFloor(CHECK, object) \ + /* SetPictureType: only for picture fills */ \ + CHECK(object, Thickness) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelWalls(CHECK, object) \ + CHECK(object, GetFill) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + CHECK(object, GetPictureType) \ + /* GetPictureUnit: only for picture fills */ \ + CHECK(object, GetThickness) \ + /* 6 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelWalls(CHECK, object) \ + /* SetPictureType: only for picture fills */ \ + /* SetPictureUnit: the getter is excluded */ \ + CHECK(object, Thickness) \ + /* 3 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelUpBars(CHECK, object) \ + CHECK(object, GetFill) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelUpBars(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelDownBars(CHECK, object) \ + CHECK(object, GetFill) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelDownBars(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelHiLoLines(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelHiLoLines(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelDropLines(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelDropLines(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSeriesLines(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetFormat) \ + CHECK(object, GetName) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSeriesLines(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelLeaderLines(CHECK, object) \ + CHECK(object, GetBorder) \ + CHECK(object, GetFormat) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelLeaderLines(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelCategoryCollection(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelCategoryCollection(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelChartCategory(CHECK, object) \ + CHECK(object, GetIsFiltered) \ + CHECK(object, GetName) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelChartCategory(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparklineGroups(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparklineGroups(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparklineGroup(CHECK, object) \ + CHECK(object, GetAxes) \ + CHECK(object, GetCount) \ + /* GetDateRange: only for sparklines with a date axis */ \ + CHECK(object, GetDisplayBlanksAs) \ + CHECK(object, GetDisplayHidden) \ + CHECK(object, GetLineWeight) \ + CHECK(object, GetLocation) \ + CHECK(object, GetPlotBy) \ + CHECK(object, GetPoints) \ + CHECK(object, GetSeriesColor) \ + CHECK(object, GetSourceData) \ + CHECK(object, GetType) \ + /* 12 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparklineGroup(CHECK, object) \ + /* SetDateRange: the getter is excluded */ \ + CHECK(object, DisplayBlanksAs) \ + CHECK(object, DisplayHidden) \ + CHECK(object, LineWeight) \ + CHECK(object, Location) \ + /* SetPlotBy: Excel fails setting the value it returns */ \ + CHECK(object, SourceData) \ + CHECK(object, Type) \ + /* 8 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparkline(CHECK, object) \ + CHECK(object, GetLocation) \ + CHECK(object, GetParent) \ + CHECK(object, GetSourceData) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparkline(CHECK, object) \ + CHECK(object, Location) \ + CHECK(object, SourceData) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparkAxes(CHECK, object) \ + CHECK(object, GetHorizontal) \ + CHECK(object, GetParent) \ + CHECK(object, GetVertical) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparkAxes(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparkHorizontalAxis(CHECK, object) \ + CHECK(object, GetAxis) \ + CHECK(object, GetIsDateAxis) \ + CHECK(object, GetParent) \ + CHECK(object, GetRightToLeftPlotOrder) \ + /* 4 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparkHorizontalAxis(CHECK, object) \ + CHECK(object, RightToLeftPlotOrder) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparkVerticalAxis(CHECK, object) \ + CHECK(object, GetCustomMaxScaleValue) \ + CHECK(object, GetCustomMinScaleValue) \ + CHECK(object, GetMaxScaleType) \ + CHECK(object, GetMinScaleType) \ + CHECK(object, GetParent) \ + /* 5 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparkVerticalAxis(CHECK, object) \ + CHECK(object, CustomMaxScaleValue) \ + CHECK(object, CustomMinScaleValue) \ + CHECK(object, MaxScaleType) \ + CHECK(object, MinScaleType) \ + /* 4 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparkColor(CHECK, object) \ + CHECK(object, GetColor) \ + CHECK(object, GetParent) \ + CHECK(object, GetVisible) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparkColor(CHECK, object) \ + CHECK(object, Visible) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSparkPoints(CHECK, object) \ + CHECK(object, GetFirstpoint) \ + CHECK(object, GetHighpoint) \ + CHECK(object, GetLastpoint) \ + CHECK(object, GetLowpoint) \ + CHECK(object, GetMarkers) \ + CHECK(object, GetNegative) \ + CHECK(object, GetParent) \ + /* 7 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSparkPoints(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelShapes(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelShapes(CHECK, object) \ + /* 0 setters */ + +#if WXAUTOEXCEL_USE_SHAPES && WXAUTOEXCEL_USE_CHARTS +#define WXAUTOEXCEL_GETTERS_wxExcelShape_1(CHECK, object) \ + /* GetChart: only for chart shapes */ \ + /* end */ +#else +#define WXAUTOEXCEL_GETTERS_wxExcelShape_1(CHECK, object) +#endif + +#define WXAUTOEXCEL_GETTERS_wxExcelShape(CHECK, object) \ + CHECK(object, GetAdjustments) \ + CHECK(object, GetAlternativeText) \ + CHECK(object, GetAutoShapeType) \ + CHECK(object, GetBackgroundStyle) \ + CHECK(object, GetBlackWhiteMode) \ + CHECK(object, GetBottomRightCell) \ + CHECK(object, GetCallout) \ + CHECK(object, GetChild) \ + CHECK(object, GetConnectionSiteCount) \ + CHECK(object, GetConnector) \ + CHECK(object, GetConnectorFormat) \ + CHECK(object, GetControlFormat) \ + CHECK(object, GetFill) \ + /* GetFormControlType: only for form controls */ \ + CHECK(object, GetGlow) \ + CHECK(object, GetGraphicStyle) \ + /* GetGroupItems: only for groups */ \ + CHECK(object, GetHasChart) \ + CHECK(object, GetHeight) \ + CHECK(object, GetHorizontalFlip) \ + /* GetHyperlink: fails when the shape has no hyperlink */ \ + CHECK(object, GetID) \ + CHECK(object, GetLeft) \ + CHECK(object, GetLine) \ + CHECK(object, GetLinkFormat) \ + CHECK(object, GetLockAspectRatio) \ + CHECK(object, GetLocked) \ + CHECK(object, GetModel3D) \ + CHECK(object, GetName) \ + CHECK(object, GetNodes) \ + CHECK(object, GetOLEFormat) \ + CHECK(object, GetOnAction) \ + /* GetParentGroup: only for shapes in a group */ \ + CHECK(object, GetPictureFormat) \ + CHECK(object, GetPlacement) \ + CHECK(object, GetReflection) \ + CHECK(object, GetRotation) \ + CHECK(object, GetShadow) \ + CHECK(object, GetShapeStyle) \ + CHECK(object, GetSoftEdge) \ + CHECK(object, GetTextEffect) \ + CHECK(object, GetTextFrame) \ + CHECK(object, GetTextFrame2) \ + CHECK(object, GetThreeD) \ + CHECK(object, GetTop) \ + CHECK(object, GetTopLeftCell) \ + CHECK(object, GetType) \ + CHECK(object, GetVerticalFlip) \ + CHECK(object, GetVertices) \ + CHECK(object, GetVisible) \ CHECK(object, GetWidth) \ CHECK(object, GetZOrderPosition) \ WXAUTOEXCEL_GETTERS_wxExcelShape_1(CHECK, object) \ @@ -1626,6 +2447,7 @@ CHECK(object, GetForeColor) \ CHECK(object, GetGradientColorType) \ /* GetGradientDegree: only for gradient fills */ \ + CHECK(object, GetGradientStops) \ CHECK(object, GetGradientStyle) \ CHECK(object, GetGradientVariant) \ CHECK(object, GetPattern) \ @@ -1643,7 +2465,7 @@ CHECK(object, GetTransparency) \ CHECK(object, GetType) \ CHECK(object, GetVisible) \ - /* 21 getters */ + /* 22 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelFillFormat(CHECK, object) \ /* SetRotateWithObject: Excel fails setting the value it returns */ \ @@ -1657,6 +2479,24 @@ CHECK(object, Visible) \ /* 9 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelGradientStops(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelGradientStops(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelGradientStop(CHECK, object) \ + CHECK(object, GetColor) \ + CHECK(object, GetPosition) \ + CHECK(object, GetTransparency) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelGradientStop(CHECK, object) \ + CHECK(object, Position) \ + CHECK(object, Transparency) \ + /* 2 setters */ + #define WXAUTOEXCEL_GETTERS_wxExcelLineFormat(CHECK, object) \ CHECK(object, GetBackColor) \ CHECK(object, GetBeginArrowheadLength) \ @@ -1765,6 +2605,322 @@ CHECK(object, Z) \ /* 23 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelTextFrame(CHECK, object) \ + CHECK(object, GetAutoSize) \ + CHECK(object, GetHorizontalAlignment) \ + CHECK(object, GetMarginBottom) \ + CHECK(object, GetMarginLeft) \ + CHECK(object, GetMarginRight) \ + CHECK(object, GetMarginTop) \ + CHECK(object, GetOrientation) \ + CHECK(object, GetReadingOrder) \ + CHECK(object, GetVerticalAlignment) \ + /* 9 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTextFrame(CHECK, object) \ + CHECK(object, AutoSize) \ + CHECK(object, HorizontalAlignment) \ + CHECK(object, MarginBottom) \ + CHECK(object, MarginLeft) \ + CHECK(object, MarginRight) \ + CHECK(object, MarginTop) \ + CHECK(object, Orientation) \ + /* SetReadingOrder: Excel fails setting the value it returns */ \ + CHECK(object, VerticalAlignment) \ + /* 9 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelShadowFormat(CHECK, object) \ + CHECK(object, GetBlur) \ + CHECK(object, GetForeColor) \ + CHECK(object, GetObscured) \ + CHECK(object, GetOffsetX) \ + CHECK(object, GetOffsetY) \ + CHECK(object, GetRotateWithShape) \ + CHECK(object, GetSize) \ + CHECK(object, GetStyle) \ + CHECK(object, GetTransparency) \ + CHECK(object, GetType) \ + CHECK(object, GetVisible) \ + /* 11 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelShadowFormat(CHECK, object) \ + CHECK(object, Blur) \ + CHECK(object, ForeColor) \ + CHECK(object, Obscured) \ + CHECK(object, OffsetX) \ + CHECK(object, OffsetY) \ + CHECK(object, RotateWithShape) \ + CHECK(object, Size) \ + CHECK(object, Style) \ + CHECK(object, Transparency) \ + /* SetType: fails setting msoShadowMixed which Excel returns */ \ + CHECK(object, Visible) \ + /* 11 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelGlowFormat(CHECK, object) \ + CHECK(object, GetColor) \ + CHECK(object, GetRadius) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelGlowFormat(CHECK, object) \ + CHECK(object, Radius) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelSoftEdgeFormat(CHECK, object) \ + CHECK(object, GetType) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelSoftEdgeFormat(CHECK, object) \ + CHECK(object, Type) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelReflectionFormat(CHECK, object) \ + CHECK(object, GetType) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelReflectionFormat(CHECK, object) \ + CHECK(object, Type) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTextColumn2(CHECK, object) \ + CHECK(object, GetNumber) \ + CHECK(object, GetSpacing) \ + CHECK(object, GetTextDirection) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTextColumn2(CHECK, object) \ + CHECK(object, Number) \ + CHECK(object, Spacing) \ + CHECK(object, TextDirection) \ + /* 3 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelParagraphFormat2(CHECK, object) \ + CHECK(object, GetAlignment) \ + CHECK(object, GetBaselineAlignment) \ + CHECK(object, GetBullet) \ + CHECK(object, GetFarEastLineBreakLevel) \ + CHECK(object, GetFirstLineIndent) \ + CHECK(object, GetHangingPunctuation) \ + CHECK(object, GetIndentLevel) \ + CHECK(object, GetLeftIndent) \ + CHECK(object, GetLineRuleAfter) \ + CHECK(object, GetLineRuleBefore) \ + CHECK(object, GetLineRuleWithin) \ + CHECK(object, GetRightIndent) \ + CHECK(object, GetSpaceAfter) \ + CHECK(object, GetSpaceBefore) \ + CHECK(object, GetSpaceWithin) \ + CHECK(object, GetTabStops) \ + CHECK(object, GetTextDirection) \ + CHECK(object, GetWordWrap) \ + /* 18 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelParagraphFormat2(CHECK, object) \ + CHECK(object, Alignment) \ + CHECK(object, BaselineAlignment) \ + CHECK(object, FarEastLineBreakLevel) \ + CHECK(object, FirstLineIndent) \ + CHECK(object, HangingPunctuation) \ + CHECK(object, IndentLevel) \ + CHECK(object, LeftIndent) \ + CHECK(object, LineRuleAfter) \ + CHECK(object, LineRuleBefore) \ + CHECK(object, LineRuleWithin) \ + CHECK(object, RightIndent) \ + CHECK(object, SpaceAfter) \ + CHECK(object, SpaceBefore) \ + CHECK(object, SpaceWithin) \ + /* SetTextDirection: Excel fails setting the value it returns */ \ + CHECK(object, WordWrap) \ + /* 16 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelBulletFormat2(CHECK, object) \ + CHECK(object, GetCharacter) \ + CHECK(object, GetFont) \ + CHECK(object, GetNumber) \ + CHECK(object, GetRelativeSize) \ + CHECK(object, GetStartValue) \ + CHECK(object, GetStyle) \ + CHECK(object, GetType) \ + CHECK(object, GetUseTextColor) \ + CHECK(object, GetUseTextFont) \ + CHECK(object, GetVisible) \ + /* 10 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelBulletFormat2(CHECK, object) \ + CHECK(object, Character) \ + CHECK(object, RelativeSize) \ + CHECK(object, StartValue) \ + CHECK(object, Style) \ + CHECK(object, Type) \ + CHECK(object, UseTextColor) \ + CHECK(object, UseTextFont) \ + CHECK(object, Visible) \ + /* 8 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTabStops2(CHECK, object) \ + CHECK(object, GetCount) \ + CHECK(object, GetDefaultSpacing) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTabStops2(CHECK, object) \ + CHECK(object, DefaultSpacing) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTabStop2(CHECK, object) \ + CHECK(object, GetPosition) \ + CHECK(object, GetType) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTabStop2(CHECK, object) \ + CHECK(object, Position) \ + CHECK(object, Type) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelCalloutFormat(CHECK, object) \ + CHECK(object, GetAccent) \ + CHECK(object, GetAngle) \ + CHECK(object, GetAutoAttach) \ + CHECK(object, GetAutoLength) \ + CHECK(object, GetBorder) \ + CHECK(object, GetDrop) \ + CHECK(object, GetDropType) \ + CHECK(object, GetGap) \ + CHECK(object, GetLength) \ + CHECK(object, GetType) \ + /* 10 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelCalloutFormat(CHECK, object) \ + CHECK(object, Accent) \ + CHECK(object, Angle) \ + /* SetAutoAttach: Excel fails setting the value it returns */ \ + CHECK(object, Border) \ + CHECK(object, Gap) \ + CHECK(object, Type) \ + /* 6 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelConnectorFormat(CHECK, object) \ + CHECK(object, GetBeginConnected) \ + /* GetBeginConnectedShape: only for connectors connected to a shape */ \ + CHECK(object, GetBeginConnectionSite) \ + CHECK(object, GetEndConnected) \ + /* GetEndConnectedShape: only for connectors connected to a shape */ \ + CHECK(object, GetEndConnectionSite) \ + CHECK(object, GetType) \ + /* 7 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelConnectorFormat(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelControlFormat(CHECK, object) \ + /* GetDropDownLines: not for check boxes, the test uses one */ \ + CHECK(object, GetEnabled) \ + /* GetLargeChange: not for check boxes, the test uses one */ \ + CHECK(object, GetLinkedCell) \ + /* GetListCount: not for check boxes, the test uses one */ \ + /* GetListFillRange: not for check boxes, the test uses one */ \ + /* GetListIndex: not for check boxes, the test uses one */ \ + CHECK(object, GetLockedText) \ + /* GetMax: not for check boxes, the test uses one */ \ + /* GetMin: not for check boxes, the test uses one */ \ + /* GetMultiSelect: not for check boxes, the test uses one */ \ + CHECK(object, GetPrintObject) \ + /* GetSmallChange: not for check boxes, the test uses one */ \ + CHECK(object, GetValue) \ + /* 14 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelControlFormat(CHECK, object) \ + /* SetDropDownLines: the getter is excluded */ \ + CHECK(object, Enabled) \ + /* SetLargeChange: the getter is excluded */ \ + CHECK(object, LinkedCell) \ + /* SetListFillRange: the getter is excluded */ \ + /* SetListIndex: the getter is excluded */ \ + CHECK(object, LockedText) \ + /* SetMax: the getter is excluded */ \ + /* SetMin: the getter is excluded */ \ + /* SetMultiSelect: the getter is excluded */ \ + CHECK(object, PrintObject) \ + /* SetSmallChange: the getter is excluded */ \ + CHECK(object, Value) \ + /* 13 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelShapeNodes(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelShapeNodes(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelShapeNode(CHECK, object) \ + CHECK(object, GetEditingType) \ + CHECK(object, GetPoints) \ + CHECK(object, GetSegmentType) \ + /* 3 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelShapeNode(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelTextEffectFormat(CHECK, object) \ + CHECK(object, GetAlignment) \ + CHECK(object, GetFontBold) \ + CHECK(object, GetFontItalic) \ + CHECK(object, GetFontName) \ + CHECK(object, GetFontSize) \ + CHECK(object, GetKernedPairs) \ + CHECK(object, GetNormalizedHeight) \ + /* GetPresetShape: Excel fails getting it for a text effect added by AddTextEffect(), also in VBA */ \ + CHECK(object, GetPresetTextEffect) \ + CHECK(object, GetRotatedChars) \ + CHECK(object, GetText) \ + CHECK(object, GetTracking) \ + /* 12 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelTextEffectFormat(CHECK, object) \ + CHECK(object, FontBold) \ + CHECK(object, FontItalic) \ + CHECK(object, FontName) \ + CHECK(object, FontSize) \ + CHECK(object, KernedPairs) \ + CHECK(object, NormalizedHeight) \ + /* SetPresetShape: the getter is excluded */ \ + /* SetPresetTextEffect: Excel fails setting the value it returns */ \ + CHECK(object, RotatedChars) \ + CHECK(object, Text) \ + CHECK(object, Tracking) \ + /* 11 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelPictureFormat(CHECK, object) \ + CHECK(object, GetBrightness) \ + CHECK(object, GetColorType) \ + CHECK(object, GetContrast) \ + CHECK(object, GetCropBottom) \ + CHECK(object, GetCropLeft) \ + CHECK(object, GetCropRight) \ + CHECK(object, GetCropTop) \ + CHECK(object, GetTransparencyColor) \ + CHECK(object, GetTransparentBackground) \ + /* 9 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelPictureFormat(CHECK, object) \ + CHECK(object, Brightness) \ + CHECK(object, ColorType) \ + CHECK(object, Contrast) \ + CHECK(object, CropBottom) \ + CHECK(object, CropLeft) \ + CHECK(object, CropRight) \ + CHECK(object, CropTop) \ + CHECK(object, TransparencyColor) \ + CHECK(object, TransparentBackground) \ + /* 9 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelOLEFormat(CHECK, object) \ + CHECK(object, GetprogID) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelOLEFormat(CHECK, object) \ + /* 0 setters */ + #define WXAUTOEXCEL_GETTERS_wxExcelListObjects(CHECK, object) \ CHECK(object, GetCount) \ /* 1 getters */ @@ -1830,11 +2986,12 @@ #define WXAUTOEXCEL_GETTERS_wxExcelListColumn(CHECK, object) \ CHECK(object, GetDataBodyRange) \ CHECK(object, GetIndex) \ + CHECK(object, GetListDataFormat) \ CHECK(object, GetName) \ CHECK(object, GetRange) \ CHECK(object, GetTotal) \ CHECK(object, GetTotalsCalculation) \ - /* 6 getters */ + /* 7 getters */ #define WXAUTOEXCEL_SETTERS_wxExcelListColumn(CHECK, object) \ CHECK(object, Name) \ @@ -1856,6 +3013,24 @@ #define WXAUTOEXCEL_SETTERS_wxExcelListRow(CHECK, object) \ /* 0 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelListDataFormat(CHECK, object) \ + CHECK(object, GetAllowFillIn) \ + CHECK(object, GetChoices) \ + CHECK(object, GetDecimalPlaces) \ + CHECK(object, GetDefaultValue) \ + CHECK(object, GetIsPercent) \ + CHECK(object, Getlcid) \ + CHECK(object, GetMaxCharacters) \ + CHECK(object, GetMaxNumber) \ + CHECK(object, GetMinNumber) \ + CHECK(object, GetReadOnly) \ + CHECK(object, GetRequired) \ + CHECK(object, GetType) \ + /* 12 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelListDataFormat(CHECK, object) \ + /* 0 setters */ + #define WXAUTOEXCEL_GETTERS_wxExcelTableStyle(CHECK, object) \ CHECK(object, GetBuiltIn) \ CHECK(object, GetName) \ @@ -2176,6 +3351,63 @@ CHECK(object, Value) \ /* 3 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelFormatColor(CHECK, object) \ + CHECK(object, GetColor) \ + CHECK(object, GetColorIndex) \ + CHECK(object, GetThemeColor) \ + CHECK(object, GetTintAndShade) \ + /* 4 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelFormatColor(CHECK, object) \ + CHECK(object, Color) \ + CHECK(object, ColorIndex) \ + /* SetThemeColor: fails for a color without a theme color */ \ + CHECK(object, TintAndShade) \ + /* 4 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelDataBarBorder(CHECK, object) \ + CHECK(object, GetColor) \ + CHECK(object, GetType) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelDataBarBorder(CHECK, object) \ + CHECK(object, Type) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelNegativeBarFormat(CHECK, object) \ + CHECK(object, GetBorderColor) \ + CHECK(object, GetBorderColorType) \ + CHECK(object, GetColor) \ + CHECK(object, GetColorType) \ + /* 4 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelNegativeBarFormat(CHECK, object) \ + CHECK(object, BorderColorType) \ + CHECK(object, ColorType) \ + /* 2 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelIconSets(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelIconSets(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelIconSet(CHECK, object) \ + CHECK(object, GetCount) \ + CHECK(object, GetID) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelIconSet(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelIcon(CHECK, object) \ + CHECK(object, GetIndex) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelIcon(CHECK, object) \ + /* 0 setters */ + #if WXAUTOEXCEL_USE_CONDFORMAT #define WXAUTOEXCEL_GETTERS_wxExcelRange_1(CHECK, object) \ CHECK(object, GetFormatConditions) \ @@ -2362,6 +3594,51 @@ CHECK(object, TintAndShade) \ /* 10 setters */ +#define WXAUTOEXCEL_GETTERS_wxExcelLinearGradient(CHECK, object) \ + CHECK(object, GetColorStops) \ + CHECK(object, GetDegree) \ + /* 2 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelLinearGradient(CHECK, object) \ + CHECK(object, Degree) \ + /* 1 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelRectangularGradient(CHECK, object) \ + CHECK(object, GetColorStops) \ + CHECK(object, GetRectangleBottom) \ + CHECK(object, GetRectangleLeft) \ + CHECK(object, GetRectangleRight) \ + CHECK(object, GetRectangleTop) \ + /* 5 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelRectangularGradient(CHECK, object) \ + CHECK(object, RectangleBottom) \ + CHECK(object, RectangleLeft) \ + CHECK(object, RectangleRight) \ + CHECK(object, RectangleTop) \ + /* 4 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelColorStops(CHECK, object) \ + CHECK(object, GetCount) \ + /* 1 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelColorStops(CHECK, object) \ + /* 0 setters */ + +#define WXAUTOEXCEL_GETTERS_wxExcelColorStop(CHECK, object) \ + CHECK(object, GetColor) \ + CHECK(object, GetPosition) \ + CHECK(object, GetThemeColor) \ + CHECK(object, GetTintAndShade) \ + /* 4 getters */ + +#define WXAUTOEXCEL_SETTERS_wxExcelColorStop(CHECK, object) \ + CHECK(object, Color) \ + CHECK(object, Position) \ + /* SetThemeColor: fails after setting Color makes the color explicit */ \ + CHECK(object, TintAndShade) \ + /* 4 setters */ + #define WXAUTOEXCEL_GETTERS_wxExcelBorders(CHECK, object) \ CHECK(object, GetColor) \ CHECK(object, GetColorIndex) \ diff --git a/tests/temp_files.h b/tests/temp_files.h new file mode 100644 index 00000000..792676c2 --- /dev/null +++ b/tests/temp_files.h @@ -0,0 +1,79 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Temporary files used by the tests, e.g. for pictures +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#ifndef WXAUTOEXCEL_TESTS_TEMP_FILES_H +#define WXAUTOEXCEL_TESTS_TEMP_FILES_H + +#include + +#include +#include + +// A temporary file with the given extension and content, deleted when the +// object is destroyed. +class TempFile +{ +public: + TempFile(const wxString& extension, const void* data, size_t size) + { + path = wxFileName::CreateTempFileName("wxae"); + wxRemoveFile(path); + path += "." + extension; + + wxFFile file(path, "wb"); + REQUIRE(file.IsOpened()); + REQUIRE(file.Write(data, size) == size); + } + + ~TempFile() + { + wxRemoveFile(path); + } + + const wxString& GetPath() const { return path; } + +private: + wxString path; + + TempFile(const TempFile&); + TempFile& operator=(const TempFile&); +}; + +// A temporary 2x2 pixel BMP picture. +class TempPicture : public TempFile +{ +public: + TempPicture() : TempFile("bmp", GetData(), GetSize()) { } + +private: + // the file and info headers, followed by two rows of 2 pixels, + // each row padded to 4 bytes + static const unsigned char* GetData() + { + static const unsigned char bmp[] = + { + 'B', 'M', 70, 0, 0, 0, 0, 0, 0, 0, 54, 0, 0, 0, + 40, 0, 0, 0, 2, 0, 0, 0, 2, 0, 0, 0, 1, 0, 24, 0, + 0, 0, 0, 0, 16, 0, 0, 0, 0x13, 0x0B, 0, 0, 0x13, 0x0B, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 255, 0, 255, 0, 0, 0, + 255, 0, 0, 255, 255, 255, 0, 0 + }; + return bmp; + } + + static size_t GetSize() { return 70; } +}; + +// A temporary text file, e.g. to embed in a worksheet as an OLE object. +class TempTextFile : public TempFile +{ +public: + TempTextFile() : TempFile("txt", "wxAutoExcel", 11) { } +}; + +#endif // WXAUTOEXCEL_TESTS_TEMP_FILES_H diff --git a/tests/tools/generate_getter_lists.py b/tests/tools/generate_getter_lists.py index 7d49dd3d..f9e0be50 100644 --- a/tests/tools/generate_getter_lists.py +++ b/tests/tools/generate_getter_lists.py @@ -45,6 +45,31 @@ "wxExcelName", "wxExcelStyles", "wxExcelStyle", + "wxExcelCustomProperties", + "wxExcelCustomProperty", + "wxExcelErrors", + "wxExcelError", + "wxExcelErrorCheckingOptions", + "wxExcelMultiThreadedCalculation", + "wxExcelTableStyles", + "wxExcelTableStyleElements", + "wxExcelTableStyleElement", + "wxExcelOLEObjects", + "wxExcelOLEObject", + # windows + "wxExcelWindows", + "wxExcelWindow", + "wxExcelPanes", + "wxExcelPane", + "wxExcelSheetViews", + "wxExcelSheetView", + "wxExcelWorksheetView", + # protection + "wxExcelProtection", + "wxExcelAllowEditRanges", + "wxExcelAllowEditRange", + "wxExcelUserAccessList", + "wxExcelUserAccess", # charts "wxExcelChartObjects", "wxExcelChartObject", @@ -59,11 +84,45 @@ "wxExcelAxis", "wxExcelAxisTitle", "wxExcelSeriesCollection", + "wxExcelFullSeriesCollection", "wxExcelSeries", "wxExcelPoints", "wxExcelPoint", "wxExcelDataLabels", "wxExcelDataLabel", + # chart elements + "wxExcelChartFormat", + "wxExcelChartFillFormat", + "wxExcelChartColorFormat", + "wxExcelErrorBars", + "wxExcelTrendlines", + "wxExcelTrendline", + "wxExcelTickLabels", + "wxExcelGridlines", + "wxExcelLegendEntries", + "wxExcelLegendEntry", + "wxExcelLegendKey", + "wxExcelDataTable", + "wxExcelDisplayUnitLabel", + "wxExcelFloor", + "wxExcelWalls", + "wxExcelUpBars", + "wxExcelDownBars", + "wxExcelHiLoLines", + "wxExcelDropLines", + "wxExcelSeriesLines", + "wxExcelLeaderLines", + "wxExcelCategoryCollection", + "wxExcelChartCategory", + # sparklines + "wxExcelSparklineGroups", + "wxExcelSparklineGroup", + "wxExcelSparkline", + "wxExcelSparkAxes", + "wxExcelSparkHorizontalAxis", + "wxExcelSparkVerticalAxis", + "wxExcelSparkColor", + "wxExcelSparkPoints", # shapes "wxExcelShapes", "wxExcelShape", @@ -73,9 +132,29 @@ "wxExcelTextRange2", "wxExcelFont2", "wxExcelFillFormat", + "wxExcelGradientStops", + "wxExcelGradientStop", "wxExcelLineFormat", "wxExcelColorFormat", "wxExcelThreeDFormat", + "wxExcelTextFrame", + "wxExcelShadowFormat", + "wxExcelGlowFormat", + "wxExcelSoftEdgeFormat", + "wxExcelReflectionFormat", + "wxExcelTextColumn2", + "wxExcelParagraphFormat2", + "wxExcelBulletFormat2", + "wxExcelTabStops2", + "wxExcelTabStop2", + "wxExcelCalloutFormat", + "wxExcelConnectorFormat", + "wxExcelControlFormat", + "wxExcelShapeNodes", + "wxExcelShapeNode", + "wxExcelTextEffectFormat", + "wxExcelPictureFormat", + "wxExcelOLEFormat", # tables and sorting "wxExcelListObjects", "wxExcelListObject", @@ -83,6 +162,7 @@ "wxExcelListColumn", "wxExcelListRows", "wxExcelListRow", + "wxExcelListDataFormat", "wxExcelTableStyle", "wxExcelSort", "wxExcelSortFields", @@ -104,10 +184,20 @@ "wxExcelIconSetCondition", "wxExcelIconCriteria", "wxExcelIconCriterion", + "wxExcelFormatColor", + "wxExcelDataBarBorder", + "wxExcelNegativeBarFormat", + "wxExcelIconSets", + "wxExcelIconSet", + "wxExcelIcon", # ranges, also with cells having different values "wxExcelRange", "wxExcelFont", "wxExcelInterior", + "wxExcelLinearGradient", + "wxExcelRectangularGradient", + "wxExcelColorStops", + "wxExcelColorStop", "wxExcelBorders", "wxExcelBorder", # other range related objects @@ -141,6 +231,10 @@ MARKERS = "only for chart types with markers" TEXTURE = "only for texture fills" ONE_SHAPE = "only for a range of one shape, the test uses two" +SHAPE_ONLY = "only for shapes, the test uses the format of a series" +CHECK_BOX = "not for check boxes, the test uses one" +LINKED_OLE = "only for linked OLE objects, the test embeds a file" +ACTIVEX = "only for ActiveX controls, the test embeds a file" EXCLUDED = { "wxExcelApplication": { @@ -272,6 +366,59 @@ "GetIsTotal": "only for waterfall charts", "GetSecondaryPlot": "only for pie of pie and bar of pie charts", }, + "wxExcelConnectorFormat": { + "GetBeginConnectedShape": "only for connectors connected to a shape", + "GetEndConnectedShape": "only for connectors connected to a shape", + }, + "wxExcelControlFormat": { + "GetDropDownLines": CHECK_BOX, + "GetLargeChange": CHECK_BOX, + "GetListCount": CHECK_BOX, + "GetListFillRange": CHECK_BOX, + "GetListIndex": CHECK_BOX, + "GetMax": CHECK_BOX, + "GetMin": CHECK_BOX, + "GetMultiSelect": CHECK_BOX, + "GetSmallChange": CHECK_BOX, + }, + "wxExcelOLEObject": { + "GetAutoUpdate": LINKED_OLE, + "GetLinkedCell": ACTIVEX, + "GetListFillRange": ACTIVEX, + "GetSourceName": LINKED_OLE, + }, + "wxExcelTextEffectFormat": { + "GetPresetShape": "Excel fails getting it for a text effect added by AddTextEffect(), also in VBA", + }, + "wxExcelTableStyleElement": { + "GetStripeSize": "fails for the elements of a custom table style", + }, + "wxExcelChartFormat": { + "GetAdjustments": SHAPE_ONLY, + "GetAutoShapeType": SHAPE_ONLY, + "GetTextFrame2": SHAPE_ONLY, + }, + "wxExcelLegendKey": { + "GetMarkerBackgroundColor": MARKERS, + "GetMarkerBackgroundColorIndex": MARKERS, + "GetMarkerForegroundColor": MARKERS, + "GetMarkerForegroundColorIndex": MARKERS, + "GetSmooth": "only for line and scatter charts", + }, + "wxExcelChartFillFormat": { + "GetGradientDegree": "only for gradient fills", + "GetTextureName": TEXTURE, + }, + "wxExcelTickLabels": { + "GetAlignment": CATEGORY_AXIS, + "GetMultiLevel": CATEGORY_AXIS, + }, + "wxExcelWalls": { + "GetPictureUnit": PICTURE_FILL, + }, + "wxExcelSparklineGroup": { + "GetDateRange": "only for sparklines with a date axis", + }, "wxExcelHyperlink": { "GetEmailSubject": "only for mailto hyperlinks", "GetShape": "only for hyperlinks of shapes", @@ -361,6 +508,24 @@ "SetBackgroundStyle": "fails for the style of a shape without a background style", "SetGraphicStyle": SET_FAILS, }, + "wxExcelCalloutFormat": {"SetAutoAttach": SET_FAILS}, + "wxExcelCustomProperty": {"SetName": SET_FAILS}, + "wxExcelParagraphFormat2": {"SetTextDirection": SET_FAILS}, + "wxExcelShadowFormat": {"SetType": "fails setting msoShadowMixed which Excel returns"}, + "wxExcelTextFrame": {"SetReadingOrder": SET_FAILS}, + "wxExcelTextEffectFormat": {"SetPresetTextEffect": SET_FAILS}, + "wxExcelColorStop": {"SetThemeColor": EXPLICIT_COLOR}, + "wxExcelLegendKey": { + "SetPictureType": PICTURE_FILL, + "SetPictureUnit": PICTURE_FILL, + "SetPictureUnit2": PICTURE_FILL, + }, + "wxExcelFloor": {"SetPictureType": PICTURE_FILL}, + "wxExcelWalls": {"SetPictureType": PICTURE_FILL}, + "wxExcelTrendline": {"SetPeriod": "only for moving average trendlines, the test uses a linear one"}, + "wxExcelSparklineGroup": {"SetPlotBy": SET_FAILS}, + "wxExcelAllowEditRange": {"SetTitle": "fails setting the title the range already has"}, + "wxExcelFormatColor": {"SetThemeColor": "fails for a color without a theme color"}, "wxExcelChartGroup": {"SetDoughnutHoleSize": "only for doughnut charts, the test uses a column chart"}, "wxExcelTextFrame2": {"SetWordArtformat": SET_FAILS}, "wxExcelFont2": {"SetWordArtformat": SET_FAILS}, diff --git a/tests/wxExcelApplication.cpp b/tests/wxExcelApplication.cpp index 0f9ecfeb..8d07f03f 100644 --- a/tests/wxExcelApplication.cpp +++ b/tests/wxExcelApplication.cpp @@ -5,6 +5,7 @@ // License: MIT license ///////////////////////////////////////////////////////////////////////////// +#include #include #include "excel_test_fixture.h" @@ -298,3 +299,74 @@ TEST_CASE("wxExcelApplication returns the active workbook, sheet, and cell", REQUIRE(cell); CHECK(cell.GetAddress() == "$C$4"); } + +TEST_CASE("wxExcelApplication converts centimeters and inches to points", + "[excel][application]") +{ + wxExcelApplication& application = wxAutoExcelTests::GetApplication(); + + CHECK(application.CentimetersToPoints(2.54) == Catch::Approx(72.0)); + CHECK(application.InchesToPoints(0.5) == Catch::Approx(36.0)); + REQUIRE(application); +} + +TEST_CASE("wxExcelApplication recalculates formulas with manual calculation", + "[excel][application][calculation]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + wxExcelApplication& application = wxAutoExcelTests::GetApplication(); + + wxExcelRange input = book.GetRange("A1"); + wxExcelRange result = book.GetRange("B1"); + input.SetValue(wxVariant(1L)); + result.SetFormula("=A1*2"); + REQUIRE(result); + + const XlCalculation calculation = application.GetCalculation(); + REQUIRE(application); + application.SetCalculation(xlCalculationManual); + REQUIRE(application); + + input.SetValue(wxVariant(5L)); + CHECK(result.GetValue().GetDouble() == 2.0); + + application.CalculateFull(); + REQUIRE(application); + CHECK(result.GetValue().GetDouble() == 10.0); + + input.SetValue(wxVariant(6L)); + application.CalculateFullRebuild(); + REQUIRE(application); + CHECK(result.GetValue().GetDouble() == 12.0); + + application.SetCalculation(calculation); + REQUIRE(application); +} + +TEST_CASE("wxExcelApplication adds and deletes a custom list", + "[excel][application][customlists]") +{ + wxExcelApplication& application = wxAutoExcelTests::GetApplication(); + + const long countBefore = application.GetCustomListCount(); + REQUIRE(application); + + wxArrayString list; + list.push_back("wxAutoExcelAlpha"); + list.push_back("wxAutoExcelBeta"); + list.push_back("wxAutoExcelGamma"); + REQUIRE(application.AddCustomList(list)); + CHECK(application.GetCustomListCount() == countBefore + 1); + + const long listNum = application.GetCustomListNum(list); + REQUIRE(application); + CHECK(listNum > 0); + + const wxArrayString contents = application.GetCustomListContents(listNum); + REQUIRE(application); + CHECK(contents == list); + + REQUIRE(application.DeleteCustomList(listNum)); + CHECK(application.GetCustomListCount() == countBefore); +} diff --git a/tests/wxExcelChart.cpp b/tests/wxExcelChart.cpp index 1ec0e058..2beb0b47 100644 --- a/tests/wxExcelChart.cpp +++ b/tests/wxExcelChart.cpp @@ -247,4 +247,336 @@ TEST_CASE("wxExcelChart moves from the worksheet to a chart sheet", REQUIRE(charts); } +TEST_CASE("wxExcelSeries adds error bars", + "[excel][chart][series]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + + wxExcelSeries income = chart.SeriesCollection(1); + REQUIRE(income); + CHECK_FALSE(income.GetHasErrorBars()); + REQUIRE(income); + + double amount = 5; + CHECK(income.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypeFixedValue, &amount)); + REQUIRE(income); + CHECK(income.GetHasErrorBars()); + REQUIRE(income); + + // the standard error does not need an amount + wxExcelSeries costs = chart.SeriesCollection(2); + REQUIRE(costs); + CHECK(costs.ErrorBar(xlY, xlErrorBarIncludePlusValues, xlErrorBarTypeStError)); + REQUIRE(costs); + CHECK(costs.GetHasErrorBars()); + REQUIRE(costs); +} + +TEST_CASE("wxExcelSeries adds custom error bars", + "[excel][chart][series]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + wxExcelRange plus = book.GetRange("E2:E5"); + wxExcelRange minus = book.GetRange("F2:F5"); + plus.SetValue(wxVariant(3.0)); + REQUIRE(plus); + minus.SetValue(wxVariant(1.0)); + REQUIRE(minus); + + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + + SECTION("from ranges") + { + CHECK(series.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypeCustom, plus, minus)); + } + + SECTION("from arrays") + { + const wxVariantList empty; + wxVariant amount(empty), minusValues(empty); + for ( long i = 0; i < 4; ++i ) + { + amount.Append(wxVariant(2.0 * (i + 1))); + minusValues.Append(wxVariant(1.0)); + } + CHECK(series.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypeCustom, amount, minusValues)); + } + + SECTION("from strings") + { + const wxString sheetName = book.GetWorksheet().GetName(); + REQUIRE_FALSE(sheetName.empty()); + CHECK(series.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypeCustom, + wxVariant("={1,2,3,4}"), wxVariant("='" + sheetName + "'!$F$2:$F$5"))); + } + + SECTION("from the values of a range and a number") + { + CHECK(series.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypeCustom, plus, wxVariant(1.0))); + } + + REQUIRE(series); + CHECK(series.GetHasErrorBars()); + REQUIRE(series); +} + +TEST_CASE("wxExcelErrorBars changes and deletes the error bars of a series", + "[excel][chart][series][errorbars]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + + double amount = 10; + REQUIRE(series.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypePercent, &amount)); + + wxExcelErrorBars errorBars = series.GetErrorBars(); + REQUIRE(errorBars); + CHECK_FALSE(errorBars.GetName().empty()); + CHECK(errorBars.GetEndStyle() == xlCap); + REQUIRE(errorBars); + + errorBars.SetEndStyle(xlNoCap); + REQUIRE(errorBars); + CHECK(series.GetErrorBars().GetEndStyle() == xlNoCap); + + wxExcelBorder border = errorBars.GetBorder(); + REQUIRE(border); + border.SetColor(*wxRED); + REQUIRE(border); + CHECK(errorBars.GetBorder().GetColor() == *wxRED); + + CHECK(errorBars.ClearFormats()); + CHECK(series.GetHasErrorBars()); + REQUIRE(series); + + CHECK(errorBars.Delete()); + CHECK_FALSE(series.GetHasErrorBars()); + REQUIRE(series); +} + +TEST_CASE("wxExcelTrendlines adds trendlines of different types", + "[excel][chart][series][trendlines]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + + wxExcelTrendlines trendlines = series.Trendlines(); + REQUIRE(trendlines); + CHECK(trendlines.GetCount() == 0); + REQUIRE(trendlines); + + // the type is linear by default + wxExcelTrendline linear = trendlines.Add(); + REQUIRE(linear); + CHECK(linear.GetType() == xlLinear); + CHECK(linear.GetIndex() == 1); + REQUIRE(linear); + + XlTrendlineType type = xlPolynomial; + long order = 3; + wxExcelTrendline polynomial = trendlines.Add(&type, &order); + REQUIRE(polynomial); + CHECK(polynomial.GetType() == xlPolynomial); + CHECK(polynomial.GetOrder() == 3); + REQUIRE(polynomial); + + type = xlMovingAvg; + long period = 2; + wxExcelTrendline movingAverage = trendlines.Add(&type, NULL, &period, NULL, NULL, NULL, + wxDefaultXlTribool, wxDefaultXlTribool, "Average"); + REQUIRE(movingAverage); + CHECK(movingAverage.GetType() == xlMovingAvg); + CHECK(movingAverage.GetPeriod() == 2); + CHECK(movingAverage.GetName() == "Average"); + CHECK_FALSE(movingAverage.GetNameIsAuto()); + REQUIRE(movingAverage); + + CHECK(trendlines.GetCount() == 3); + CHECK(trendlines.Item(2).GetType() == xlPolynomial); + REQUIRE(trendlines); + + REQUIRE(polynomial.Delete()); + CHECK(trendlines.GetCount() == 2); + CHECK(trendlines.Item(2).GetType() == xlMovingAvg); + REQUIRE(trendlines); +} + +TEST_CASE("wxExcelTrendline changes its forecast, intercept, and label", + "[excel][chart][series][trendlines]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + wxExcelTrendline trendline = series.Trendlines().Add(); + REQUIRE(trendline); + + trendline.SetForward2(1.5); + trendline.SetBackward2(0.5); + REQUIRE(trendline); + CHECK(trendline.GetForward2() == 1.5); + CHECK(trendline.GetBackward2() == 0.5); + REQUIRE(trendline); + + CHECK(trendline.GetInterceptIsAuto()); + trendline.SetIntercept(10); + REQUIRE(trendline); + CHECK(trendline.GetIntercept() == 10.0); + CHECK_FALSE(trendline.GetInterceptIsAuto()); + REQUIRE(trendline); + + trendline.SetType(xlExponential); + REQUIRE(trendline); + CHECK(trendline.GetType() == xlExponential); + + // showing the R-squared value adds the data label + CHECK_FALSE(trendline.GetDisplayRSquared()); + trendline.SetDisplayRSquared(true); + REQUIRE(trendline); + CHECK(trendline.GetDisplayRSquared()); + // the text of the label is empty until the chart is drawn, + // which it is not in the hidden Excel instance + wxExcelDataLabel label = trendline.GetDataLabel(); + REQUIRE(label); + + CHECK(trendline.ClearFormats()); + CHECK(trendline.Delete()); + CHECK(series.Trendlines().GetCount() == 0); +} + +TEST_CASE("wxExcelChart full series collection includes the filtered series", + "[excel][chart][series]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + CHECK(GetSeriesCount(chart) == 2); + + wxExcelFullSeriesCollection fullSeries = chart.FullSeriesCollection(); + REQUIRE(fullSeries); + CHECK(fullSeries.GetCount() == 2); + REQUIRE(fullSeries); + + wxExcelSeries costs = chart.FullSeriesCollection(2); + REQUIRE(costs); + CHECK_FALSE(costs.GetIsFiltered()); + costs.SetIsFiltered(true); + REQUIRE(costs); + CHECK(costs.GetIsFiltered()); + + // the filtered series is not shown, so only the full collection has it + CHECK(GetSeriesCount(chart) == 1); + CHECK(fullSeries.GetCount() == 2); + CHECK(fullSeries.Item(2).GetName() == "Costs"); + REQUIRE(fullSeries); + + long count = 0; + for ( wxExcelSeries series : fullSeries ) + { + CHECK(series); + ++count; + } + CHECK(count == 2); +} + +TEST_CASE("wxExcelChartFillFormat changes the fill of chart elements", + "[excel][chart][fill]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + + wxExcelChartFillFormat chartAreaFill = chart.GetChartArea().GetFill(); + REQUIRE(chartAreaFill); + + chartAreaFill.Solid(); + REQUIRE(chartAreaFill); + CHECK(chartAreaFill.GetType() == msoFillSolid); + + wxExcelChartColorFormat foreColor = chartAreaFill.GetForeColor(); + REQUIRE(foreColor); + foreColor.SetSchemeColor(3); + REQUIRE(foreColor); + CHECK(foreColor.GetSchemeColor() == 3); + CHECK(foreColor.GetRGB() == *wxRED); + REQUIRE(foreColor); + + chartAreaFill.TwoColorGradient(msoGradientVertical, 1); + REQUIRE(chartAreaFill); + CHECK(chartAreaFill.GetType() == msoFillGradient); + CHECK(chartAreaFill.GetGradientStyle() == msoGradientVertical); + REQUIRE(chartAreaFill); + + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + wxExcelChartFillFormat seriesFill = series.GetFill(); + REQUIRE(seriesFill); + seriesFill.Patterned(msoPattern30Percent); + REQUIRE(seriesFill); + CHECK(seriesFill.GetType() == msoFillPatterned); + CHECK(seriesFill.GetPattern() == msoPattern30Percent); + REQUIRE(seriesFill); + + // the fill is the same as the one of the newer format + wxExcelFillFormat formatFill = series.GetFormat().GetFill(); + REQUIRE(formatFill); + CHECK(formatFill.GetType() == msoFillPatterned); + REQUIRE(formatFill); + + wxExcelChartFillFormat plotAreaFill = chart.GetPlotArea().GetFill(); + REQUIRE(plotAreaFill); + plotAreaFill.PresetTextured(msoTexturePapyrus); + REQUIRE(plotAreaFill); + CHECK(plotAreaFill.GetType() == msoFillTextured); +} + +TEST_CASE("wxExcelSeries applies data labels", + "[excel][chart][series]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelChart chart = AddChart(book); + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + CHECK_FALSE(series.GetHasDataLabels()); + REQUIRE(series); + + XlDataLabelsType type = xlDataLabelsShowValue; + series.ApplyDataLabels(&type); + REQUIRE(series); + CHECK(series.GetHasDataLabels()); + + // the label of the first point shows its value + wxExcelDataLabel label = series.Points(1).GetDataLabel(); + REQUIRE(label); + CHECK(label.GetShowValue()); + CHECK_FALSE(label.GetShowCategoryName()); + REQUIRE(label); + + type = xlDataLabelsShowNone; + series.ApplyDataLabels(&type); + REQUIRE(series); + CHECK_FALSE(series.GetHasDataLabels()); +} + #endif // WXAUTOEXCEL_USE_CHARTS diff --git a/tests/wxExcelFillFormat.cpp b/tests/wxExcelFillFormat.cpp new file mode 100644 index 00000000..1c9742b6 --- /dev/null +++ b/tests/wxExcelFillFormat.cpp @@ -0,0 +1,202 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Tests for the methods of wxExcelFillFormat setting the fill type +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#include +#include + +#include "excel_test_fixture.h" +#include "temp_files.h" + +#if WXAUTOEXCEL_USE_SHAPES + +using namespace wxAutoExcel; + +namespace +{ + +wxExcelFillFormat AddRectangleFill(ExcelTestWorkbook& book) +{ + wxExcelShapes shapes = book.GetWorksheet().GetShapes(); + REQUIRE(shapes); + wxExcelShape rectangle = shapes.AddShape(msoShapeRectangle, 10, 10, 120, 60); + REQUIRE(rectangle); + wxExcelFillFormat fill = rectangle.GetFill(); + REQUIRE(fill); + return fill; +} + +MsoFillType GetType(wxExcelFillFormat& fill) +{ + const MsoFillType type = fill.GetType(); + REQUIRE(fill); + return type; +} + +} // unnamed namespace + +TEST_CASE("wxExcelFillFormat sets a solid or patterned fill", + "[excel][shapes][fill]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelFillFormat fill = AddRectangleFill(book); + + fill.Patterned(msoPattern30Percent); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillPatterned); + CHECK(fill.GetPattern() == msoPattern30Percent); + REQUIRE(fill); + + fill.Solid(); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillSolid); + + wxExcelColorFormat foreColor = fill.GetForeColor(); + REQUIRE(foreColor); + foreColor.SetRGB(*wxRED); + REQUIRE(foreColor); + CHECK(fill.GetForeColor().GetRGB() == *wxRED); +} + +TEST_CASE("wxExcelFillFormat sets gradient fills", + "[excel][shapes][fill]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelFillFormat fill = AddRectangleFill(book); + + SECTION("one-color gradient") + { + fill.OneColorGradient(msoGradientHorizontal, 1, 0.5); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillGradient); + CHECK(fill.GetGradientStyle() == msoGradientHorizontal); + CHECK(fill.GetGradientVariant() == 1); + CHECK(fill.GetGradientColorType() == msoGradientOneColor); + CHECK(fill.GetGradientDegree() == Catch::Approx(0.5)); + REQUIRE(fill); + } + + SECTION("two-color gradient") + { + fill.TwoColorGradient(msoGradientVertical, 2); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillGradient); + CHECK(fill.GetGradientStyle() == msoGradientVertical); + CHECK(fill.GetGradientVariant() == 2); + REQUIRE(fill); + } + + SECTION("preset gradient") + { + fill.PresetGradient(msoGradientDiagonalUp, 1, msoGradientEarlySunset); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillGradient); + CHECK(fill.GetGradientStyle() == msoGradientDiagonalUp); + CHECK(fill.GetGradientColorType() == msoGradientPresetColors); + CHECK(fill.GetPresetGradientType() == msoGradientEarlySunset); + REQUIRE(fill); + } +} + +TEST_CASE("wxExcelFillFormat sets texture and picture fills", + "[excel][shapes][fill]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelFillFormat fill = AddRectangleFill(book); + + SECTION("preset texture") + { + fill.PresetTextured(msoTexturePapyrus); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillTextured); + } + + SECTION("user texture") + { + TempPicture picture; + fill.UserTextured(picture.GetPath()); + REQUIRE(fill); + // Excel returns msoTextureTypeMixed as its TextureType + CHECK(GetType(fill) == msoFillTextured); + } + + SECTION("user picture") + { + TempPicture picture; + fill.UserPicture(picture.GetPath()); + REQUIRE(fill); + CHECK(GetType(fill) == msoFillPicture); + } +} + +TEST_CASE("wxExcelGradientStops inserts and deletes the stops of a gradient", + "[excel][shapes][fill]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelFillFormat fill = AddRectangleFill(book); + fill.TwoColorGradient(msoGradientHorizontal, 1); + REQUIRE(fill); + + wxExcelGradientStops stops = fill.GetGradientStops(); + REQUIRE(stops); + CHECK(stops.GetCount() == 2); + REQUIRE(stops); + + wxExcelGradientStop first = stops.GetItem(1); + REQUIRE(first); + CHECK(first.GetPosition() == 0.0); + REQUIRE(first); + + stops.Insert(*wxGREEN, 0.5, 0.25); + REQUIRE(stops); + CHECK(stops.GetCount() == 3); + REQUIRE(stops); + + // the stop is added after the last one, whatever its position + wxExcelGradientStop middle = stops.GetItem(3); + REQUIRE(middle); + CHECK(middle.GetPosition() == Catch::Approx(0.5)); + CHECK(middle.GetTransparency() == Catch::Approx(0.25)); + CHECK(middle.GetColor().GetRGB() == *wxGREEN); + REQUIRE(middle); + + middle.SetPosition(0.4); + middle.SetTransparency(0); + REQUIRE(middle); + CHECK(middle.GetPosition() == Catch::Approx(0.4)); + CHECK(middle.GetTransparency() == Catch::Approx(0.0)); + REQUIRE(middle); + + stops.Insert2(*wxBLUE, 0.8, 0, -1, 0.5); + REQUIRE(stops); + CHECK(stops.GetCount() == 4); + REQUIRE(stops); + + long count = 0; + for ( wxExcelGradientStop stop : stops ) + { + CHECK(stop); + ++count; + } + CHECK(count == 4); + + stops.Delete(2); + REQUIRE(stops); + CHECK(stops.GetCount() == 3); + stops.Delete(); + REQUIRE(stops); + CHECK(stops.GetCount() == 2); +} + +#endif // WXAUTOEXCEL_USE_SHAPES diff --git a/tests/wxExcelFormatConditions.cpp b/tests/wxExcelFormatConditions.cpp index e841ab85..a79bd98d 100644 --- a/tests/wxExcelFormatConditions.cpp +++ b/tests/wxExcelFormatConditions.cpp @@ -263,4 +263,46 @@ TEST_CASE("wxExcelFormatConditions adds unique, top 10, data bar, and color scal CHECK(GetDisplayedColor(book, "A10") == White); } +TEST_CASE("wxExcelIconSetCondition uses an icon set of the workbook", + "[excel][formatconditions][iconsets]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelRange range = book.GetRange("A1:A10"); + range.SetFormula("=ROW()"); + REQUIRE(range); + + wxExcelIconSetCondition condition = GetFormatConditions(range).AddIconSetCondition(); + REQUIRE(condition); + + wxExcelIconSet iconSet = condition.GetIconSet(); + REQUIRE(iconSet); + CHECK(iconSet.GetCount() == 3); + REQUIRE(iconSet); + + wxExcelIconSets iconSets = book.GetWorkbook().GetIconSets(); + REQUIRE(iconSets); + CHECK(iconSets.GetCount() >= 17); + REQUIRE(iconSets); + + wxExcelIconSet arrows = book.GetWorkbook().GetIconSets(xl5Arrows); + REQUIRE(arrows); + CHECK(arrows.GetID() == xl5Arrows); + CHECK(arrows.GetCount() == 5); + REQUIRE(arrows); + + condition.SetIconSet(arrows); + REQUIRE(condition); + wxExcelIconSet changed = condition.GetIconSet(); + REQUIRE(changed); + CHECK(changed.GetID() == xl5Arrows); + CHECK(changed.GetCount() == 5); + REQUIRE(changed); + + wxExcelIcon icon = changed.GetItem(5); + REQUIRE(icon); + CHECK(icon.GetIndex() == 5); +} + #endif // WXAUTOEXCEL_USE_CONDFORMAT diff --git a/tests/wxExcelProtection.cpp b/tests/wxExcelProtection.cpp new file mode 100644 index 00000000..aad7747b --- /dev/null +++ b/tests/wxExcelProtection.cpp @@ -0,0 +1,189 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Tests for worksheet protection: wxExcelProtection, +// wxExcelAllowEditRanges, and wxExcelUserAccessList +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#include + +#include "excel_test_fixture.h" + +using namespace wxAutoExcel; + +namespace +{ + +wxExcelProtection GetProtection(ExcelTestWorkbook& book) +{ + wxExcelProtection protection = book.GetWorksheet().GetProtection(); + REQUIRE(protection); + return protection; +} + +wxExcelAllowEditRanges GetAllowEditRanges(ExcelTestWorkbook& book) +{ + wxExcelAllowEditRanges ranges = GetProtection(book).GetAllowEditRanges(); + REQUIRE(ranges); + return ranges; +} + +long GetCount(wxExcelAllowEditRanges& ranges) +{ + const long count = ranges.GetCount(); + REQUIRE(ranges); + return count; +} + +// Returns true if the value of the cell could be set. +bool CanSetValue(ExcelTestWorkbook& book, const wxString& address) +{ + wxAutoExcelObjectErrorModeOverrider noErrors(wxExcelObject::Err_DoNothing, true); + wxExcelRange cell = book.GetRange(address); + cell.SetValue(wxVariant(42L)); + return static_cast(cell); +} + +} // unnamed namespace + +TEST_CASE("wxExcelWorksheet protection allows only the given operations", + "[excel][protection]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + wxExcelWorksheet& worksheet = book.GetWorksheet(); + + CHECK_FALSE(worksheet.GetProtectContents()); + CHECK(CanSetValue(book, "A1")); + + worksheet.Protect("password", wxDefaultXlTribool, true, wxDefaultXlTribool, wxDefaultXlTribool, + true, // allowFormattingCells + false, false, false, false, false, false, false, + true, // allowSorting + true); // allowFiltering + REQUIRE(worksheet); + CHECK(worksheet.GetProtectContents()); + + wxExcelProtection protection = GetProtection(book); + CHECK(protection.GetAllowFormattingCells()); + CHECK_FALSE(protection.GetAllowFormattingColumns()); + CHECK_FALSE(protection.GetAllowFormattingRows()); + CHECK_FALSE(protection.GetAllowInsertingColumns()); + CHECK_FALSE(protection.GetAllowInsertingRows()); + CHECK_FALSE(protection.GetAllowInsertingHyperlinks()); + CHECK_FALSE(protection.GetAllowDeletingColumns()); + CHECK_FALSE(protection.GetAllowDeletingRows()); + CHECK(protection.GetAllowSorting()); + CHECK(protection.GetAllowFiltering()); + CHECK_FALSE(protection.GetAllowUsingPivotTables()); + REQUIRE(protection); + + // the cells are locked by default + CHECK_FALSE(CanSetValue(book, "A1")); + + REQUIRE(worksheet.Unprotect("password")); + CHECK_FALSE(worksheet.GetProtectContents()); + CHECK(CanSetValue(book, "A1")); +} + +TEST_CASE("wxExcelAllowEditRanges adds, renames, and deletes ranges", + "[excel][protection]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelAllowEditRanges ranges = GetAllowEditRanges(book); + CHECK(GetCount(ranges) == 0); + + wxExcelRange inputs = book.GetRange("B2:C5"); + wxExcelAllowEditRange range = ranges.Add("Inputs", inputs); + REQUIRE(range); + CHECK(GetCount(ranges) == 1); + CHECK(range.GetTitle() == "Inputs"); + CHECK(range.GetRange().GetAddress(false, false) == "B2:C5"); + REQUIRE(range); + + range.SetTitle("Data"); + REQUIRE(range); + wxExcelAllowEditRange found = ranges.GetItem("Data"); + REQUIRE(found); + CHECK(found.GetRange().GetAddress(false, false) == "B2:C5"); + REQUIRE(found); + + range.SetRange(book.GetRange("D1:D3")); + REQUIRE(range); + CHECK(range.GetRange().GetAddress(false, false) == "D1:D3"); + REQUIRE(range); + + range.ChangePassword("secret"); + REQUIRE(range); + + wxExcelRange other = book.GetRange("E1"); + REQUIRE(ranges.Add("Other", other)); + CHECK(GetCount(ranges) == 2); + CHECK(ranges.GetItem(2).GetTitle() == "Other"); + + range.Delete(); + REQUIRE(range); + CHECK(GetCount(ranges) == 1); + CHECK(ranges.GetItem(1).GetTitle() == "Other"); +} + +TEST_CASE("wxExcelAllowEditRange can be edited on a protected worksheet", + "[excel][protection]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelAllowEditRanges ranges = GetAllowEditRanges(book); + wxExcelRange inputs = book.GetRange("B2"); + REQUIRE(ranges.Add("Inputs", inputs)); + + book.GetWorksheet().Protect("password"); + REQUIRE(book.GetWorksheet()); + + CHECK(CanSetValue(book, "B2")); + CHECK_FALSE(CanSetValue(book, "A1")); + + // the ranges cannot be changed while the worksheet is protected + { + wxAutoExcelObjectErrorModeOverrider noErrors(wxExcelObject::Err_DoNothing, true); + wxExcelRange other = book.GetRange("C3"); + CHECK_FALSE(ranges.Add("Other", other)); + } + + REQUIRE(book.GetWorksheet().Unprotect("password")); + CHECK(GetCount(ranges) == 1); +} + +TEST_CASE("wxExcelUserAccessList adds and removes users of a range", + "[excel][protection]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelAllowEditRanges ranges = GetAllowEditRanges(book); + wxExcelRange inputs = book.GetRange("B2:C5"); + wxExcelAllowEditRange range = ranges.Add("Inputs", inputs); + REQUIRE(range); + + wxExcelUserAccessList users = range.GetUsers(); + REQUIRE(users); + CHECK(users.GetCount() == 0); + + wxExcelUserAccess user = users.Add("Everyone", true); + REQUIRE(user); + CHECK(users.GetCount() == 1); + CHECK(user.GetAllowEdit()); + CHECK_FALSE(user.GetName().empty()); + REQUIRE(user); + + user.SetAllowEdit(false); + REQUIRE(user); + CHECK_FALSE(users.GetItem(1).GetAllowEdit()); + + users.DeleteAll(); + REQUIRE(users); + CHECK(users.GetCount() == 0); +} diff --git a/tests/wxExcelRange_format.cpp b/tests/wxExcelRange_format.cpp index 41bb9265..e6b8cbb0 100644 --- a/tests/wxExcelRange_format.cpp +++ b/tests/wxExcelRange_format.cpp @@ -417,3 +417,103 @@ TEST_CASE("wxExcelRange layout properties round-trip", CHECK(range.GetRowHeight() == Catch::Approx(24.0).margin(0.1)); REQUIRE(range); } + +TEST_CASE("wxExcelInterior sets a linear gradient with its color stops", + "[excel][range][format][gradient]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelInterior interior = book.GetRange("A1").GetInterior(); + REQUIRE(interior); + interior.SetPattern(xlPatternLinearGradient); + REQUIRE(interior); + CHECK(interior.GetPattern() == xlPatternLinearGradient); + + wxExcelLinearGradient gradient = interior.GetLinearGradient(); + REQUIRE(gradient); + gradient.SetDegree(45); + REQUIRE(gradient); + CHECK(gradient.GetDegree() == 45.0); + + wxExcelColorStops stops = gradient.GetColorStops(); + REQUIRE(stops); + CHECK(stops.GetCount() == 2); + + stops.Clear(); + REQUIRE(stops); + CHECK(stops.GetCount() == 0); + + wxExcelColorStop red = stops.Add(0); + REQUIRE(red); + red.SetColor(*wxRED); + wxExcelColorStop green = stops.Add(0.5); + REQUIRE(green); + green.SetColor(*wxGREEN); + wxExcelColorStop blue = stops.Add(1); + REQUIRE(blue); + blue.SetColor(*wxBLUE); + REQUIRE(stops); + CHECK(stops.GetCount() == 3); + + wxExcelColorStop middle = stops.GetItem(2); + REQUIRE(middle); + CHECK(middle.GetPosition() == Catch::Approx(0.5)); + CHECK(middle.GetColor() == *wxGREEN); + REQUIRE(middle); + + // the tint lightens the color, Excel stores it with a limited precision + middle.SetTintAndShade(0.25); + REQUIRE(middle); + CHECK(middle.GetTintAndShade() == Catch::Approx(0.25).margin(0.001)); + CHECK(middle.GetColor() != *wxGREEN); + REQUIRE(middle); + + middle.SetPosition(0.3); + REQUIRE(middle); + CHECK(stops.GetItem(2).GetPosition() == Catch::Approx(0.3)); + + CHECK(middle.Delete()); + CHECK(stops.GetCount() == 2); + CHECK(stops.GetItem(2).GetColor() == *wxBLUE); + + // the theme color replaces the explicit one + wxExcelColorStop first = stops.GetItem(1); + REQUIRE(first); + first.SetThemeColor(xlThemeColorAccent1); + REQUIRE(first); + CHECK(first.GetThemeColor() == xlThemeColorAccent1); +} + +TEST_CASE("wxExcelInterior sets a rectangular gradient", + "[excel][range][format][gradient]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelInterior interior = book.GetRange("B2").GetInterior(); + REQUIRE(interior); + interior.SetPattern(xlPatternRectangularGradient); + REQUIRE(interior); + CHECK(interior.GetPattern() == xlPatternRectangularGradient); + + wxExcelRectangularGradient gradient = interior.GetRectangularGradient(); + REQUIRE(gradient); + gradient.SetRectangleLeft(0.25); + gradient.SetRectangleTop(0.5); + gradient.SetRectangleRight(0.75); + gradient.SetRectangleBottom(1); + REQUIRE(gradient); + CHECK(gradient.GetRectangleLeft() == Catch::Approx(0.25)); + CHECK(gradient.GetRectangleTop() == Catch::Approx(0.5)); + CHECK(gradient.GetRectangleRight() == Catch::Approx(0.75)); + CHECK(gradient.GetRectangleBottom() == Catch::Approx(1.0)); + REQUIRE(gradient); + + wxExcelColorStops stops = gradient.GetColorStops(); + REQUIRE(stops); + CHECK(stops.GetCount() == 2); + REQUIRE(stops); + stops.GetItem(2).SetColor(*wxRED); + CHECK(stops.GetItem(2).GetColor() == *wxRED); +} diff --git a/tests/wxExcelRange_methods.cpp b/tests/wxExcelRange_methods.cpp new file mode 100644 index 00000000..f0c867a5 --- /dev/null +++ b/tests/wxExcelRange_methods.cpp @@ -0,0 +1,216 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Tests for wxExcelRange methods drawing borders, filling +// series, creating and applying names, finding differences, +// outlining, and copying ranges as pictures +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#include + +#include "excel_test_fixture.h" + +using namespace wxAutoExcel; + +namespace +{ + +wxExcelBorder GetBorder(wxExcelRange range, XlBordersIndex index) +{ + wxExcelBorder border = range.GetBorders().GetItem(index); + REQUIRE(border); + return border; +} + +void SetValues(ExcelTestWorkbook& book, const wxString& address, + double first, double second, double third) +{ + wxExcelRange range = book.GetRange(address); + const double values[] = { first, second, third }; + for ( long i = 0; i < 3; ++i ) + { + wxExcelRange cell = range.GetItem(i + 1); + REQUIRE(cell); + cell.SetValue(wxVariant(values[i])); + REQUIRE(cell); + } +} + +wxString GetFormula(ExcelTestWorkbook& book, const wxString& address) +{ + wxExcelRange cell = book.GetRange(address); + const wxString formula = cell.GetFormula(); + REQUIRE(cell); + return formula; +} + +} // unnamed namespace + +TEST_CASE("wxExcelRange draws a border around the range", + "[excel][range][borders]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelRange range = book.GetRange("B2:C3"); + XlLineStyle lineStyle = xlContinuous; + XlBorderWeight weight = xlThick; + REQUIRE(range.BorderAround(&lineStyle, &weight, NULL, wxRED)); + + const XlBordersIndex edges[] = { xlEdgeTop, xlEdgeBottom, xlEdgeLeft, xlEdgeRight }; + for ( size_t i = 0; i < WXSIZEOF(edges); ++i ) + { + wxExcelBorder border = GetBorder(range, edges[i]); + CHECK(border.GetLineStyle() == xlContinuous); + CHECK(border.GetWeight() == xlThick); + CHECK(border.GetColor() == *wxRED); + REQUIRE(border); + } + + // only the edges have the border, not the cells inside + CHECK(GetBorder(range, xlInsideHorizontal).GetLineStyle() == xlLineStyleNone); + CHECK(GetBorder(book.GetRange("B2"), xlEdgeBottom).GetLineStyle() == xlLineStyleNone); +} + +TEST_CASE("wxExcelRange fills a data series", + "[excel][range][series]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + SECTION("linear series in a column") + { + book.GetRange("A1").SetValue(wxVariant(1L)); + wxExcelRange range = book.GetRange("A1:A5"); + XlRowCol rowCol = xlColumns; + XlDataSeriesType type = xlDataSeriesLinear; + long step = 2; + REQUIRE(range.DataSeries(&rowCol, &type, NULL, &step)); + CHECK(book.GetRange("A2").GetValue().GetDouble() == 3.0); + CHECK(book.GetRange("A5").GetValue().GetDouble() == 9.0); + } + + SECTION("growth series in a row up to a stop value") + { + book.GetRange("A1").SetValue(wxVariant(1L)); + wxExcelRange range = book.GetRange("A1:F1"); + XlRowCol rowCol = xlRows; + XlDataSeriesType type = xlGrowth; + long step = 3; + REQUIRE(range.DataSeries(&rowCol, &type, NULL, &step, wxVariant(30L))); + CHECK(book.GetRange("D1").GetValue().GetDouble() == 27.0); + CHECK(book.GetRange("E1").GetValue().IsNull()); + } +} + +TEST_CASE("wxExcelRange creates and applies names", + "[excel][range][names]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelNames names = book.GetWorkbook().GetNames(); + REQUIRE(names); + CHECK(names.GetCount() == 0); + + // the names of the columns are created from the labels in the top row + book.GetRange("A1").SetValue("Price"); + book.GetRange("B1").SetValue("Amount"); + SetValues(book, "A2:A4", 10, 20, 30); + SetValues(book, "B2:B4", 1, 2, 3); + REQUIRE(book.GetRange("A1:B4").CreateNames(true, false, false, false)); + CHECK(names.GetCount() == 2); + wxExcelName price = names.Item("Price"); + REQUIRE(price); + CHECK(price.GetRefersToRange().GetAddress(false, false) == "A2:A4"); + REQUIRE(price); + + // all names are applied without any given + wxExcelRange total = book.GetRange("D1"); + total.SetFormula("=SUM($A$2:$A$4)+SUM($B$2:$B$4)"); + REQUIRE(total); + total.ApplyNames(); + REQUIRE(total); + CHECK(GetFormula(book, "D1") == "=SUM(Price)+SUM(Amount)"); + CHECK(book.GetRange("D1").GetValue().GetDouble() == 66.0); + + // only the given names are applied (Excel then applies only them also + // when no names are given later, so this is done after the above) + wxExcelRange other = book.GetRange("D2"); + other.SetFormula("=SUM($A$2:$A$4)+SUM($B$2:$B$4)"); + REQUIRE(other); + wxArrayString applied; + applied.push_back("Price"); + other.ApplyNames(&applied); + REQUIRE(other); + CHECK(GetFormula(book, "D2") == "=SUM(Price)+SUM($B$2:$B$4)"); +} + +TEST_CASE("wxExcelRange finds cells differing from the comparison cell", + "[excel][range][find]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + SetValues(book, "A1:A3", 1, 1, 2); + wxExcelRange column = book.GetRange("A1:A3"); + wxExcelRange columnDifferences = column.ColumnDifferences(book.GetRange("A1")); + REQUIRE(columnDifferences); + CHECK(columnDifferences.GetAddress(false, false) == "A3"); + + SetValues(book, "C1:E1", 5, 6, 5); + wxExcelRange row = book.GetRange("C1:E1"); + wxExcelRange rowDifferences = row.RowDifferences(book.GetRange("C1")); + REQUIRE(rowDifferences); + CHECK(rowDifferences.GetAddress(false, false) == "D1"); +} + +TEST_CASE("wxExcelRange creates and clears an outline", + "[excel][range][outline]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + SetValues(book, "A1:A3", 1, 2, 3); + book.GetRange("A4").SetFormula("=SUM(A1:A3)"); + + wxExcelRange range = book.GetRange("A1:A4"); + range.AutoOutline(); + REQUIRE(range); + + // the summed rows become a group, the summary row stays at the top level + CHECK(book.GetRange("A1").GetEntireRow().GetOutlineLevel() == 2); + CHECK(book.GetRange("A3").GetEntireRow().GetOutlineLevel() == 2); + CHECK(book.GetRange("A4").GetEntireRow().GetOutlineLevel() == 1); + + REQUIRE(range.ClearOutline()); + CHECK(book.GetRange("A1").GetEntireRow().GetOutlineLevel() == 1); +} + +#if WXAUTOEXCEL_USE_SHAPES + +TEST_CASE("wxExcelRange copies the range as a picture", + "[excel][range][picture]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + book.GetRange("A1").SetValue("Picture"); + XlPictureAppearance appearance = xlScreen; + XlCopyPictureFormat format = xlBitmap; + REQUIRE(book.GetRange("A1:B2").CopyPicture(&appearance, &format)); + + wxExcelRange destination = book.GetRange("D4"); + REQUIRE(book.GetWorksheet().Paste(&destination)); + + wxExcelShapes shapes = book.GetWorksheet().GetShapes(); + REQUIRE(shapes); + CHECK(shapes.GetCount() == 1); + wxExcelShape picture = shapes.Item(1); + REQUIRE(picture); + CHECK(picture.GetType() == msoPicture); + CHECK(picture.GetTopLeftCell().GetAddress(false, false) == "D4"); +} + +#endif // WXAUTOEXCEL_USE_SHAPES diff --git a/tests/wxExcelShape_formats.cpp b/tests/wxExcelShape_formats.cpp new file mode 100644 index 00000000..92d2f6ec --- /dev/null +++ b/tests/wxExcelShape_formats.cpp @@ -0,0 +1,615 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Tests for adding shapes of other types than AutoShapes, their +// formats (callouts, connectors, form controls, nodes, text +// effects, pictures, shadows, glows, soft edges, reflections, +// text frames, columns, paragraphs, bullets, and tab stops), +// and aligning, distributing, scaling, and rotating shapes +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#include +#include + +#include "excel_test_fixture.h" +#include "temp_files.h" + +#if WXAUTOEXCEL_USE_SHAPES + +using namespace wxAutoExcel; + +namespace +{ + +wxExcelShapes GetShapes(ExcelTestWorkbook& book) +{ + wxExcelShapes shapes = book.GetWorksheet().GetShapes(); + REQUIRE(shapes); + return shapes; +} + +wxExcelShape AddRectangle(wxExcelShapes& shapes, double left, double top, + double width = 100, double height = 50) +{ + wxExcelShape shape = shapes.AddShape(msoShapeRectangle, left, top, width, height); + REQUIRE(shape); + return shape; +} + +wxString GetText(wxExcelShape& shape) +{ + wxExcelTextRange2 textRange = shape.GetTextFrame2().GetTextRange(); + REQUIRE(textRange); + const wxString text = textRange.GetText(); + REQUIRE(textRange); + return text; +} + +void SetText(wxExcelShape& shape, const wxString& text) +{ + wxExcelTextRange2 textRange = shape.GetTextFrame2().GetTextRange(); + REQUIRE(textRange); + textRange.SetText(text); + REQUIRE(textRange); +} + +long GetNodeCount(wxExcelShape& shape) +{ + wxExcelShapeNodes nodes = shape.GetNodes(); + REQUIRE(nodes); + const long count = nodes.GetCount(); + REQUIRE(nodes); + return count; +} + +} // unnamed namespace + +TEST_CASE("wxExcelShapes adds text boxes, labels, callouts, and text effects", + "[excel][shapes][text]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + + wxExcelShape textBox = shapes.AddTextbox(msoTextOrientationHorizontal, 10, 10, 100, 30); + REQUIRE(textBox); + CHECK(textBox.GetType() == msoTextBox); + SetText(textBox, "Text box"); + CHECK(GetText(textBox) == "Text box"); + + wxExcelShape label = shapes.AddLabel(msoTextOrientationHorizontal, 10, 50, 100, 30); + REQUIRE(label); + SetText(label, "Label"); + CHECK(GetText(label) == "Label"); + + // Excel reports msoCalloutOne for msoCalloutTwo, so use a callout with + // a line of two segments, whose type it reports as given + wxExcelShape callout = shapes.AddCallout(msoCalloutThree, 150, 10, 100, 50); + REQUIRE(callout); + CHECK(callout.GetType() == msoCallout); + SetText(callout, "Callout"); + CHECK(GetText(callout) == "Callout"); + + wxExcelCalloutFormat calloutFormat = callout.GetCallout(); + REQUIRE(calloutFormat); + CHECK(calloutFormat.GetType() == msoCalloutThree); + calloutFormat.SetAccent(msoTrue); + calloutFormat.SetBorder(msoTrue); + calloutFormat.SetAngle(msoCalloutAngle45); + calloutFormat.PresetDrop(msoCalloutDropCenter); + calloutFormat.SetGap(5); + REQUIRE(calloutFormat); + CHECK(calloutFormat.GetAccent() == msoTrue); + CHECK(calloutFormat.GetBorder() == msoTrue); + CHECK(calloutFormat.GetAngle() == msoCalloutAngle45); + CHECK(calloutFormat.GetDropType() == msoCalloutDropCenter); + CHECK(calloutFormat.GetGap() == Catch::Approx(5.0)); + REQUIRE(calloutFormat); + + wxExcelShape textEffect = shapes.AddTextEffect(msoTextEffect1, "Effect", "Arial", 24, + msoTrue, msoFalse, 10, 100); + REQUIRE(textEffect); + wxExcelTextEffectFormat textEffectFormat = textEffect.GetTextEffect(); + REQUIRE(textEffectFormat); + CHECK(textEffectFormat.GetText() == "Effect"); + CHECK(textEffectFormat.GetFontName() == "Arial"); + CHECK(textEffectFormat.GetFontSize() == 24.0); + CHECK(textEffectFormat.GetFontBold() == msoTrue); + CHECK(textEffectFormat.GetFontItalic() == msoFalse); + REQUIRE(textEffectFormat); + + textEffectFormat.SetText("Changed"); + textEffectFormat.SetFontItalic(msoTrue); + textEffectFormat.SetFontSize(30); + REQUIRE(textEffectFormat); + CHECK(textEffectFormat.GetText() == "Changed"); + CHECK(textEffectFormat.GetFontItalic() == msoTrue); + CHECK(textEffectFormat.GetFontSize() == 30.0); +} + +TEST_CASE("wxExcelConnectorFormat connects and disconnects shapes", + "[excel][shapes][connector]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + wxExcelShape first = AddRectangle(shapes, 10, 10); + first.SetName("First"); + wxExcelShape second = AddRectangle(shapes, 200, 100); + second.SetName("Second"); + REQUIRE(first); + REQUIRE(second); + + wxExcelShape connector = shapes.AddConnector(msoConnectorElbow, 0, 0, 10, 10); + REQUIRE(connector); + CHECK(connector.GetConnector() == msoTrue); + + wxExcelConnectorFormat format = connector.GetConnectorFormat(); + REQUIRE(format); + CHECK(format.GetType() == msoConnectorElbow); + CHECK(format.GetBeginConnected() == msoFalse); + REQUIRE(format); + + format.BeginConnect(first, 1); + format.EndConnect(second, 3); + REQUIRE(format); + CHECK(format.GetBeginConnected() == msoTrue); + CHECK(format.GetEndConnected() == msoTrue); + CHECK(format.GetBeginConnectedShape().GetName() == "First"); + CHECK(format.GetEndConnectedShape().GetName() == "Second"); + CHECK(format.GetBeginConnectionSite() == 1); + CHECK(format.GetEndConnectionSite() == 3); + REQUIRE(format); + + connector.RerouteConnections(); + REQUIRE(connector); + CHECK(format.GetBeginConnected() == msoTrue); + + format.BeginDisconnect(); + format.EndDisconnect(); + REQUIRE(format); + CHECK(format.GetBeginConnected() == msoFalse); + CHECK(format.GetEndConnected() == msoFalse); +} + +TEST_CASE("wxExcelControlFormat changes form controls", + "[excel][shapes][controls]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + + SECTION("check box linked to a cell") + { + wxExcelShape checkBox = shapes.AddFormControl(xlCheckBox, 10, 10, 100, 20); + REQUIRE(checkBox); + CHECK(checkBox.GetType() == msoFormControl); + CHECK(checkBox.GetFormControlType() == xlCheckBox); + + wxExcelControlFormat control = checkBox.GetControlFormat(); + REQUIRE(control); + control.SetLinkedCell("$A$1"); + REQUIRE(control); + CHECK(control.GetLinkedCell() == "$A$1"); + + control.SetValue(xlOn); + REQUIRE(control); + CHECK(control.GetValue() == xlOn); + CHECK(book.GetRange("A1").GetValue().GetBool()); + + control.SetValue(xlOff); + REQUIRE(control); + CHECK_FALSE(book.GetRange("A1").GetValue().GetBool()); + } + + SECTION("list box with items") + { + wxExcelShape listBox = shapes.AddFormControl(xlListBox, 10, 10, 100, 60); + REQUIRE(listBox); + wxExcelControlFormat control = listBox.GetControlFormat(); + REQUIRE(control); + + control.AddItem("One", NULL); + control.AddItem("Two", NULL); + long index = 1; + control.AddItem("Zero", &index); + REQUIRE(control); + CHECK(control.GetListCount() == 3); + CHECK(control.List(1) == "Zero"); + CHECK(control.List(3) == "Two"); + REQUIRE(control); + + control.SetListIndex(2); + REQUIRE(control); + CHECK(control.GetListIndex() == 2); + + control.RemoveItem(1); + REQUIRE(control); + CHECK(control.GetListCount() == 2); + CHECK(control.List(1) == "One"); + + wxArrayString items; + items.push_back("A"); + items.push_back("B"); + control.SetList(items); + REQUIRE(control); + wxArrayString list = control.List(); + REQUIRE(control); + REQUIRE(list.size() == 2); + CHECK(list[1] == "B"); + + control.RemoveAllItems(); + REQUIRE(control); + CHECK(control.GetListCount() == 0); + } + + SECTION("list box filled from a range") + { + book.GetRange("A1").SetValue("Red"); + book.GetRange("A2").SetValue("Green"); + book.GetRange("A3").SetValue("Blue"); + + wxExcelShape listBox = shapes.AddFormControl(xlListBox, 100, 10, 100, 60); + REQUIRE(listBox); + wxExcelControlFormat control = listBox.GetControlFormat(); + REQUIRE(control); + control.SetListFillRange("$A$1:$A$3"); + REQUIRE(control); + CHECK(control.GetListFillRange() == "$A$1:$A$3"); + CHECK(control.GetListCount() == 3); + CHECK(control.List(3) == "Blue"); + REQUIRE(control); + } + + SECTION("scroll bar") + { + wxExcelShape scrollBar = shapes.AddFormControl(xlScrollBar, 10, 10, 20, 100); + REQUIRE(scrollBar); + wxExcelControlFormat control = scrollBar.GetControlFormat(); + REQUIRE(control); + control.SetMin(10); + control.SetMax(50); + control.SetSmallChange(2); + control.SetLargeChange(10); + control.SetValue(20); + REQUIRE(control); + CHECK(control.GetMin() == 10); + CHECK(control.GetMax() == 50); + CHECK(control.GetSmallChange() == 2); + CHECK(control.GetLargeChange() == 10); + CHECK(control.GetValue() == 20); + REQUIRE(control); + } +} + +TEST_CASE("wxExcelShapeNodes changes the nodes of a polyline and a freeform", + "[excel][shapes][nodes]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + + SECTION("polyline") + { + wxVector points; + points.push_back(wxPoint2DDouble(10, 10)); + points.push_back(wxPoint2DDouble(100, 50)); + points.push_back(wxPoint2DDouble(10, 100)); + wxExcelShape polyline = shapes.AddPolyline(points); + REQUIRE(polyline); + CHECK(polyline.GetType() == msoFreeform); + CHECK(GetNodeCount(polyline) == 3); + + wxExcelShapeNodes nodes = polyline.GetNodes(); + REQUIRE(nodes); + wxExcelShapeNode second = nodes.Item(2); + REQUIRE(second); + CHECK(second.GetSegmentType() == msoSegmentLine); + wxVector secondPoints = second.GetPoints(); + REQUIRE(second); + REQUIRE(secondPoints.size() == 1); + CHECK(secondPoints[0].m_x == Catch::Approx(100.0)); + CHECK(secondPoints[0].m_y == Catch::Approx(50.0)); + + nodes.Insert(2, msoSegmentLine, msoEditingAuto, 60, 20); + REQUIRE(nodes); + CHECK(GetNodeCount(polyline) == 4); + + // the node is inserted after the given one + nodes.SetPosition(3, 120, 60); + REQUIRE(nodes); + secondPoints = nodes.Item(3).GetPoints(); + REQUIRE(secondPoints.size() == 1); + CHECK(secondPoints[0].m_x == Catch::Approx(120.0)); + + nodes.Delete(2); + REQUIRE(nodes); + CHECK(GetNodeCount(polyline) == 3); + } + + SECTION("freeform") + { + wxExcelFreeformBuilder builder = shapes.BuildFreeform(msoEditingAuto, 10, 10); + REQUIRE(builder); + builder.AddNodes(msoSegmentLine, msoEditingAuto, 100, 10); + builder.AddNodes(msoSegmentLine, msoEditingAuto, 100, 100); + builder.AddNodes(msoSegmentLine, msoEditingAuto, 10, 100); + REQUIRE(builder); + + wxExcelShape freeform = builder.ConvertToShape(); + REQUIRE(freeform); + CHECK(freeform.GetType() == msoFreeform); + CHECK(GetNodeCount(freeform) == 4); + CHECK(freeform.GetWidth() == Catch::Approx(90.0)); + REQUIRE(freeform); + } +} + +TEST_CASE("wxExcelPictureFormat changes a picture", + "[excel][shapes][picture]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + TempPicture file; + wxExcelShape picture = GetShapes(book).AddPicture(file.GetPath(), msoFalse, msoTrue, 10, 10, 40, 40); + REQUIRE(picture); + CHECK(picture.GetType() == msoPicture); + REQUIRE(picture); + + wxExcelPictureFormat format = picture.GetPictureFormat(); + REQUIRE(format); + CHECK(format.GetBrightness() == Catch::Approx(0.5)); + REQUIRE(format); + + format.SetBrightness(0.7); + format.SetContrast(0.6); + REQUIRE(format); + CHECK(format.GetBrightness() == Catch::Approx(0.7)); + CHECK(format.GetContrast() == Catch::Approx(0.6)); + + format.IncrementBrightness(-0.1); + format.IncrementContrast(0.1); + REQUIRE(format); + CHECK(format.GetBrightness() == Catch::Approx(0.6)); + CHECK(format.GetContrast() == Catch::Approx(0.7)); + + format.SetColorType(msoPictureGrayscale); + REQUIRE(format); + CHECK(format.GetColorType() == msoPictureGrayscale); +} + +TEST_CASE("wxExcelShape effects change shadow, glow, soft edges, and reflection", + "[excel][shapes][effects]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + wxExcelShape shape = AddRectangle(shapes, 10, 10); + + wxExcelShadowFormat shadow = shape.GetShadow(); + REQUIRE(shadow); + shadow.SetVisible(msoTrue); + shadow.SetOffsetX(5); + shadow.SetOffsetY(-3); + shadow.SetBlur(4); + shadow.SetTransparency(0.5); + REQUIRE(shadow); + CHECK(shadow.GetVisible() == msoTrue); + CHECK(shadow.GetOffsetX() == Catch::Approx(5.0)); + CHECK(shadow.GetOffsetY() == Catch::Approx(-3.0)); + CHECK(shadow.GetBlur() == Catch::Approx(4.0)); + CHECK(shadow.GetTransparency() == Catch::Approx(0.5)); + REQUIRE(shadow); + + wxExcelGlowFormat glow = shape.GetGlow(); + REQUIRE(glow); + glow.SetRadius(8); + REQUIRE(glow); + wxExcelColorFormat glowColor = glow.GetColor(); + REQUIRE(glowColor); + glowColor.SetRGB(*wxRED); + REQUIRE(glowColor); + CHECK(glow.GetRadius() == Catch::Approx(8.0)); + CHECK(glow.GetColor().GetRGB() == *wxRED); + REQUIRE(glow); + + wxExcelSoftEdgeFormat softEdge = shape.GetSoftEdge(); + REQUIRE(softEdge); + softEdge.SetType(msoSoftEdgeType2); + REQUIRE(softEdge); + CHECK(softEdge.GetType() == msoSoftEdgeType2); + + wxExcelReflectionFormat reflection = shape.GetReflection(); + REQUIRE(reflection); + reflection.SetType(msoReflectionType3); + REQUIRE(reflection); + CHECK(reflection.GetType() == msoReflectionType3); +} + +TEST_CASE("wxExcelTextFrame changes the text layout of a shape", + "[excel][shapes][text]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + wxExcelShape shape = AddRectangle(shapes, 10, 10, 150, 80); + SetText(shape, "Some text"); + + wxExcelTextFrame frame = shape.GetTextFrame(); + REQUIRE(frame); + CHECK(frame.Characters().GetText() == "Some text"); + long start = 6, length = 4; + CHECK(frame.Characters(&start, &length).GetText() == "text"); + REQUIRE(frame); + + frame.SetMarginLeft(10); + frame.SetMarginTop(5); + frame.SetHorizontalAlignment(xlHAlignRight); + frame.SetVerticalAlignment(xlVAlignTop); + REQUIRE(frame); + CHECK(frame.GetMarginLeft() == Catch::Approx(10.0)); + CHECK(frame.GetMarginTop() == Catch::Approx(5.0)); + CHECK(frame.GetHorizontalAlignment() == xlHAlignRight); + CHECK(frame.GetVerticalAlignment() == xlVAlignTop); + REQUIRE(frame); + + frame.SetAutoSize(true); + REQUIRE(frame); + CHECK(frame.GetAutoSize()); + + wxExcelTextColumn2 column = shape.GetTextFrame2().GetColumn(); + REQUIRE(column); + column.SetNumber(2); + column.SetSpacing(12); + REQUIRE(column); + CHECK(column.GetNumber() == 2); + CHECK(column.GetSpacing() == Catch::Approx(12.0)); +} + +TEST_CASE("wxExcelParagraphFormat2 changes alignment, bullets, and tab stops", + "[excel][shapes][text]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + wxExcelShape shape = AddRectangle(shapes, 10, 10, 150, 80); + SetText(shape, "First\rSecond"); + + wxExcelTextRange2 text = shape.GetTextFrame2().GetTextRange(); + REQUIRE(text); + wxExcelParagraphFormat2 paragraph = text.GetParagraphFormat(); + REQUIRE(paragraph); + + paragraph.SetAlignment(msoAlignCenter); + paragraph.SetLeftIndent(10); + paragraph.SetSpaceAfter(6); + REQUIRE(paragraph); + CHECK(paragraph.GetAlignment() == msoAlignCenter); + CHECK(paragraph.GetLeftIndent() == Catch::Approx(10.0)); + CHECK(paragraph.GetSpaceAfter() == Catch::Approx(6.0)); + REQUIRE(paragraph); + + wxExcelBulletFormat2 bullet = paragraph.GetBullet(); + REQUIRE(bullet); + bullet.SetVisible(msoTrue); + bullet.SetType(msoBulletNumbered); + bullet.SetStartValue(3); + REQUIRE(bullet); + CHECK(bullet.GetVisible() == msoTrue); + CHECK(bullet.GetType() == msoBulletNumbered); + CHECK(bullet.GetStartValue() == 3); + REQUIRE(bullet); + + bullet.SetType(msoBulletUnnumbered); + bullet.SetCharacter(8226); + bullet.SetRelativeSize(1.5); + REQUIRE(bullet); + CHECK(bullet.GetCharacter() == 8226); + CHECK(bullet.GetRelativeSize() == Catch::Approx(1.5)); + REQUIRE(bullet); + + wxExcelTabStops2 tabStops = paragraph.GetTabStops(); + REQUIRE(tabStops); + CHECK(tabStops.GetCount() == 0); + REQUIRE(tabStops.Add(msoTabStopLeft, 20)); + REQUIRE(tabStops.Add(msoTabStopRight, 60)); + CHECK(tabStops.GetCount() == 2); + REQUIRE(tabStops); + + wxExcelTabStop2 right = tabStops.Item(2); + REQUIRE(right); + CHECK(right.GetType() == msoTabStopRight); + CHECK(right.GetPosition() == Catch::Approx(60.0)); + right.SetPosition(80); + REQUIRE(right); + CHECK(tabStops.Item(2).GetPosition() == Catch::Approx(80.0)); + + tabStops.Item(1).Clear(); + REQUIRE(tabStops); + CHECK(tabStops.GetCount() == 1); +} + +TEST_CASE("wxExcelShapeRange aligns and distributes shapes", + "[excel][shapes][range]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + wxExcelShape first = AddRectangle(shapes, 10, 10, 50, 50); + wxExcelShape second = AddRectangle(shapes, 40, 100, 50, 50); + wxExcelShape third = AddRectangle(shapes, 300, 200, 50, 50); + + wxVector indices; + indices.push_back(1); + indices.push_back(2); + indices.push_back(3); + wxExcelShapeRange range = shapes.GetRange(indices); + REQUIRE(range); + + range.Align(msoAlignLefts); + REQUIRE(range); + CHECK(first.GetLeft() == Catch::Approx(10.0)); + CHECK(second.GetLeft() == Catch::Approx(10.0)); + CHECK(third.GetLeft() == Catch::Approx(10.0)); + + // the space between the shapes becomes the same, the outer ones stay + range.Distribute(msoDistributeVertically); + REQUIRE(range); + CHECK(first.GetTop() == Catch::Approx(10.0)); + CHECK(third.GetTop() == Catch::Approx(200.0)); + CHECK(second.GetTop() == Catch::Approx(105.0)); +} + +TEST_CASE("wxExcelShape scales and rotates", + "[excel][shapes]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = GetShapes(book); + wxExcelShape shape = AddRectangle(shapes, 10, 10, 100, 50); + + MsoScaleFrom fromTopLeft = msoScaleFromTopLeft; + shape.ScaleWidth(2, msoFalse, &fromTopLeft); + shape.ScaleHeight(0.5, msoFalse, &fromTopLeft); + REQUIRE(shape); + CHECK(shape.GetWidth() == Catch::Approx(200.0)); + CHECK(shape.GetHeight() == Catch::Approx(25.0)); + CHECK(shape.GetLeft() == Catch::Approx(10.0)); + REQUIRE(shape); + + shape.IncrementRotation(30); + REQUIRE(shape); + CHECK(shape.GetRotation() == Catch::Approx(30.0)); + shape.IncrementRotation(-45); + REQUIRE(shape); + CHECK(shape.GetRotation() == Catch::Approx(345.0)); + + wxExcelThreeDFormat threeD = shape.GetThreeD(); + REQUIRE(threeD); + threeD.IncrementRotationX(20); + threeD.IncrementRotationY(10); + threeD.IncrementRotationZ(5); + REQUIRE(threeD); + CHECK(threeD.GetRotationX() == Catch::Approx(20.0)); + CHECK(threeD.GetRotationY() == Catch::Approx(10.0)); + CHECK(threeD.GetRotationZ() == Catch::Approx(5.0)); + REQUIRE(threeD); + + threeD.ResetRotation(); + REQUIRE(threeD); + CHECK(threeD.GetRotationX() == Catch::Approx(0.0)); + CHECK(threeD.GetRotationY() == Catch::Approx(0.0)); +} + +#endif // WXAUTOEXCEL_USE_SHAPES diff --git a/tests/wxExcelWindow.cpp b/tests/wxExcelWindow.cpp new file mode 100644 index 00000000..c9085460 --- /dev/null +++ b/tests/wxExcelWindow.cpp @@ -0,0 +1,231 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Tests for wxExcelWindows, wxExcelWindow, wxExcelPanes, +// wxExcelPane, wxExcelSheetViews, and wxExcelWorksheetView +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#include + +#include "excel_test_fixture.h" + +using namespace wxAutoExcel; + +namespace +{ + +// Returns the window of the workbook, after activating the workbook and its +// first worksheet, so that the window shows the worksheet. +wxExcelWindow GetWindow(ExcelTestWorkbook& book) +{ + REQUIRE(book.GetWorkbook().Activate()); + REQUIRE(book.GetWorksheet().Activate()); + + wxExcelWindows windows = book.GetWorkbook().GetWindows(); + REQUIRE(windows); + wxExcelWindow window = windows.GetItem(1); + REQUIRE(window); + return window; +} + +long GetPaneCount(wxExcelWindow& window) +{ + wxExcelPanes panes = window.GetPanes(); + REQUIRE(panes); + const long count = panes.GetCount(); + REQUIRE(panes); + return count; +} + +// Returns the address of the top-left cell of the range, e.g. "C10". +wxString GetTopLeftCell(wxExcelRange range) +{ + REQUIRE(range); + const wxString address = range.GetRange("A1").GetAddress(false, false); + REQUIRE(range); + return address; +} + +} // unnamed namespace + +TEST_CASE("wxExcelWindow shows the active sheet and cell of its workbook", + "[excel][window]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelWindow window = GetWindow(book); + + CHECK(window.GetType() == xlWorkbook); + CHECK(window.GetIndex() == 1); + CHECK(window.GetCaption() == book.GetWorkbook().GetName()); + REQUIRE(window); + + wxExcelSheet sheet = window.GetActiveSheet(); + REQUIRE(sheet); + CHECK(sheet.GetName() == book.GetWorksheet().GetName()); + + REQUIRE(book.GetRange("C3").Activate()); + wxExcelRange activeCell = window.GetActiveCell(); + REQUIRE(activeCell); + CHECK(activeCell.GetAddress(false, false) == "C3"); + + CHECK(book.GetWorkbook().GetWindows().GetCount() == 1); + wxExcelWindow newWindow = window.NewWindow(); + REQUIRE(newWindow); + CHECK(book.GetWorkbook().GetWindows().GetCount() == 2); + CHECK(newWindow.GetIndex() == 1); +} + +TEST_CASE("wxExcelWindow changes zoom, view, and displayed elements", + "[excel][window]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelWindow window = GetWindow(book); + + window.SetZoom(150); + REQUIRE(window); + CHECK(window.GetZoom() == 150); + + CHECK(window.GetDisplayGridlines()); + window.SetDisplayGridlines(false); + REQUIRE(window); + CHECK_FALSE(window.GetDisplayGridlines()); + + CHECK(window.GetDisplayHeadings()); + window.SetDisplayHeadings(false); + REQUIRE(window); + CHECK_FALSE(window.GetDisplayHeadings()); + + window.SetDisplayFormulas(true); + REQUIRE(window); + CHECK(window.GetDisplayFormulas()); + + window.SetDisplayZeros(false); + REQUIRE(window); + CHECK_FALSE(window.GetDisplayZeros()); + + CHECK(window.GetView() == xlNormalView); + window.SetView(xlPageLayoutView); + REQUIRE(window); + CHECK(window.GetView() == xlPageLayoutView); + window.SetView(xlNormalView); + REQUIRE(window); + CHECK(window.GetView() == xlNormalView); +} + +TEST_CASE("wxExcelWindow splits and freezes its panes", + "[excel][window][panes]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelWindow window = GetWindow(book); + + CHECK_FALSE(window.GetSplit()); + CHECK(GetPaneCount(window) == 1); + + window.SetSplitRow(2); + window.SetSplitColumn(1); + REQUIRE(window); + CHECK(window.GetSplit()); + CHECK(window.GetSplitRow() == 2); + CHECK(window.GetSplitColumn() == 1); + CHECK(GetPaneCount(window) == 4); + + // each pane starts at its own cell + wxExcelPanes panes = window.GetPanes(); + REQUIRE(panes); + wxExcelPane bottomRight = panes.GetItem(4); + REQUIRE(bottomRight); + CHECK(bottomRight.GetIndex() == 4); + CHECK(GetTopLeftCell(bottomRight.GetVisibleRange()) == "B3"); + CHECK(GetTopLeftCell(panes.GetItem(1).GetVisibleRange()) == "A1"); + + CHECK_FALSE(window.GetFreezePanes()); + window.SetFreezePanes(true); + REQUIRE(window); + CHECK(window.GetFreezePanes()); + CHECK(GetPaneCount(window) == 4); + + window.SetFreezePanes(false); + window.SetSplit(false); + REQUIRE(window); + CHECK_FALSE(window.GetFreezePanes()); + CHECK_FALSE(window.GetSplit()); + CHECK(GetPaneCount(window) == 1); +} + +TEST_CASE("wxExcelWindow and wxExcelPane scroll", + "[excel][window][panes]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelWindow window = GetWindow(book); + + window.SetScrollRow(10); + window.SetScrollColumn(3); + REQUIRE(window); + CHECK(window.GetScrollRow() == 10); + CHECK(window.GetScrollColumn() == 3); + CHECK(GetTopLeftCell(window.GetVisibleRange()) == "C10"); + + long down = 2; + REQUIRE(window.SmallScroll(&down)); + CHECK(window.GetScrollRow() == 12); + + // the only pane scrolls with the window + wxExcelPane pane = window.GetActivePane(); + REQUIRE(pane); + CHECK(pane.GetScrollRow() == 12); + CHECK(pane.GetScrollColumn() == 3); + + long toLeft = 1; + REQUIRE(pane.SmallScroll(NULL, NULL, NULL, &toLeft)); + CHECK(pane.GetScrollColumn() == 2); + CHECK(window.GetScrollColumn() == 2); + + pane.SetScrollRow(1); + pane.SetScrollColumn(1); + REQUIRE(pane); + CHECK(GetTopLeftCell(pane.GetVisibleRange()) == "A1"); +} + +TEST_CASE("wxExcelWorksheetView changes how the window shows its worksheet", + "[excel][window][sheetviews]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelWindow window = GetWindow(book); + + wxExcelSheetViews sheetViews = window.GetSheetViews(); + REQUIRE(sheetViews); + CHECK(sheetViews.GetCount() == 1); + REQUIRE(sheetViews); + + wxExcelSheetView sheetView = sheetViews.GetItem(1); + REQUIRE(sheetView); + CHECK(sheetView.IsView(wxExcelSheetView::WorksheetView)); + CHECK_FALSE(sheetView.IsView(wxExcelSheetView::ChartView)); + + wxExcelWorksheetView worksheetView = sheetView.ToWorksheetView(); + REQUIRE(worksheetView); + + wxExcelWorksheet sheet = worksheetView.GetSheet(); + REQUIRE(sheet); + CHECK(sheet.GetName() == book.GetWorksheet().GetName()); + + worksheetView.SetDisplayGridlines(false); + REQUIRE(worksheetView); + CHECK_FALSE(worksheetView.GetDisplayGridlines()); + CHECK_FALSE(window.GetDisplayGridlines()); + + worksheetView.SetDisplayZeros(false); + REQUIRE(worksheetView); + CHECK_FALSE(window.GetDisplayZeros()); +} diff --git a/tests/wxExcelWorkbook.cpp b/tests/wxExcelWorkbook.cpp index 4853512f..b29d44ba 100644 --- a/tests/wxExcelWorkbook.cpp +++ b/tests/wxExcelWorkbook.cpp @@ -443,3 +443,69 @@ TEST_CASE("wxExcelWorkbook Close saves the changes or discards them", CHECK(GetCellValue(reopened, "A1").GetDouble() == 3.0); } } + +TEST_CASE("wxExcelWorkbook changes and breaks links to other workbooks", + "[excel][workbook][links]") +{ + TempFolder folder; + const wxString sourceName = folder.GetFilePath("Source.xlsx"); + const wxString otherName = folder.GetFilePath("Other.xlsx"); + wxString sheetName; + + // the linked workbooks, with different values in A1 + { + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + sheetName = book.GetWorksheet().GetName(); + XlFileFormat fileFormat = xlOpenXMLWorkbook; + + book.GetRange("A1").SetValue(wxVariant(7L)); + REQUIRE(book.GetWorkbook().SaveAs(sourceName, &fileFormat)); + book.GetRange("A1").SetValue(wxVariant(9L)); + REQUIRE(book.GetWorkbook().SaveAs(otherName, &fileFormat)); + } + + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + wxExcelWorkbook& workbook = book.GetWorkbook(); + + wxExcelRange cell = book.GetRange("A1"); + cell.SetFormula("='" + folder.GetPath() + wxFileName::GetPathSeparator() + + "[Source.xlsx]" + sheetName + "'!$A$1"); + REQUIRE(cell); + CHECK(cell.GetValue().GetDouble() == 7.0); + CHECK(cell.GetFormula().Contains("[Source.xlsx]")); + + XlLinkType type = xlLinkTypeExcelLinks; + workbook.ChangeLink(sourceName, otherName, &type); + REQUIRE(workbook); + CHECK(cell.GetFormula().Contains("[Other.xlsx]")); + CHECK(cell.GetValue().GetDouble() == 9.0); + + // the formula is replaced with its value + workbook.BreakLink(otherName, xlLinkTypeExcelLinks); + REQUIRE(workbook); + CHECK(cell.GetHasFormula().GetState() == wxXlTribool::tb_false); + CHECK(cell.GetValue().GetDouble() == 9.0); +} + +TEST_CASE("wxExcelWorkbook deletes a custom number format", + "[excel][workbook][format]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + // a whole number, as its text does not depend on the decimal separator + const wxString format = "0\" units\""; + wxExcelRange cell = book.GetRange("A1"); + cell.SetValue(wxVariant(2L)); + cell.SetNumberformat(format); + REQUIRE(cell); + CHECK(cell.GetText() == "2 units"); + + // the cells using the deleted format get the General format + book.GetWorkbook().DeleteNumberFormat(format); + REQUIRE(book.GetWorkbook()); + CHECK(cell.GetNumberformat() == "General"); + CHECK(cell.GetText() == "2"); +} diff --git a/tests/wxExcelWorkbook_objects.cpp b/tests/wxExcelWorkbook_objects.cpp new file mode 100644 index 00000000..01fe1981 --- /dev/null +++ b/tests/wxExcelWorkbook_objects.cpp @@ -0,0 +1,243 @@ +///////////////////////////////////////////////////////////////////////////// +// Purpose: Tests for the objects of worksheets, workbooks, and the +// application: custom properties, cell errors and error +// checking, table styles, OLE objects, and multithreaded +// calculation +// Author: Claude Opus 5.5 (Anthropic), under the direction of PB +// Copyright: (c) 2026 PB +// License: MIT license +///////////////////////////////////////////////////////////////////////////// + +#include +#include + +#include "excel_test_fixture.h" +#include "temp_files.h" + +using namespace wxAutoExcel; + +namespace +{ + +// The OLEObjects collection is not updated when objects are added or +// deleted, so a new one must be obtained to count them. +long GetOLEObjectCount(ExcelTestWorkbook& book) +{ + wxExcelOLEObjects objects = book.GetWorksheet().OLEObjects(); + REQUIRE(objects); + const long count = objects.GetCount(); + REQUIRE(objects); + return count; +} + +} // unnamed namespace + +TEST_CASE("wxExcelCustomProperties adds, changes, and deletes properties", + "[excel][worksheet][customproperties]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelCustomProperties properties = book.GetWorksheet().GetCustomProperties(); + REQUIRE(properties); + CHECK(properties.GetCount() == 0); + + wxExcelCustomProperty key = properties.Add("Key", "Value"); + REQUIRE(key); + REQUIRE(properties.Add("Number", wxVariant(42L))); + CHECK(properties.GetCount() == 2); + REQUIRE(properties); + + CHECK(key.GetName() == "Key"); + CHECK(key.GetValue().GetString() == "Value"); + REQUIRE(key); + + key.SetValue("Changed"); + REQUIRE(key); + CHECK(properties.GetItem(1).GetValue().GetString() == "Changed"); + + wxExcelCustomProperty number = properties.GetItem(2); + REQUIRE(number); + CHECK(number.GetName() == "Number"); + CHECK(number.GetValue().GetLong() == 42); + REQUIRE(number); + + long count = 0; + for ( wxExcelCustomProperty property : properties ) + { + CHECK(property); + ++count; + } + CHECK(count == 2); + + key.Delete(); + REQUIRE(key); + CHECK(properties.GetCount() == 1); + CHECK(properties.GetItem(1).GetName() == "Number"); +} + +TEST_CASE("wxExcelErrors reports and ignores the errors of a cell", + "[excel][range][errors]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelErrorCheckingOptions options = wxAutoExcelTests::GetApplication().GetErrorCheckingOptions(); + REQUIRE(options); + REQUIRE(options.GetNumberAsText()); + + wxExcelRange text = book.GetRange("A1"); + text.SetValue("'123"); + REQUIRE(text); + wxExcelRange number = book.GetRange("A2"); + number.SetValue(wxVariant(123L)); + REQUIRE(number); + + wxExcelError textError = text.GetErrors().GetItem(xlNumberAsText); + REQUIRE(textError); + CHECK(textError.GetValue()); + CHECK_FALSE(textError.GetIgnore()); + REQUIRE(textError); + + wxExcelError numberError = number.GetErrors().GetItem(xlNumberAsText); + REQUIRE(numberError); + CHECK_FALSE(numberError.GetValue()); + REQUIRE(numberError); + + textError.SetIgnore(true); + REQUIRE(textError); + CHECK(text.GetErrors().GetItem(xlNumberAsText).GetIgnore()); + + // the checking can be turned off for the whole application + options.SetNumberAsText(false); + REQUIRE(options); + CHECK_FALSE(options.GetNumberAsText()); + options.SetNumberAsText(true); + REQUIRE(options); + CHECK(options.GetNumberAsText()); +} + +TEST_CASE("wxExcelMultiThreadedCalculation changes the thread mode", + "[excel][application][calculation]") +{ + wxExcelMultiThreadedCalculation calculation = + wxAutoExcelTests::GetApplication().GetMultiThreadedCalculation(); + REQUIRE(calculation); + + const bool enabled = calculation.GetEnabled(); + const XlThreadMode mode = calculation.GetThreadMode(); + const long count = calculation.GetThreadCount(); + REQUIRE(calculation); + CHECK(count >= 1); + + calculation.SetEnabled(!enabled); + REQUIRE(calculation); + CHECK(calculation.GetEnabled() == !enabled); + + calculation.SetThreadMode(xlThreadModeManual); + REQUIRE(calculation); + CHECK(calculation.GetThreadMode() == xlThreadModeManual); + + calculation.SetEnabled(enabled); + calculation.SetThreadMode(mode); + REQUIRE(calculation); + CHECK(calculation.GetEnabled() == enabled); + CHECK(calculation.GetThreadMode() == mode); +} + +TEST_CASE("wxExcelTableStyles adds, formats, and deletes a custom table style", + "[excel][workbook][tablestyles]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelTableStyles styles = book.GetWorkbook().GetTableStyles(); + REQUIRE(styles); + const long builtInCount = styles.GetCount(); + REQUIRE(styles); + CHECK(builtInCount > 0); + CHECK(styles.GetItem("TableStyleMedium2").GetBuiltIn()); + + wxExcelTableStyle style = styles.Add("TestStyle"); + REQUIRE(style); + CHECK(styles.GetCount() == builtInCount + 1); + CHECK(style.GetName() == "TestStyle"); + CHECK_FALSE(style.GetBuiltIn()); + REQUIRE(style); + + wxExcelTableStyleElement header = style.GetTableStyleElements().GetItem(xlHeaderRow); + REQUIRE(header); + CHECK_FALSE(header.GetHasFormat()); + + wxExcelInterior interior = header.GetInterior(); + REQUIRE(interior); + interior.SetColor(*wxRED); + REQUIRE(interior); + CHECK(header.GetHasFormat()); + CHECK(header.GetInterior().GetColor() == *wxRED); + REQUIRE(header); + + // the style can be used for a table + book.GetRange("A1").SetValue("Header"); + book.GetRange("A2").SetValue(wxVariant(1L)); + wxExcelRange source = book.GetRange("A1:A2"); + XlYesNoGuess hasHeaders = xlYes; + wxExcelListObject table = book.GetWorksheet().GetListObjects().Add(&source, &hasHeaders); + REQUIRE(table); + table.SetTableStyle(style); + REQUIRE(table); + CHECK(table.GetTableStyle().GetName() == "TestStyle"); + CHECK(book.GetRange("A1").GetDisplayFormat().GetInterior().GetColor() == *wxRED); + + header.Clear(); + REQUIRE(header); + CHECK_FALSE(header.GetHasFormat()); + + wxExcelTableStyle copy = style.Duplicate("CopiedStyle"); + REQUIRE(copy); + CHECK(copy.GetName() == "CopiedStyle"); + CHECK(styles.GetCount() == builtInCount + 2); + + copy.Delete(); + REQUIRE(copy); + CHECK(styles.GetCount() == builtInCount + 1); +} + +TEST_CASE("wxExcelOLEObjects embeds and deletes a file", + "[excel][worksheet][oleobjects]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelOLEObjects objects = book.GetWorksheet().OLEObjects(); + REQUIRE(objects); + CHECK(GetOLEObjectCount(book) == 0); + + TempTextFile file; + double left = 100, top = 50; + wxExcelOLEObject object = objects.Add(wxEmptyString, file.GetPath(), false, false, + wxEmptyString, NULL, wxEmptyString, &left, &top); + REQUIRE(object); + CHECK(GetOLEObjectCount(book) == 1); + CHECK(object.GetprogID() == "Package"); + // Excel rounds the position to whole pixels + CHECK(object.GetLeft() == Catch::Approx(100.0).margin(1.0)); + CHECK(object.GetTop() == Catch::Approx(50.0).margin(1.0)); + REQUIRE(object); + + object.SetName("Embedded"); + REQUIRE(object); + CHECK(objects.Item("Embedded").GetprogID() == "Package"); + +#if WXAUTOEXCEL_USE_SHAPES + // the object is a shape too + wxExcelShape shape = book.GetWorksheet().GetShapes().Item("Embedded"); + REQUIRE(shape); + CHECK(shape.GetType() == msoEmbeddedOLEObject); + CHECK(shape.GetOLEFormat().GetprogID() == "Package"); + REQUIRE(shape); +#endif // WXAUTOEXCEL_USE_SHAPES + + CHECK(object.Delete()); + CHECK(GetOLEObjectCount(book) == 0); +} diff --git a/tests/wxExcel_getters.cpp b/tests/wxExcel_getters.cpp index eeb7d1a7..fb549f77 100644 --- a/tests/wxExcel_getters.cpp +++ b/tests/wxExcel_getters.cpp @@ -19,6 +19,7 @@ #include "excel_test_fixture.h" #include "getter_lists.h" +#include "temp_files.h" using namespace wxAutoExcel; @@ -161,6 +162,146 @@ TEST_CASE("Application and workbook getters succeed", CHECK_GETTERS(wxExcelStyle, style); } +TEST_CASE("Worksheet and application object getters succeed", + "[excel][getters][workbook]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelApplication& application = wxAutoExcelTests::GetApplication(); + wxExcelWorksheet& worksheet = book.GetWorksheet(); + + wxExcelCustomProperties customProperties = worksheet.GetCustomProperties(); + REQUIRE(customProperties); + wxExcelCustomProperty customProperty = customProperties.Add("Key", "Value"); + REQUIRE(customProperty); + CHECK_GETTERS(wxExcelCustomProperties, customProperties); + CHECK_GETTERS(wxExcelCustomProperty, customProperty); + + // a number stored as text is reported as an error of the cell + wxExcelRange cell = book.GetRange("A1"); + cell.SetValue("'123"); + REQUIRE(cell); + wxExcelErrors errors = cell.GetErrors(); + REQUIRE(errors); + CHECK_GETTERS(wxExcelErrors, errors); + + wxExcelError error = errors.GetItem(xlNumberAsText); + REQUIRE(error); + CHECK_GETTERS(wxExcelError, error); + + wxExcelErrorCheckingOptions errorCheckingOptions = application.GetErrorCheckingOptions(); + REQUIRE(errorCheckingOptions); + CHECK_GETTERS(wxExcelErrorCheckingOptions, errorCheckingOptions); + + wxExcelMultiThreadedCalculation multiThreadedCalculation = application.GetMultiThreadedCalculation(); + REQUIRE(multiThreadedCalculation); + CHECK_GETTERS(wxExcelMultiThreadedCalculation, multiThreadedCalculation); + + wxExcelTableStyles tableStyles = book.GetWorkbook().GetTableStyles(); + REQUIRE(tableStyles); + CHECK_GETTERS(wxExcelTableStyles, tableStyles); + + // a custom style, as the built-in ones cannot be changed + wxExcelTableStyle tableStyle = tableStyles.Add("TestStyle"); + REQUIRE(tableStyle); + wxExcelTableStyleElements tableStyleElements = tableStyle.GetTableStyleElements(); + REQUIRE(tableStyleElements); + CHECK_GETTERS(wxExcelTableStyleElements, tableStyleElements); + + wxExcelTableStyleElement tableStyleElement = tableStyleElements.GetItem(xlWholeTable); + REQUIRE(tableStyleElement); + CHECK_GETTERS(wxExcelTableStyleElement, tableStyleElement); + + TempTextFile file; + wxExcelOLEObjects oleObjects = worksheet.OLEObjects(); + REQUIRE(oleObjects); + wxExcelOLEObject oleObject = oleObjects.Add(wxEmptyString, file.GetPath()); + REQUIRE(oleObject); + CHECK_GETTERS(wxExcelOLEObjects, oleObjects); + CHECK_GETTERS(wxExcelOLEObject, oleObject); + +#if WXAUTOEXCEL_USE_SHAPES + wxExcelShape oleShape = worksheet.GetShapes().Item(oleObject.GetName()); + REQUIRE(oleShape); + wxExcelOLEFormat oleFormat = oleShape.GetOLEFormat(); + REQUIRE(oleFormat); + CHECK_GETTERS(wxExcelOLEFormat, oleFormat); +#endif // WXAUTOEXCEL_USE_SHAPES +} + +TEST_CASE("Window getters succeed", "[excel][getters][window]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelApplication& application = wxAutoExcelTests::GetApplication(); + wxExcelWorkbook& workbook = book.GetWorkbook(); + REQUIRE(workbook.Activate()); + REQUIRE(book.GetWorksheet().Activate()); + + wxExcelWindows applicationWindows = application.GetWindows(); + REQUIRE(applicationWindows); + CHECK_GETTERS(wxExcelWindows, applicationWindows); + + wxExcelWindows windows = workbook.GetWindows(); + REQUIRE(windows); + CHECK_GETTERS(wxExcelWindows, windows); + + wxExcelWindow window = windows.GetItem(1); + REQUIRE(window); + // split the window to have more panes + window.SetSplitRow(2); + window.SetSplitColumn(1); + REQUIRE(window); + CHECK_GETTERS(wxExcelWindow, window); + + wxExcelPanes panes = window.GetPanes(); + REQUIRE(panes); + CHECK_GETTERS(wxExcelPanes, panes); + + wxExcelPane pane = panes.GetItem(1); + REQUIRE(pane); + CHECK_GETTERS(wxExcelPane, pane); + + wxExcelSheetViews sheetViews = window.GetSheetViews(); + REQUIRE(sheetViews); + CHECK_GETTERS(wxExcelSheetViews, sheetViews); + + wxExcelSheetView sheetView = sheetViews.GetItem(1); + REQUIRE(sheetView); + CHECK_GETTERS(wxExcelSheetView, sheetView); + + wxExcelWorksheetView worksheetView = sheetView.ToWorksheetView(); + REQUIRE(worksheetView); + CHECK_GETTERS(wxExcelWorksheetView, worksheetView); +} + +TEST_CASE("Protection getters succeed", "[excel][getters][protection]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelProtection protection = book.GetWorksheet().GetProtection(); + REQUIRE(protection); + CHECK_GETTERS(wxExcelProtection, protection); + + wxExcelAllowEditRanges allowEditRanges = protection.GetAllowEditRanges(); + REQUIRE(allowEditRanges); + wxExcelRange range = book.GetRange("B2:C5"); + wxExcelAllowEditRange allowEditRange = allowEditRanges.Add("Inputs", range); + REQUIRE(allowEditRange); + CHECK_GETTERS(wxExcelAllowEditRanges, allowEditRanges); + CHECK_GETTERS(wxExcelAllowEditRange, allowEditRange); + + wxExcelUserAccessList users = allowEditRange.GetUsers(); + REQUIRE(users); + wxExcelUserAccess user = users.Add("Everyone", true); + REQUIRE(user); + CHECK_GETTERS(wxExcelUserAccessList, users); + CHECK_GETTERS(wxExcelUserAccess, user); +} + #if WXAUTOEXCEL_USE_CHARTS TEST_CASE("Chart getters succeed", "[excel][getters][chart]") { @@ -229,6 +370,10 @@ TEST_CASE("Chart getters succeed", "[excel][getters][chart]") REQUIRE(seriesCollection); CHECK_GETTERS(wxExcelSeriesCollection, seriesCollection); + wxExcelFullSeriesCollection fullSeriesCollection = chart.FullSeriesCollection(); + REQUIRE(fullSeriesCollection); + CHECK_GETTERS(wxExcelFullSeriesCollection, fullSeriesCollection); + wxExcelSeries series = chart.SeriesCollection(1); REQUIRE(series); series.SetHasDataLabels(true); @@ -251,6 +396,221 @@ TEST_CASE("Chart getters succeed", "[excel][getters][chart]") REQUIRE(dataLabel); CHECK_GETTERS(wxExcelDataLabel, dataLabel); } + +namespace +{ + +// Adds a chart of the given type showing the data in A1:C5. +wxExcelChart AddChart(ExcelTestWorkbook& book, XlChartType type) +{ + wxExcelChartObject chartObject = book.GetWorksheet().ChartObjects().Add(200, 10, 400, 250); + REQUIRE(chartObject); + wxExcelChart chart = chartObject.GetChart(); + REQUIRE(chart); + chart.SetSourceData(book.GetRange("A1:C5")); + chart.SetChartType(type); + REQUIRE(chart); + return chart; +} + +} // unnamed namespace + +TEST_CASE("Chart element getters succeed", "[excel][getters][chart]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + FillTable(book, "A1:C5"); + + SECTION("Column chart") + { + wxExcelChart chart = AddChart(book, xlColumnClustered); + chart.SetHasLegend(true); + chart.SetHasDataTable(true); + REQUIRE(chart); + + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + wxExcelChartFormat format = series.GetFormat(); + REQUIRE(format); + CHECK_GETTERS(wxExcelChartFormat, format); + + wxExcelChartFillFormat chartFill = chart.GetChartArea().GetFill(); + REQUIRE(chartFill); + CHECK_GETTERS(wxExcelChartFillFormat, chartFill); + + wxExcelChartColorFormat chartColor = chartFill.GetForeColor(); + REQUIRE(chartColor); + CHECK_GETTERS(wxExcelChartColorFormat, chartColor); + + double amount = 5; + REQUIRE(series.ErrorBar(xlY, xlErrorBarIncludeBoth, xlErrorBarTypeFixedValue, &amount)); + wxExcelErrorBars errorBars = series.GetErrorBars(); + REQUIRE(errorBars); + CHECK_GETTERS(wxExcelErrorBars, errorBars); + + wxExcelTrendlines trendlines = series.Trendlines(); + REQUIRE(trendlines); + wxExcelTrendline trendline = trendlines.Add(); + REQUIRE(trendline); + CHECK_GETTERS(wxExcelTrendlines, trendlines); + CHECK_GETTERS(wxExcelTrendline, trendline); + + wxExcelAxis valueAxis = chart.Axes(xlValue); + REQUIRE(valueAxis); + valueAxis.SetDisplayUnit(xlThousands); + valueAxis.SetHasDisplayUnitLabel(true); + valueAxis.SetHasMajorGridlines(true); + REQUIRE(valueAxis); + + wxExcelTickLabels tickLabels = valueAxis.GetTickLabels(); + REQUIRE(tickLabels); + CHECK_GETTERS(wxExcelTickLabels, tickLabels); + + wxExcelGridlines gridlines = valueAxis.GetMajorGridlines(); + REQUIRE(gridlines); + CHECK_GETTERS(wxExcelGridlines, gridlines); + + wxExcelDisplayUnitLabel displayUnitLabel = valueAxis.GetDisplayUnitLabel(); + REQUIRE(displayUnitLabel); + CHECK_GETTERS(wxExcelDisplayUnitLabel, displayUnitLabel); + + wxExcelLegendEntries legendEntries = chart.GetLegend().LegendEntries(); + REQUIRE(legendEntries); + CHECK_GETTERS(wxExcelLegendEntries, legendEntries); + + wxExcelLegendEntry legendEntry = legendEntries.Item(1); + REQUIRE(legendEntry); + CHECK_GETTERS(wxExcelLegendEntry, legendEntry); + + wxExcelLegendKey legendKey = legendEntry.GetLegendKey(); + REQUIRE(legendKey); + CHECK_GETTERS(wxExcelLegendKey, legendKey); + + wxExcelDataTable dataTable = chart.GetDataTable(); + REQUIRE(dataTable); + CHECK_GETTERS(wxExcelDataTable, dataTable); + + wxExcelChartGroup chartGroup = chart.ChartGroups(1); + REQUIRE(chartGroup); + wxExcelCategoryCollection categories = chartGroup.CategoryCollection(); + REQUIRE(categories); + CHECK_GETTERS(wxExcelCategoryCollection, categories); + + wxExcelChartCategory category = chartGroup.CategoryCollection(1); + REQUIRE(category); + CHECK_GETTERS(wxExcelChartCategory, category); + } + + SECTION("Line chart") + { + // make the second series lower at one point to have both up and + // down bars, Excel fails to get the bars of the kind the chart doesn't have + book.GetRange("C3").SetValue(wxVariant(0.0)); + wxExcelChart chart = AddChart(book, xlLine); + wxExcelChartGroup chartGroup = chart.ChartGroups(1); + REQUIRE(chartGroup); + chartGroup.SetHasUpDownBars(true); + chartGroup.SetHasHiLoLines(true); + chartGroup.SetHasDropLines(true); + REQUIRE(chartGroup); + + wxExcelUpBars upBars = chartGroup.GetUpBars(); + REQUIRE(upBars); + CHECK_GETTERS(wxExcelUpBars, upBars); + + wxExcelDownBars downBars = chartGroup.GetDownBars(); + REQUIRE(downBars); + CHECK_GETTERS(wxExcelDownBars, downBars); + + wxExcelHiLoLines hiLoLines = chartGroup.GetHiLoLines(); + REQUIRE(hiLoLines); + CHECK_GETTERS(wxExcelHiLoLines, hiLoLines); + + wxExcelDropLines dropLines = chartGroup.GetDropLines(); + REQUIRE(dropLines); + CHECK_GETTERS(wxExcelDropLines, dropLines); + } + + SECTION("Stacked column chart") + { + wxExcelChart chart = AddChart(book, xlColumnStacked); + wxExcelChartGroup chartGroup = chart.ChartGroups(1); + REQUIRE(chartGroup); + chartGroup.SetHasSeriesLines(true); + REQUIRE(chartGroup); + + wxExcelSeriesLines seriesLines = chartGroup.GetSeriesLines(); + REQUIRE(seriesLines); + CHECK_GETTERS(wxExcelSeriesLines, seriesLines); + } + + SECTION("Pie chart") + { + wxExcelChart chart = AddChart(book, xlPie); + wxExcelSeries series = chart.SeriesCollection(1); + REQUIRE(series); + series.SetHasDataLabels(true); + series.SetHasLeaderLines(true); + REQUIRE(series); + + wxExcelLeaderLines leaderLines = series.GetLeaderLines(); + REQUIRE(leaderLines); + CHECK_GETTERS(wxExcelLeaderLines, leaderLines); + } + + SECTION("3-D column chart") + { + wxExcelChart chart = AddChart(book, xl3DColumn); + + wxExcelFloor floor = chart.GetFloor(); + REQUIRE(floor); + CHECK_GETTERS(wxExcelFloor, floor); + + wxExcelWalls walls = chart.GetWalls(); + REQUIRE(walls); + CHECK_GETTERS(wxExcelWalls, walls); + } +} + +TEST_CASE("Sparkline getters succeed", "[excel][getters][sparklines]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + FillTable(book, "A1:E3"); + + wxExcelSparklineGroups groups = book.GetRange("F2:F3").GetSparklineGroups(); + REQUIRE(groups); + wxExcelSparklineGroup group = groups.Add(xlSparkLine, "B2:E3"); + REQUIRE(group); + CHECK_GETTERS(wxExcelSparklineGroups, groups); + CHECK_GETTERS(wxExcelSparklineGroup, group); + + wxExcelSparkline sparkline = group.GetItem(1); + REQUIRE(sparkline); + CHECK_GETTERS(wxExcelSparkline, sparkline); + + wxExcelSparkAxes axes = group.GetAxes(); + REQUIRE(axes); + CHECK_GETTERS(wxExcelSparkAxes, axes); + + wxExcelSparkHorizontalAxis horizontalAxis = axes.GetHorizontal(); + REQUIRE(horizontalAxis); + CHECK_GETTERS(wxExcelSparkHorizontalAxis, horizontalAxis); + + wxExcelSparkVerticalAxis verticalAxis = axes.GetVertical(); + REQUIRE(verticalAxis); + CHECK_GETTERS(wxExcelSparkVerticalAxis, verticalAxis); + + wxExcelSparkPoints points = group.GetPoints(); + REQUIRE(points); + CHECK_GETTERS(wxExcelSparkPoints, points); + + wxExcelSparkColor color = points.GetFirstpoint(); + REQUIRE(color); + CHECK_GETTERS(wxExcelSparkColor, color); +} #endif // WXAUTOEXCEL_USE_CHARTS #if WXAUTOEXCEL_USE_SHAPES @@ -295,6 +655,18 @@ TEST_CASE("Shape getters succeed", "[excel][getters][shape]") REQUIRE(color); CHECK_GETTERS(wxExcelColorFormat, color); + wxExcelFillFormat gradientFill = oval.GetFill(); + REQUIRE(gradientFill); + gradientFill.TwoColorGradient(msoGradientHorizontal, 1); + REQUIRE(gradientFill); + wxExcelGradientStops gradientStops = gradientFill.GetGradientStops(); + REQUIRE(gradientStops); + CHECK_GETTERS(wxExcelGradientStops, gradientStops); + + wxExcelGradientStop gradientStop = gradientStops.GetItem(1); + REQUIRE(gradientStop); + CHECK_GETTERS(wxExcelGradientStop, gradientStop); + wxExcelThreeDFormat threeD = rectangle.GetThreeD(); REQUIRE(threeD); CHECK_GETTERS(wxExcelThreeDFormat, threeD); @@ -312,6 +684,109 @@ TEST_CASE("Shape getters succeed", "[excel][getters][shape]") REQUIRE(groupShapes); CHECK_GETTERS(wxExcelGroupShapes, groupShapes); } + +TEST_CASE("Shape format getters succeed", "[excel][getters][shape]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelShapes shapes = book.GetWorksheet().GetShapes(); + REQUIRE(shapes); + + wxExcelShape rectangle = shapes.AddShape(msoShapeRectangle, 10, 10, 120, 60); + REQUIRE(rectangle); + wxExcelTextFrame2 textFrame2 = rectangle.GetTextFrame2(); + REQUIRE(textFrame2); + wxExcelTextRange2 textRange = textFrame2.GetTextRange(); + REQUIRE(textRange); + textRange.SetText("Rectangle"); + REQUIRE(textRange); + + wxExcelTextFrame textFrame = rectangle.GetTextFrame(); + REQUIRE(textFrame); + CHECK_GETTERS(wxExcelTextFrame, textFrame); + + wxExcelShadowFormat shadow = rectangle.GetShadow(); + REQUIRE(shadow); + CHECK_GETTERS(wxExcelShadowFormat, shadow); + + wxExcelGlowFormat glow = rectangle.GetGlow(); + REQUIRE(glow); + CHECK_GETTERS(wxExcelGlowFormat, glow); + + wxExcelSoftEdgeFormat softEdge = rectangle.GetSoftEdge(); + REQUIRE(softEdge); + CHECK_GETTERS(wxExcelSoftEdgeFormat, softEdge); + + wxExcelReflectionFormat reflection = rectangle.GetReflection(); + REQUIRE(reflection); + CHECK_GETTERS(wxExcelReflectionFormat, reflection); + + wxExcelTextColumn2 textColumn = textFrame2.GetColumn(); + REQUIRE(textColumn); + CHECK_GETTERS(wxExcelTextColumn2, textColumn); + + wxExcelParagraphFormat2 paragraphFormat = textRange.GetParagraphFormat(); + REQUIRE(paragraphFormat); + CHECK_GETTERS(wxExcelParagraphFormat2, paragraphFormat); + + wxExcelBulletFormat2 bullet = paragraphFormat.GetBullet(); + REQUIRE(bullet); + CHECK_GETTERS(wxExcelBulletFormat2, bullet); + + wxExcelTabStops2 tabStops = paragraphFormat.GetTabStops(); + REQUIRE(tabStops); + wxExcelTabStop2 tabStop = tabStops.Add(msoTabStopLeft, 20); + REQUIRE(tabStop); + CHECK_GETTERS(wxExcelTabStops2, tabStops); + CHECK_GETTERS(wxExcelTabStop2, tabStop); + + wxExcelShape callout = shapes.AddCallout(msoCalloutTwo, 150, 10, 100, 50); + REQUIRE(callout); + wxExcelCalloutFormat calloutFormat = callout.GetCallout(); + REQUIRE(calloutFormat); + CHECK_GETTERS(wxExcelCalloutFormat, calloutFormat); + + wxExcelShape connector = shapes.AddConnector(msoConnectorStraight, 10, 100, 100, 150); + REQUIRE(connector); + wxExcelConnectorFormat connectorFormat = connector.GetConnectorFormat(); + REQUIRE(connectorFormat); + CHECK_GETTERS(wxExcelConnectorFormat, connectorFormat); + + wxExcelShape checkBox = shapes.AddFormControl(xlCheckBox, 150, 100, 100, 20); + REQUIRE(checkBox); + wxExcelControlFormat controlFormat = checkBox.GetControlFormat(); + REQUIRE(controlFormat); + CHECK_GETTERS(wxExcelControlFormat, controlFormat); + + wxVector points; + points.push_back(wxPoint2DDouble(10, 200)); + points.push_back(wxPoint2DDouble(60, 180)); + points.push_back(wxPoint2DDouble(110, 220)); + wxExcelShape polyline = shapes.AddPolyline(points); + REQUIRE(polyline); + wxExcelShapeNodes nodes = polyline.GetNodes(); + REQUIRE(nodes); + CHECK_GETTERS(wxExcelShapeNodes, nodes); + + wxExcelShapeNode node = nodes.Item(1); + REQUIRE(node); + CHECK_GETTERS(wxExcelShapeNode, node); + + wxExcelShape textEffect = shapes.AddTextEffect(msoTextEffect1, "Text", "Arial", 20, + msoFalse, msoFalse, 150, 200); + REQUIRE(textEffect); + wxExcelTextEffectFormat textEffectFormat = textEffect.GetTextEffect(); + REQUIRE(textEffectFormat); + CHECK_GETTERS(wxExcelTextEffectFormat, textEffectFormat); + + TempPicture file; + wxExcelShape picture = shapes.AddPicture(file.GetPath(), msoFalse, msoTrue, 10, 250, 40, 40); + REQUIRE(picture); + wxExcelPictureFormat pictureFormat = picture.GetPictureFormat(); + REQUIRE(pictureFormat); + CHECK_GETTERS(wxExcelPictureFormat, pictureFormat); +} #endif // WXAUTOEXCEL_USE_SHAPES TEST_CASE("Table, sort, and filter getters succeed", @@ -352,6 +827,10 @@ TEST_CASE("Table, sort, and filter getters succeed", REQUIRE(listRow); CHECK_GETTERS(wxExcelListRow, listRow); + wxExcelListDataFormat listDataFormat = listColumn.GetListDataFormat(); + REQUIRE(listDataFormat); + CHECK_GETTERS(wxExcelListDataFormat, listDataFormat); + wxExcelTableStyle tableStyle = listObject.GetTableStyle(); REQUIRE(tableStyle); CHECK_GETTERS(wxExcelTableStyle, tableStyle); @@ -444,9 +923,63 @@ TEST_CASE("Conditional format getters succeed", wxExcelIconCriterion iconCriterion = iconCriteria.GetItem(2); REQUIRE(iconCriterion); CHECK_GETTERS(wxExcelIconCriterion, iconCriterion); + + wxExcelFormatColor barColor = databar.GetBarColor(); + REQUIRE(barColor); + CHECK_GETTERS(wxExcelFormatColor, barColor); + + wxExcelDataBarBorder barBorder = databar.GetBarBorder(); + REQUIRE(barBorder); + CHECK_GETTERS(wxExcelDataBarBorder, barBorder); + + wxExcelNegativeBarFormat negativeBarFormat = databar.GetNegativeBarFormat(); + REQUIRE(negativeBarFormat); + CHECK_GETTERS(wxExcelNegativeBarFormat, negativeBarFormat); + + wxExcelIconSets iconSets = book.GetWorkbook().GetIconSets(); + REQUIRE(iconSets); + CHECK_GETTERS(wxExcelIconSets, iconSets); + + wxExcelIconSet iconSet = iconSetCondition.GetIconSet(); + REQUIRE(iconSet); + CHECK_GETTERS(wxExcelIconSet, iconSet); + + wxExcelIcon icon = iconSet.GetItem(1); + REQUIRE(icon); + CHECK_GETTERS(wxExcelIcon, icon); } #endif // WXAUTOEXCEL_USE_CONDFORMAT +TEST_CASE("Range gradient getters succeed", "[excel][getters][range][gradient]") +{ + ExcelTestWorkbook book; + REQUIRE(book.IsReady()); + + wxExcelInterior linearInterior = book.GetRange("A1").GetInterior(); + REQUIRE(linearInterior); + linearInterior.SetPattern(xlPatternLinearGradient); + REQUIRE(linearInterior); + wxExcelLinearGradient linearGradient = linearInterior.GetLinearGradient(); + REQUIRE(linearGradient); + CHECK_GETTERS(wxExcelLinearGradient, linearGradient); + + wxExcelColorStops colorStops = linearGradient.GetColorStops(); + REQUIRE(colorStops); + CHECK_GETTERS(wxExcelColorStops, colorStops); + + wxExcelColorStop colorStop = colorStops.GetItem(1); + REQUIRE(colorStop); + CHECK_GETTERS(wxExcelColorStop, colorStop); + + wxExcelInterior rectangularInterior = book.GetRange("B1").GetInterior(); + REQUIRE(rectangularInterior); + rectangularInterior.SetPattern(xlPatternRectangularGradient); + REQUIRE(rectangularInterior); + wxExcelRectangularGradient rectangularGradient = rectangularInterior.GetRectangularGradient(); + REQUIRE(rectangularGradient); + CHECK_GETTERS(wxExcelRectangularGradient, rectangularGradient); +} + TEST_CASE("Range getters succeed for a single cell and for cells with different values", "[excel][getters][range]") { diff --git a/util/GenerateEnums/EnumDeclarationGenerator.cpp b/util/GenerateEnums/EnumDeclarationGenerator.cpp deleted file mode 100644 index 00753e88..00000000 --- a/util/GenerateEnums/EnumDeclarationGenerator.cpp +++ /dev/null @@ -1,162 +0,0 @@ -#include "EnumDeclarationGenerator.h" - -#include -#include - -bool EnumDeclarationGenerator::Generate(const EnumInfos& excelEnums, const EnumInfos& officeEnums, - std::vector& excelDeclarations, - std::vector& officeDeclarations, - bool omitDeprecated) -{ - wxCHECK_MSG(!excelEnums.empty(), false, "exceEnums cannot be empty"); - wxCHECK_MSG(!officeEnums.empty(), false, "officeEnums cannot be empty"); - wxCHECK_MSG(excelDeclarations.empty(), false, "excelDeclarations must be empty"); - wxCHECK_MSG(officeDeclarations.empty(), false, "officeDeclarations must be empty"); - - std::set excelEnumNames; - std::vector tmpExcelDeclarations; - std::vector tmpOfficeDeclarations; - - for ( const auto& e : excelEnums ) - { - if ( e.IsDeprecated() && omitDeprecated ) - continue; - - std::vector decl; - - GenerateDeclaration(e, true, decl); - tmpExcelDeclarations.insert(tmpExcelDeclarations.end(), decl.begin(), decl.end()); - AddEmptyLine(tmpExcelDeclarations); - - excelEnumNames.insert(e.GetName()); - } - - for ( const auto& e : officeEnums ) - { - if ( e.IsDeprecated() && omitDeprecated ) - continue; - - // some Excel enums are included in Office ones, skip those - if ( excelEnumNames.find(e.GetName()) != excelEnumNames.end() ) - continue; - - std::vector decl; - - GenerateDeclaration(e, false, decl); - tmpOfficeDeclarations.insert(tmpOfficeDeclarations.end(), decl.begin(), decl.end()); - AddEmptyLine(tmpOfficeDeclarations); - } - - excelDeclarations = std::move(tmpExcelDeclarations); - officeDeclarations = std::move(tmpOfficeDeclarations); - return true; -} - -void AddMissingChartTypes(EnumInfo::Fields& fields) -{ - auto AddChartType = [&fields](const auto& name, auto value) - { - if ( std::any_of(fields.begin(), - fields.end(), [&name](const auto& elem) { return elem.name.CmpNoCase(name) == 0; }) ) - { - wxLogDebug("The chart type '%s' is already there.", name); - return; - } - - EnumInfo::Field f; - - f.name = name; f.value = value; f.description = "not officially documented"; - fields.push_back(f); - }; - - AddChartType("xlBoxwhisker", 121); - AddChartType("xlFunnel", 123); - AddChartType("xlHistogram", 118); - AddChartType("xlPareto", 122); - AddChartType("xlSunburst", 120); - AddChartType("xlTreemap", 117); - AddChartType("xlWaterfall", 119); - - std::sort(fields.begin(), fields.end(), - [](const auto& a, const auto& b) { return a.name.CmpNoCase(b.name) < 0; }); -} - -bool EnumDeclarationGenerator::GenerateDeclaration(const EnumInfo& info, bool isExcel, - std::vector& declaration) -{ - const size_t leftIndentSize = 4; // 4 spaces - const wxString doxygenCommentStart = "/**"; - const wxString doxygenCommentEnd = "*/"; - const wxString excelURLStart = "https://docs.microsoft.com/office/vba/api/excel."; - const wxString officeURLStart = "https://docs.microsoft.com/office/vba/api/office."; - - wxCHECK(!info.GetName().empty(), false); - wxCHECK(declaration.empty(), false); - - EnumInfo::Fields fields = info.GetFields(); - wxString documentationURL; - - int longestName = 0; - int longestValue = 0; - - declaration.reserve(8 + fields.size()); - - declaration.push_back(doxygenCommentStart); - - declaration.push_back(info.GetDescription()); - AddEmptyLine(declaration); - - documentationURL.Printf("[Official VBA documentation for %s](%s%s)", - info.GetName(), - isExcel ? excelURLStart : officeURLStart, - info.GetName().Lower()); - declaration.push_back(documentationURL); - - declaration.push_back(doxygenCommentEnd); - - declaration.push_back(wxString::Format("enum %s", info.GetName())); - declaration.push_back("{"); - - // hotfix for newer chart types which are not documented - if ( isExcel && info.GetName() == "XlChartType" ) - AddMissingChartTypes(fields); - - for ( const auto& v : fields ) - { - longestName = wxMax(longestName, v.name.size()); - longestValue = wxMax(longestValue, wxString::Format("%ld", v.value).size()); - } - - for ( const auto& v : fields ) - { - wxString field; - - field.Printf("%-*s = %*ld,", longestName, v.name, longestValue, v.value); - if ( !v.description.empty() ) - field += wxString::Format(" /*!< %s */", v.description); - AddLeftIndent(field, leftIndentSize); - - // hotfix for Constants::xlManual which conflicts with XlSortOrder::xlManual - if ( isExcel && info.GetName() == "Constants" && v.name == "xlManual" ) - { - declaration.push_back("// xlManual is commented out here to avoid conflict with XlSortOrder::xlManual"); - field.Prepend("//"); - } - - declaration.emplace_back(field); - } - - declaration.push_back("};"); - - return true; -} - -void EnumDeclarationGenerator::AddEmptyLine(std::vector& declaration) -{ - declaration.push_back(wxString()); -} - -wxString& EnumDeclarationGenerator::AddLeftIndent(wxString& str, size_t count) -{ - return str.Pad(count, ' ', false); -} diff --git a/util/GenerateEnums/EnumDeclarationGenerator.h b/util/GenerateEnums/EnumDeclarationGenerator.h deleted file mode 100644 index e01f3533..00000000 --- a/util/GenerateEnums/EnumDeclarationGenerator.h +++ /dev/null @@ -1,20 +0,0 @@ -#pragma once - -#include "EnumInfo.h" - - -class EnumDeclarationGenerator -{ -public: - static bool Generate(const EnumInfos& excelEnums, const EnumInfos& officeEnums, - std::vector& excelDeclarations, - std::vector& officeDeclarations, - bool omitDeprecated = true); - -private: - static bool GenerateDeclaration(const EnumInfo& info, bool isExcel, - std::vector& declaration); - - static void AddEmptyLine(std::vector& declaration); - static wxString& AddLeftIndent(wxString& str, size_t count); -}; diff --git a/util/GenerateEnums/EnumInfo.cpp b/util/GenerateEnums/EnumInfo.cpp deleted file mode 100644 index 1df76be1..00000000 --- a/util/GenerateEnums/EnumInfo.cpp +++ /dev/null @@ -1,360 +0,0 @@ -#include "EnumInfo.h" - -#include -#include - -/************************************* -class EnumInfo -*************************************/ - -// Loads enum information from the official VBA documentation - -bool EnumInfo::LoadFromMDFile(const wxString& MDFileName) -{ - wxTextFile enumFile; - - if ( !enumFile.Open(MDFileName) ) - return false; - - std::vector lines; - wxString name, description; - Fields fields; - bool isDeprecated = false; - size_t startLokingForfieldsLineNo = 0; - wxString errorInfo; - - lines.reserve(enumFile.GetLineCount()); - for ( size_t i = 0; i < enumFile.GetLineCount(); ++i ) - lines.push_back(enumFile[i]); - - if ( !LoadNameAndDescription(lines, name, description, startLokingForfieldsLineNo, errorInfo) ) - { - wxLogError("File '%s': %s.", MDFileName, errorInfo); - return false; - } - - isDeprecated = CheckDeprecated(lines); - if ( isDeprecated ) - wxLogDebug("Enum '%s' is deprecated.", name); - - if ( !LoadFields(lines, startLokingForfieldsLineNo, fields, errorInfo) ) - { - if ( !isDeprecated ) - { - wxLogError("File '%s': %s.", MDFileName, errorInfo); - return false; - } - } - - m_name = name; - m_description = description; - m_fields = std::move(fields); - m_isDeprecated = isDeprecated; - - return true; -} - -wxString EnumInfo::GetName() const -{ - return m_name; -} - -wxString EnumInfo::GetDescription() const -{ - return m_description; -} - -EnumInfo::Fields EnumInfo::GetFields() const -{ - return m_fields; -} - -bool EnumInfo::IsDeprecated() const -{ - return m_isDeprecated; -} - -// Find name and description of this enum -bool EnumInfo::LoadNameAndDescription(const std::vector& lines, - wxString& name, wxString& description, - size_t& startLokingForfieldsLine, - wxString& errorInfo) -{ - wxString tmpName, tmpDescription; - - for ( size_t i = 0; i < lines.size(); ++i ) - { - const wxString& line = lines[i]; - wxString s1 = line; - wxString s2; - size_t descriptionLineIdx = 0; - - s1.Trim(true).Trim(false); - - if ( s1.StartsWith("# ", &s2) - && s2.Contains(" enumeration (") ) - { - s2.Trim(true).Trim(false); - s2 = s2.BeforeFirst(' '); - if ( s2.empty() ) - continue; - - tmpName = s2; - // there is one empty line and the line after - // that contains description - - descriptionLineIdx = i + 2; - - while ( descriptionLineIdx < lines.size() - && !lines[descriptionLineIdx].empty() ) - { - tmpDescription += lines[descriptionLineIdx++]; - } - - if ( tmpDescription.empty() ) - { - errorInfo.Printf("Could not obtain description for enum '%s' on line %zu", name, i + 1 + 2); - return false; - } - startLokingForfieldsLine = descriptionLineIdx; - - break; - } - } - - if ( tmpName.empty() ) - { - errorInfo.Printf("Could not find enum name"); - return false; - } - - name = tmpName; - description = tmpDescription; - return true; -} - -// Parse enum individual fields stored in a markdown file, where a line for an enum field looks like -// "|**BroadcastCapFileSizeLimited**|**1**|The size of the file being broadcasted is limited.|" -// where the first column has field name, second field value, and third field description -// Unfortunately, the files sometimes do not obey this format exactly, so the code has workarounds for -// the inconstencies I have encountered so far. -bool EnumInfo::LoadFields(const std::vector& lines, - const size_t startLokingForfieldsLine, - Fields& fields, wxString& errorInfo) -{ - static const size_t minSplitCount = 4; - - static const size_t nameIndex = 1; - static const size_t valueIndex = 2; - static const size_t descriptionIndex = 3; - - Fields tmpfields; - - for ( size_t i = startLokingForfieldsLine; - i < lines.size(); - ++i ) - { - const wxString& line = lines[i]; - - if ( line.StartsWith("|") ) // can be an enum field, but also the table markdown - { - wxArrayString as = wxSplit(line, '|'); - wxString s; - long l; - Field field; - - if ( as.size() < minSplitCount ) - { - continue; - } - - s = as[nameIndex]; - s.Replace("*", ""); - s.Trim(true).Trim(false); - if (s.find(' ') ) - s = s.BeforeFirst(' '); - - if ( s.empty() ) - { - errorInfo.Printf("Could not parse enum field name at line %zu", i + 1); - return false; - } - field.name = s; - - s = as[valueIndex]; - s.Replace("*", ""); - s.Trim(true).Trim(false); - if (s.find(' ') ) - s = s.BeforeFirst(' '); - if ( !s.ToCLong(&l) ) - { - continue; // probably not a line with enum field - } - field.value = l; - - s = as[descriptionIndex]; - s.Trim(true).Trim(false); - field.description = s; - - tmpfields.emplace_back(field); - } - else if ( !tmpfields.empty() ) - { - // We already parsed the block we are interested in; - // do not process any more lines, which can also - // contain different information but looking like - // lines we are interested in. - break; - } - } - - if ( tmpfields.empty() ) - { - errorInfo.Printf("Could not find any enum fields"); - return false; - } - - fields = std::move(tmpfields); - return true; -} - -bool EnumInfo::CheckDeprecated(const std::vector& lines) -{ - // Check if the line contains " deprecated" anywhere but - // in field description - for ( const auto& l : lines ) - { - wxString s = l; - - s.Trim(false); - if ( !s.StartsWith('|') && s.Contains(" deprecated") ) - return true; - } - - return false; -} - - -/************************************* -class EnumInfoLoader -*************************************/ - -bool EnumInfoLoader::LoadEnumInfos(const wxString& MDFileName, EnumInfos& enumInfos) -{ - std::vector files; - EnumInfos infos; - - LoadEnumList(MDFileName, files); - LoadEnums(files, infos); - - enumInfos = std::move(infos); - return !enumInfos.empty(); -} - -bool EnumInfoLoader::LoadEnumList(const wxString& MDFileName, std::vector& enumInfoFiles) -{ - wxTextFile enumListFile; - - if ( !enumListFile.Open(MDFileName) ) - return false; - - std::vector files; - size_t numErrors = 0; - - wxLogMessage("Loading list of files with enum descriptions from '%s'...", MDFileName); - - // Enums are listed with the enum name in brackets and the name - // of enum documentation file in parentheses, like this - // "- [BackstageGroupStyle](../../Office.BackstageGroupStyle.md)" - for ( size_t i = 0; i < enumListFile.GetLineCount(); ++i ) - { - const wxString& line = enumListFile[i]; - - if ( !line.StartsWith("- [") ) - { - if ( !files.empty() ) - { - // We already parsed the block we are interested in; - // do not process any more lines, which can also - // contain different information but looking like - // lines we are interested in. - break; - } - else - { - continue; - } - } - - const wxString enumName = line.AfterFirst('[').BeforeFirst(']'); - const wxString enumFileName = line.AfterFirst('(').BeforeLast(')'); - - if ( enumName.empty() ) - { - wxLogError("Could not obtain enum name (line %zu)", i + 1); - ++numErrors; - continue; - } - - if ( enumFileName.empty() ) - { - wxLogError("Could not obtain enum file name (line %zu)", i + 1); - ++numErrors; - continue; - } - - wxFileName enumFileNameFN(enumFileName); - - if ( !enumFileNameFN.Normalize(wxPATH_NORM_ABSOLUTE | wxPATH_NORM_DOTS, - wxFileName(MDFileName).GetPath()) ) - { - wxLogError("Could not normalize file name '%s' (line %zu)", enumFileName, i + 1); - ++numErrors; - continue; - } - - files.emplace_back(enumFileNameFN.GetFullPath()); - } - - wxLogMessage("Errors encountered: %zu, files identified: %zu.", - numErrors, files.size()); - - enumInfoFiles = std::move(files); - - return !enumInfoFiles.empty() && numErrors == 0; -} - -bool EnumInfoLoader::LoadEnums(const std::vector& enumInfoFiles, EnumInfos& enumInfos) -{ - wxCHECK_MSG(!enumInfoFiles.empty(), false, "enumInfoFiles cannot be empty"); - wxCHECK_MSG(enumInfos.empty(), false, "enumInfos must be empty"); - - EnumInfos infos; - size_t numErrors = 0; - size_t deprecatedCount = 0; - - wxLogMessage("Parsing enums from %zu files...", enumInfoFiles.size()); - - for ( const auto& infoFile : enumInfoFiles ) - { - EnumInfo info; - - if ( !info.LoadFromMDFile(infoFile) ) - { - ++numErrors; - continue; - } - - if ( info.IsDeprecated() ) - ++deprecatedCount; - - infos.emplace_back(info); - } - - wxLogMessage("Errors encountered: %zu, enums parsed: %zu (%zu deprecated).", - numErrors, infos.size(), deprecatedCount); - - enumInfos = std::move(infos); - - return !enumInfos.empty() && numErrors == 0; -} \ No newline at end of file diff --git a/util/GenerateEnums/EnumInfo.h b/util/GenerateEnums/EnumInfo.h deleted file mode 100644 index 31529ff3..00000000 --- a/util/GenerateEnums/EnumInfo.h +++ /dev/null @@ -1,59 +0,0 @@ -#pragma once - -#include - -#include -#include - -class EnumInfo -{ -public: - struct Field - { - wxString name; - long value{std::numeric_limits::min()}; - wxString description; - }; - - typedef std::vector Fields; - - EnumInfo() {} - - bool LoadFromMDFile(const wxString& MDFileName); - - wxString GetName() const; - wxString GetDescription() const; - Fields GetFields() const; - - bool IsDeprecated() const; - -private: - wxString m_name; - wxString m_description; - Fields m_fields; - bool m_isDeprecated{false}; - - static bool LoadNameAndDescription(const std::vector& lines, - wxString& name, wxString& description, - size_t& startLokingForFieldsLineNo, - wxString& errorInfo); - - static bool LoadFields(const std::vector& lines, - const size_t startLokingForFieldsLineNo, - Fields& fields, wxString& errorInfo); - - static bool CheckDeprecated(const std::vector& lines); -}; - -typedef std::vector EnumInfos; - -class EnumInfoLoader -{ -public: - - static bool LoadEnumInfos(const wxString& MDFileName, EnumInfos& enumInfos); - -private: - static bool LoadEnumList(const wxString& MDFileName, std::vector& enumInfoFiles); - static bool LoadEnums(const std::vector& enumInfoFiles, EnumInfos& enumInfos); -}; \ No newline at end of file diff --git a/util/GenerateEnums/GenerateEnums.rc b/util/GenerateEnums/GenerateEnums.rc deleted file mode 100644 index cd4601f7..00000000 Binary files a/util/GenerateEnums/GenerateEnums.rc and /dev/null differ diff --git a/util/GenerateEnums/GenerateEnums.sln b/util/GenerateEnums/GenerateEnums.sln deleted file mode 100644 index a8a39fb0..00000000 --- a/util/GenerateEnums/GenerateEnums.sln +++ /dev/null @@ -1,31 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio Version 16 -VisualStudioVersion = 16.0.30225.117 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "GenerateEnums", "GenerateEnums.vcxproj", "{32BE4844-29F5-41A7-853A-423A4F4329D7}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|x64 = Debug|x64 - Debug|x86 = Debug|x86 - Release|x64 = Release|x64 - Release|x86 = Release|x86 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Debug|x64.ActiveCfg = Debug|x64 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Debug|x64.Build.0 = Debug|x64 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Debug|x86.ActiveCfg = Debug|Win32 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Debug|x86.Build.0 = Debug|Win32 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Release|x64.ActiveCfg = Release|x64 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Release|x64.Build.0 = Release|x64 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Release|x86.ActiveCfg = Release|Win32 - {32BE4844-29F5-41A7-853A-423A4F4329D7}.Release|x86.Build.0 = Release|Win32 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection - GlobalSection(ExtensibilityGlobals) = postSolution - SolutionGuid = {BBC60045-38E1-4D79-93E5-5248845C667A} - EndGlobalSection -EndGlobal diff --git a/util/GenerateEnums/GenerateEnums.vcxproj b/util/GenerateEnums/GenerateEnums.vcxproj deleted file mode 100644 index 2a0b46db..00000000 --- a/util/GenerateEnums/GenerateEnums.vcxproj +++ /dev/null @@ -1,213 +0,0 @@ - - - - - Debug - Win32 - - - Release - Win32 - - - Debug - x64 - - - Release - x64 - - - - 16.0 - Win32Proj - {32be4844-29f5-41a7-853a-423a4f4329d7} - GenerateEnums - 10.0 - - - - Application - true - v142 - Unicode - - - Application - false - v142 - true - Unicode - - - Application - true - v142 - Unicode - - - Application - false - v142 - true - Unicode - - - - - - - - - - - - - - - - - - - - - true - false - - - false - false - - - true - false - - - false - false - - - - Level4 - true - WIN32;_DEBUG;__WXMSW__;__WXDEBUG__;WXUSINGDLL;_CRT_SECURE_NO_WARNINGS;_SCL_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - $(WXWIN)\include\msvc;$(WXWIN)\include - - - Windows - true - $(WXWIN)\lib\vc_dll - - - - - - - - - $(WXWIN)\include - - - - - - - - Level4 - true - true - true - NDEBUG;__WXMSW__;WXUSINGDLL;_CRT_SECURE_NO_WARNINGS;_SCL_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - $(WXWIN)\include\msvc;$(WXWIN)\include - - - Windows - true - true - true - $(WXWIN)\lib\vc_dll - - - - - - - - - $(WXWIN)\include - - - - - Level4 - true - WIN32;_DEBUG;__WXMSW__;__WXDEBUG__;WXUSINGDLL;_CRT_SECURE_NO_WARNINGS;_SCL_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - $(WXWIN)\include\msvc;$(WXWIN)\include - - - Windows - true - $(WXWIN)\lib\vc_x64_dll - - - - - - - - - $(WXWIN)\include - - - - - - - - Level4 - true - true - true - NDEBUG;__WXMSW__;WXUSINGDLL;_CRT_SECURE_NO_WARNINGS;_SCL_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - $(WXWIN)\include\msvc;$(WXWIN)\include - - - Windows - true - true - true - $(WXWIN)\lib\vc_x64_dll - - - - - - - - - $(WXWIN)\include - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/util/GenerateEnums/GenerateEnums.vcxproj.filters b/util/GenerateEnums/GenerateEnums.vcxproj.filters deleted file mode 100644 index dc2a760f..00000000 --- a/util/GenerateEnums/GenerateEnums.vcxproj.filters +++ /dev/null @@ -1,50 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;c++;def;odl;idl;hpj;bat;asm;asmx - - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms - - - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - - - Resource Files - - - - - Header Files - - - Header Files - - - Header Files - - - Header Files - - - \ No newline at end of file diff --git a/util/GenerateEnums/GenerateEnums.vcxproj.user b/util/GenerateEnums/GenerateEnums.vcxproj.user deleted file mode 100644 index 880f5037..00000000 --- a/util/GenerateEnums/GenerateEnums.vcxproj.user +++ /dev/null @@ -1,19 +0,0 @@ - - - - PATH=$(WXWIN)\lib\vc_x64_dll - WindowsLocalDebugger - - - PATH=$(WXWIN)\lib\vc_x64_dll - WindowsLocalDebugger - - - PATH=$(WXWIN)\lib\vc_dll - WindowsLocalDebugger - - - PATH=$(WXWIN)\lib\vc_dll - WindowsLocalDebugger - - \ No newline at end of file diff --git a/util/GenerateEnums/GenerateEnumsApp.cpp b/util/GenerateEnums/GenerateEnumsApp.cpp deleted file mode 100644 index 804dcb2c..00000000 --- a/util/GenerateEnums/GenerateEnumsApp.cpp +++ /dev/null @@ -1,29 +0,0 @@ -#include -#include - -#include "MainFrame.h" -#include "version.h" - -class GenerateEnumsApp : public wxApp -{ -public: - bool OnInit() override; -}; - -bool GenerateEnumsApp::OnInit() -{ - if ( !wxApp::OnInit() ) - return false; - - SetVendorName(APP_VENDOR_STR); - SetAppName(APP_NAME_STR); - - delete wxConfigBase::Set(new wxConfig(GetAppName(), GetVendorName())); - - MainFrame* frame = new MainFrame(); - frame->Show(); - - return true; -} - -wxIMPLEMENT_APP(GenerateEnumsApp); \ No newline at end of file diff --git a/util/GenerateEnums/MainFrame.cpp b/util/GenerateEnums/MainFrame.cpp deleted file mode 100644 index 3ffc1044..00000000 --- a/util/GenerateEnums/MainFrame.cpp +++ /dev/null @@ -1,184 +0,0 @@ -#include "MainFrame.h" -#include "EnumDeclarationGenerator.h" - -#include "version.h" - -#include -#include -#include -#include -#include - -#include - -MainFrame::MainFrame() - : wxFrame(nullptr, wxID_ANY, "") -{ - SetIcons(wxIconBundle("appIcon", nullptr)); - SetTitle(wxString::Format("%s %s", APP_NAME_STR, APP_VERSION_NUM_DOT_STRING)); - SetMinClientSize(FromDIP(wxSize(800, 600))); - - LoadOptions(); - - wxPanel* mainPanel = new wxPanel(this); - wxBoxSizer* mainPanelSizer = new wxBoxSizer(wxVERTICAL); - wxBoxSizer* buttonsSizer = new wxBoxSizer(wxHORIZONTAL); - wxButton* button = nullptr; - - button = new wxButton(mainPanel, wxID_ANY, "Load Microsoft Excel Enums..."); - buttonsSizer->Add(button, wxSizerFlags().Proportion(1).Expand().Border()); - button->Bind(wxEVT_COMMAND_BUTTON_CLICKED, &MainFrame::OnLoadExcelEnums, this); - - button = new wxButton(mainPanel, wxID_ANY, "Load Microsoft Office Enums..."); - buttonsSizer->Add(button, wxSizerFlags().Proportion(1).Expand().Border()); - button->Bind(wxEVT_COMMAND_BUTTON_CLICKED, &MainFrame::OnLoadOfficeEnums, this); - - m_ctlGenerateBtn = new wxButton(mainPanel, wxID_ANY, "Generate Enum Declarations..."); - buttonsSizer->Add(m_ctlGenerateBtn, wxSizerFlags().Proportion(1).Expand().Border()); - m_ctlGenerateBtn->Bind(wxEVT_COMMAND_BUTTON_CLICKED, &MainFrame::OnGenerateDeclarations, this); - - mainPanelSizer->Add(buttonsSizer, wxSizerFlags().Expand()); - - wxTextCtrl* logCtrl = new wxTextCtrl(mainPanel, wxID_ANY, wxEmptyString, wxDefaultPosition, wxDefaultSize, - wxTE_MULTILINE | wxTE_READONLY | wxTE_RICH2); - wxLog::SetActiveTarget(new wxLogTextCtrl(logCtrl)); - mainPanelSizer->Add(logCtrl, wxSizerFlags().Proportion(1).Expand().Border()); - - mainPanel->SetSizer(mainPanelSizer); - - Bind(wxEVT_UPDATE_UI, &MainFrame::OnUpdateUI, this); -} - -MainFrame::~MainFrame() -{ - SaveOptions(); -} - -void MainFrame::LoadOptions() -{ - const wxConfigBase* config = wxConfigBase::Get(); - wxConfigPathChanger pathChanger(config, "/"); - - m_lastFolderExcel = config->Read("Excel Enums Last Folder"); - m_lastFolderOffice = config->Read("Office Enums Last Folder"); - m_lastFolderGenerated = config->Read("Generated File Last Folder"); -} - -void MainFrame::SaveOptions() -{ - wxConfigBase* config = wxConfigBase::Get(); - wxConfigPathChanger pathChanger(config, "/"); - - config->Write("Excel Enums Last Folder", m_lastFolderExcel); - config->Write("Office Enums Last Folder", m_lastFolderOffice); - config->Write("Generated File Last Folder", m_lastFolderGenerated); -} - -// The file should be in VBA_DOCS_ROOT\api -void MainFrame::OnLoadExcelEnums(wxCommandEvent&) -{ - LoadEnums("Excel", this, "Excel(enumerations).md", m_lastFolderExcel, m_enumsExcel); -} - -// The file should be in VBA_DOCS_ROOT\api\overview\Library-Reference -void MainFrame::OnLoadOfficeEnums(wxCommandEvent&) -{ - LoadEnums("Office", this, "enumerations-office.md", m_lastFolderOffice, m_enumsOffice); -} - -void MainFrame::OnGenerateDeclarations(wxCommandEvent&) -{ - wxCHECK_RET(!m_enumsExcel.empty() && !m_enumsOffice.empty(), "Enums cannot be empty"); - - const wxString fileName = wxFileSelector("Save Enumerations Declarations As", - m_lastFolderGenerated, "Excel and Office Enums", "", - "Text Files (*.txt)|*.txt", - wxFD_SAVE | wxFD_OVERWRITE_PROMPT, - this); - - if ( fileName.empty() ) - return; - - m_lastFolderGenerated = wxFileName(fileName).GetPath(); - - std::vector excelDeclarations; - std::vector officeDeclarations; - wxTextFile textFile; - - if ( wxFileExists(fileName) ) - { - if ( !textFile.Open(fileName) ) - return; - } - else if ( !textFile.Create(fileName) ) - { - return; - } - - wxLogMessage("Generating declarations..."); - if ( !EnumDeclarationGenerator::Generate(m_enumsExcel, m_enumsOffice, - excelDeclarations, officeDeclarations) ) - { - wxLogError("Could not generate enum declarations."); - return; - } - - wxLogMessage("Writing declarations into '%s'...", fileName); - - textFile.Clear(); - - textFile.AddLine("The text below should replace contents of wxAutoExcel_enums.h"); - textFile.AddLine("inside the namespace wxAutoExcel block"); - textFile.AddLine("---8<------------------------------------------------"); - textFile.AddLine(""); - - textFile.AddLine("/*************************************"); - textFile.AddLine(" Microsoft Excel enumerations"); - textFile.AddLine("*************************************/"); - textFile.AddLine(""); - for ( const auto& d : excelDeclarations ) - textFile.AddLine(d); - - textFile.AddLine(""); - textFile.AddLine(""); - textFile.AddLine("/*************************************"); - textFile.AddLine(" Microsoft Office enumerations"); - textFile.AddLine("*************************************/"); - textFile.AddLine(""); - for ( const auto& d : officeDeclarations ) - textFile.AddLine(d); - - textFile.Write(); - - wxLogMessage("Finished writing declarations."); - - if ( wxMessageBox("Do you want to open file with declarations?", "Question", - wxYES_NO, this) == wxYES ) - { - wxLaunchDefaultApplication(fileName); - } -} - -void MainFrame::OnUpdateUI(wxUpdateUIEvent&) -{ - m_ctlGenerateBtn->Enable(!m_enumsExcel.empty() && !m_enumsOffice.empty()); -} - -void MainFrame::LoadEnums(const wxString& enumGroup, wxWindow* parent, - const wxString& defaultFileName, wxString& defaultDir, - EnumInfos& enums) -{ - const wxString fileName = wxFileSelector(wxString::Format("Select File With List of Microsoft %s Enumerations", enumGroup), - defaultDir, defaultFileName, "", - "Markdown Files (*.md)|*.md", - wxFD_OPEN | wxFD_FILE_MUST_EXIST, - parent); - - if ( fileName.empty() ) - return; - - defaultDir = wxFileName(fileName).GetPath(); - - enums.clear(); - EnumInfoLoader::LoadEnumInfos(fileName, enums); -} \ No newline at end of file diff --git a/util/GenerateEnums/MainFrame.h b/util/GenerateEnums/MainFrame.h deleted file mode 100644 index 702eea0c..00000000 --- a/util/GenerateEnums/MainFrame.h +++ /dev/null @@ -1,35 +0,0 @@ -#pragma once - -#include - -#include "EnumInfo.h" - -class MainFrame : public wxFrame -{ -public: - MainFrame(); - ~MainFrame(); - -private: - EnumInfos m_enumsExcel; - EnumInfos m_enumsOffice; - - wxString m_lastFolderExcel; - wxString m_lastFolderOffice; - wxString m_lastFolderGenerated; - - wxButton* m_ctlGenerateBtn; - - void LoadOptions(); - void SaveOptions(); - - void OnLoadExcelEnums(wxCommandEvent&); - void OnLoadOfficeEnums(wxCommandEvent&); - void OnGenerateDeclarations(wxCommandEvent&); - - void OnUpdateUI(wxUpdateUIEvent&); - - static void LoadEnums(const wxString& enumGroup, wxWindow* parent, - const wxString& defaultFileName, wxString& defaultDir, - EnumInfos& enums); -}; diff --git a/util/GenerateEnums/readme.txt b/util/GenerateEnums/readme.txt deleted file mode 100644 index 4dbd1a36..00000000 --- a/util/GenerateEnums/readme.txt +++ /dev/null @@ -1,3 +0,0 @@ -This simple application generates Microsoft Excel and Office enum declarations -for wxAutoExcel, using a local copy of the official VBA documentation in markdown -format cloned from https://github.com/MicrosoftDocs/VBA-Docs \ No newline at end of file diff --git a/util/GenerateEnums/resources/app.ico b/util/GenerateEnums/resources/app.ico deleted file mode 100644 index c87d5803..00000000 Binary files a/util/GenerateEnums/resources/app.ico and /dev/null differ diff --git a/util/GenerateEnums/resources/app.manifest b/util/GenerateEnums/resources/app.manifest deleted file mode 100644 index 191407c0..00000000 --- a/util/GenerateEnums/resources/app.manifest +++ /dev/null @@ -1,35 +0,0 @@ - - - Enum Generator for wxAutoExcel - - - - - - - - - - - - - - - - - - - - - - true - - - \ No newline at end of file diff --git a/util/GenerateEnums/version.h b/util/GenerateEnums/version.h deleted file mode 100644 index c2679958..00000000 --- a/util/GenerateEnums/version.h +++ /dev/null @@ -1,12 +0,0 @@ -#pragma once - -#define APP_MAJOR_VERSION 1 -#define APP_MINOR_VERSION 1 -#define APP_RELEASE_NUMBER 0 -#define APP_SUBRELEASE_NUMBER 0 - -#define APP_VERSION_NUM_DOT_STRING "1.1.0" - - -#define APP_VENDOR_STR "PB " -#define APP_NAME_STR "Generator of enum declarations for wxAutoExcel"