Blog
How to use Application.Hwnd in the xlwings API way
The Application.Hwnd property in Excel’s object model is a read-only property that returns the window handle (a unique integer identifier) of the main Excel application window. In the context of xlwings, a powerful Python library for automating Excel, this property can be accessed to obtain the handle, which is useful for advanced Windows API interactions, such as setting window focus, modifying window styles, or integrating with other GUI automation frameworks. It is particularly valuable when you need to manipulate the Excel window at the operating system level beyond the capabilities of standard xlwings or Excel object model methods.
Syntax in xlwings:
In xlwings, you can access the Hwnd property through the app object, which represents the Excel application. The syntax is straightforward:
hwnd_value = app.api.Hwnd
Here, app is an instance of the xlwings App class (e.g., created via app = xw.App() or xw.apps collection). The .api attribute provides direct access to the underlying Excel object model, allowing you to call the Hwnd property. This property does not take any parameters and returns a Long integer representing the window handle.
Key Points:
- Return Value: The
Hwndproperty returns a unique handle (as an integer) that Windows assigns to the Excel main window. This handle can change if Excel is restarted or if the window is recreated. - Usage Scope: It applies to the main application window, not individual workbook or sheet windows. For workbook-specific window handles, you might need to explore other properties like
Window.Hwndin the Excel object model. - Common Use Cases:
- Window Focus: Use the handle with Windows API functions (via libraries like
pywin32orctypes) to bring the Excel window to the foreground. - GUI Automation: Integrate with tools like
pyautoguiorsikulifor screenshot-based automation by locating the window. - Custom Window Management: Adjust window size, position, or state programmatically through Windows messages.
Example Code in xlwings:
Below is a practical example demonstrating how to retrieve and use the Hwnd property in xlwings. This example includes fetching the handle and using it with the pywin32 library to set the Excel window as the foreground window.
import xlwings as xw
import win32gui # Part of pywin32, install via: pip install pywin32
# Start or connect to an Excel application
app = xw.App(visible=True) # Ensure Excel is visible
wb = app.books.add() # Add a new workbook for demonstration
# Access the Hwnd property via the xlwings api
hwnd = app.api.Hwnd
print(f"Excel main window handle (Hwnd): {hwnd}")
# Use the handle to bring the Excel window to the foreground
# First, check if the window is minimized and restore it if necessary
if win32gui.IsIconic(hwnd):
win32gui.ShowWindow(hwnd, 9) # SW_RESTORE = 9
win32gui.SetForegroundWindow(hwnd) # Bring to front
# Optional: Use the handle to get window title and other info
window_title = win32gui.GetWindowText(hwnd)
print(f"Window title: {window_title}")
# Close the workbook and quit the app (cleanup)
wb.close()
app.quit()
How to use Application.HinstancePtr in the xlwings API way
The Application.HinstancePtr member in Excel’s object model is a property that provides a handle to the instance of the Excel application. In xlwings, this is particularly useful for advanced Windows API interactions or when you need to obtain the window handle (HWND) of the Excel application for integration with other desktop applications or for performing low-level window operations. This property returns a LongPtr value, which is a pointer to the application instance, and it can be accessed to retrieve the window handle for the main Excel window.
Functionality:
The primary function of HinstancePtr is to return the instance handle of the Excel application. This handle is essential for tasks such as:
- Interacting with the Windows API to manipulate Excel windows (e.g., setting focus, resizing, or moving windows programmatically).
- Integrating Excel with other applications that require window handles for communication or automation.
- Debugging or monitoring Excel’s window messages in complex automation scenarios.
Syntax:
In xlwings, you can access the HinstancePtr property through the app object, which represents the Excel application. The syntax is straightforward, as it is a read-only property. The call format is:
instance_handle = app.api.HinstancePtr
This returns a Long integer representing the instance handle. Note that app is an xlwings App object, and .api is used to access the underlying Excel object model. There are no parameters for this property, as it simply retrieves the handle.
Example:
Here is a practical example of using HinstancePtr in xlwings to obtain the Excel application’s instance handle and then use it with the Windows API via the ctypes library to perform a basic window operation, such as getting the window text. This example assumes you are running on Windows and have the necessary permissions.
import xlwings as xw
import ctypes
from ctypes import wintypes
# Connect to the active Excel application
app = xw.apps.active
# Get the instance handle using HinstancePtr
instance_handle = app.api.HinstancePtr
print(f"Excel instance handle (HinstancePtr): {instance_handle}")
# To get the main window handle (HWND), you typically use the Windows API
# First, define the FindWindowW function from user32.dll
user32 = ctypes.WinDLL('user32', use_last_error=True)
FindWindowW = user32.FindWindowW
FindWindowW.argtypes = [wintypes.LPCWSTR, wintypes.LPCWSTR]
FindWindowW.restype = wintypes.HWND
# Use the instance handle to find the Excel window (class name is "XLMAIN")
# Note: HinstancePtr is not directly the HWND, but you can use it in context
# Here, we find the window by its class name, which is common for Excel
excel_hwnd = FindWindowW("XLMAIN", None)
if excel_hwnd:
print(f"Excel main window handle (HWND): {excel_hwnd}")
# Example: Get the window text length
GetWindowTextLengthW = user32.GetWindowTextLengthW
GetWindowTextLengthW.argtypes = [wintypes.HWND]
GetWindowTextLengthW.restype = ctypes.c_int
text_length = GetWindowTextLengthW(excel_hwnd)
print(f"Length of Excel window title: {text_length}")
else:
print("Excel window not found.")
How to use Application.Hinstance in the xlwings API way
The Application.Hinstance property in Excel’s object model provides access to the instance handle (hWnd) of the main Excel application window. This is a read-only property that returns a Long value representing the Windows handle. In xlwings, this property is particularly useful for advanced Windows API interactions, such as manipulating the Excel window (e.g., minimizing, maximizing, or setting focus) or integrating with other applications that require window handles. It allows for low-level control over the Excel application instance from Python, enabling tasks that go beyond standard spreadsheet operations.
Functionality:
The primary function of Application.Hinstance is to retrieve the window handle of the Excel application. This handle can be used in conjunction with the Windows API (via libraries like pywin32 or ctypes) to perform operations such as:
- Changing the window state (e.g., minimizing or restoring the window).
- Bringing the Excel window to the foreground.
- Interacting with other windows in the system.
- Monitoring application events at the OS level.
In xlwings, accessing this property allows Python scripts to interact directly with the Excel application’s window, facilitating integration in automated workflows where GUI manipulation is required.
Syntax:
In xlwings, the Application.Hinstance property is accessed through the App object. The syntax is straightforward, as it is a property without parameters:
app_instance_handle = app.hinstance
Here, app is an instance of the xlwings App class, representing the Excel application. The hinstance property returns an integer representing the window handle.
Parameters:
This property does not accept any parameters. It is a read-only attribute that provides the handle value directly.
Example Usage:
Below is a code example demonstrating how to use the Application.Hinstance property in xlwings to retrieve the window handle and perform a basic operation—minimizing the Excel window using the Windows API via ctypes. This example assumes you have xlwings installed and Excel running.
import xlwings as xw
import ctypes
# Connect to the active Excel application
app = xw.apps.active
# Get the instance handle (hWnd) of the Excel application
excel_handle = app.hinstance
print(f"Excel application window handle: {excel_handle}")
# Use ctypes to call the Windows API for minimizing the window
# The ShowWindow function is part of the user32.dll
user32 = ctypes.windll.user32
# Constants for window commands (SW_MINIMIZE = 6)
SW_MINIMIZE = 6
# Minimize the Excel window using its handle
result = user32.ShowWindow(excel_handle, SW_MINIMIZE)
if result:
print("Excel window minimized successfully.")
else:
print("Failed to minimize the window.")
# Note: This is a simple example; in practice, you might need error handling
# and checks for window state. The handle can be used for other operations,
# such as restoring or maximizing the window, by changing the command constant.
How to use Application.HighQualityModeForGraphics in the xlwings API way
The Application.HighQualityModeForGraphics property in Excel, when accessed through the xlwings library, provides control over a performance optimization setting specifically for graphics rendering. This feature is particularly relevant when dealing with workbooks that contain a large number of charts, shapes, or other graphic elements. Enabling high-quality mode can improve the visual fidelity of graphics during screen updates and printing, but it may come at the cost of increased memory usage and potentially slower performance, especially on complex documents. The property allows developers to programmatically balance visual quality against application responsiveness based on the specific needs of their automation script or add-in.
Syntax and Parameters
In xlwings, you interact with this property through the Application object. The property is a read/write Boolean.
# Getting the current setting
current_setting = xw.apps[0].api.HighQualityModeForGraphics
# Setting a new value
xw.apps[0].api.HighQualityModeForGraphics = True # or False
- Member Access: The property is accessed via the
.apiattribute of the xw.apps object. This.apigateway provides direct access to the underlying Excel object model, allowing you to use the native property names as defined in the VBA documentation. - Property Type: Boolean (
bool). - Values:
True: Enables high-quality mode for graphics. Excel uses more memory to cache graphic elements, aiming for better rendering quality.False(Default): Disables high-quality mode, favoring performance and lower memory consumption. Graphics might be rendered with lower detail during rapid screen changes.
Code Examples
Here are practical examples demonstrating how to use this property with xlwings:
- Checking the Current Status:
This is useful for diagnostics or for conditionally adjusting other settings.
import xlwings as xw
# Connect to the active instance of Excel
app = xw.apps.active
# Get the current HighQualityModeForGraphics setting
hq_setting = app.api.HighQualityModeForGraphics
print(f"High Quality Mode for Graphics is currently: {hq_setting}")
- Enabling High-Quality Mode for a Printing Routine:
Temporarily enable high-quality graphics before a print job to ensure the best output, then restore the original setting.
import xlwings as xw
app = xw.apps.active
wb = app.books.active
# Store the original setting
original_setting = app.api.HighQualityModeForGraphics
try:
# Enable high-quality mode for printing
app.api.HighQualityModeForGraphics = True
print("High-quality mode enabled for printing.")
# Perform the print action (e.g., print the active sheet)
wb.api.ActiveSheet.PrintOut()
finally:
# Restore the original setting reliably, even if an error occurs during printing
app.api.HighQualityModeForGraphics = original_setting
print(f"High-quality mode restored to: {original_setting}")
- Optimizing Performance for a Data Processing Macro:
If your script is primarily manipulating data and doesn’t require perfect graphic rendering during the process, disabling this mode can improve speed.
import xlwings as xw
app = xw.apps.active
original_setting = app.api.HighQualityModeForGraphics
# Disable high-quality mode for faster processing
app.api.HighQualityModeForGraphics = False
# ... Perform intensive data operations, chart updates, or shape manipulations ...
# Restore the setting after operations are complete
app.api.HighQualityModeForGraphics = original_setting
How to use Application.Height in the xlwings API way
The Height property of the Application object in Excel refers to the height, in points, of the main application window. This property is part of the window management capabilities, allowing developers to programmatically control the size and position of the Excel window. In xlwings, this property is accessible through the api property, which provides direct access to the underlying Excel object model. By manipulating the Height property, you can adjust the window’s vertical dimension to fit specific user interface requirements or to optimize the display for different screen resolutions.
Syntax in xlwings:app.api.Height
Here, app represents the xlwings App object, which corresponds to the Excel application instance. The Height property is a read/write property of type Single (a floating-point number). When setting the height, the value is specified in points, where one point equals 1/72 of an inch. The minimum and maximum allowable values depend on the screen resolution and system settings, but typically, the height can range from a small window size to the full screen height. To retrieve the current height, you can read this property; to change it, assign a new numeric value.
Example Usage:
Below are practical xlwings API code examples that demonstrate how to get and set the Height property of the Excel application window.
- Getting the Current Height:
This example retrieves the current height of the Excel window and prints it to the console. It is useful for logging or conditional resizing based on the existing window size.
import xlwings as xw
app = xw.apps.active # Get the active Excel application
current_height = app.api.Height # Read the Height property
print(f"The current Excel window height is {current_height} points.")
- Setting a Specific Height:
Here, the height of the Excel window is set to 600 points. This can be used to standardize the window size across different user sessions or to create a tailored viewing area.
import xlwings as xw
app = xw.apps.active
app.api.Height = 600 # Set the Height property to 600 points
print("Excel window height has been set to 600 points.")
- Dynamic Resizing Based on Screen Resolution:
This advanced example calculates a percentage of the screen’s working area height (using thepyautoguilibrary for screen info) and sets the Excel window accordingly. It ensures the window adapts to different monitor setups.
import xlwings as xw
import pyautogui
app = xw.apps.active
screen_width, screen_height = pyautogui.size() # Get screen dimensions
new_height = screen_height * 0.75 # Set to 75% of screen height
app.api.Height = new_height
print(f"Excel window height adjusted to {new_height:.0f} points (75% of screen height).")
- Restoring Window to a Default Size:
In this scenario, the height is reset to a default value (e.g., 500 points) as part of a cleanup or initialization routine, ensuring consistency in the user interface.
import xlwings as xw
app = xw.apps.active
default_height = 500
app.api.Height = default_height
print(f"Excel window height restored to {default_height} points.")
How to use Application.GenerateTableRefs in the xlwings API way
The GenerateTableRefs member of the Application object in Excel is a method used to convert structured references from Excel tables into standard cell references (A1-style notation). This is particularly useful when you need to translate the user-friendly table column names, such as TableName[ColumnName], into the explicit range addresses that xlwings or other programming interfaces can directly manipulate. It simplifies dynamic range handling in macros or scripts when working with Excel Table objects.
Syntax in xlwings:
app.api.GenerateTableRefs(TableRef, UseTableNames, RefStyle)
- TableRef: A required string argument that specifies the structured reference you want to convert. This can be a single table reference like
"Sales[Amount]"or multiple references separated by commas. - UseTableNames: An optional Boolean argument. If set to
True, the method returns references using table names (e.g.,TableName[ColumnName]). IfFalseor omitted, it converts to standard cell references (e.g.,$A$1:$A$10). The default isFalse. - RefStyle: An optional constant from the
XlReferenceStyleenumeration, which determines the reference style. The two primary values are: xlwings.constants.xlA1: Returns references in A1-style (default).xlwings.constants.xlR1C1: Returns references in R1C1-style.
Example:
Suppose you have an Excel workbook with a table named SalesData spanning columns A through C, and you want to convert the structured reference for the Revenue column into a standard range. Using xlwings, you can achieve this as follows:
import xlwings as xw
# Connect to the active Excel instance or open a workbook
app = xw.apps.active # or xw.App() for a new instance
wb = app.books['YourWorkbook.xlsx'] # Replace with your workbook name
ws = wb.sheets['Sheet1']
# Convert the table reference to A1-style cell references
table_ref = "SalesData[Revenue]"
converted_ref = app.api.GenerateTableRefs(TableRef=table_ref, UseTableNames=False, RefStyle=xw.constants.xlA1)
print(f"Converted reference: {converted_ref}") # Output might be something like "$C$2:$C$100"
# You can then use this reference in xlwings for operations, e.g., to get the range:
if converted_ref:
revenue_range = ws.range(converted_ref)
values = revenue_range.value # Retrieve values from the range
print(f"Revenue values: {values}")
How to use Application.GenerateGetPivotData in the xlwings API way
The Application.GenerateGetPivotData member in Excel is a powerful feature for programmatically retrieving specific data points from PivotTables. In the context of xlwings, which provides a clean Python interface to the Excel Object Model, this functionality allows for precise, dynamic data extraction based on PivotTable field items, rather than relying on static cell references. This is essential for building robust reporting tools and dashboards where underlying PivotTable layouts might change.
Functionality
The primary purpose of GenerateGetPivotData is to construct a GETPIVOTDATA formula string. This formula is the engine behind Excel’s ability to fetch data from a PivotTable by specifying one or more field/item pairs. For instance, instead of linking to cell $F$10, you can create a formula that means “get the sum of Sales for the Region ‘West’ and the Product ‘Widgets'”. This formula remains accurate even if the PivotTable is refreshed, sorted, or its layout is modified. Using xlwings, you can generate this formula string from your Python code and insert it into a cell, or use it to perform calculations directly.
Syntax in xlwings
The xlwings API mirrors the VBA object model. The method is accessed through the Application object of the main App instance. The typical call pattern is:
formula_string = xw.apps[0].api.GenerateGetPivotData(Data, PivotTable, Field1, Item1, Field2, Item2, ...)
- Data (Optional): A string specifying the data field name (e.g., “Sum of Sales”). If omitted, the PivotTable’s first data field is used.
- PivotTable (Required): A
Rangeobject representing any single cell within the target PivotTable. - Field1, Item1, … (Optional): Pairs of strings defining the criteria.
Field1is the name of a PivotTable field (e.g., “Region”), andItem1is the name of a specific item within that field (e.g., “West”). You can provide multiple field/item pairs to narrow down the data point.
Important Note on Parameters: The parameter list is variable-length. In VBA, you can use Array("Region", "West", "Product", "Widgets"). In xlwings, you typically pass these as separate arguments. If you have a dynamic list of criteria, you might need to construct the call using *args unpacking.
Code Example
The following xlwings script demonstrates how to generate a GETPIVOTDATA formula and place it in a cell. It assumes an active Excel instance with a PivotTable where one cell (e.g., A5) is inside it.
import xlwings as xw
# Connect to the active Excel instance
app = xw.apps.active
# Define the target cell within the PivotTable (e.g., cell A5)
pivot_table_cell = app.api.ActiveSheet.Range("A5")
# Generate the GETPIVOTDATA formula string.
# This example gets data for "Sum of Revenue" where Region is "North" and Product is "Gadget".
formula = app.api.GenerateGetPivotData(
"Sum of Revenue", # Data field
pivot_table_cell, # PivotTable location
"Region", "North", # First field/item pair
"Product", "Gadget" # Second field/item pair
)
# Write the generated formula to cell H1 on the active sheet
app.api.ActiveSheet.Range("H1").Formula = "=" + formula
# Alternatively, you can use xlwings' more Pythonic syntax for the final step
sheet = xw.sheets.active
sheet["H1"].formula = f"={formula}"
print(f"Formula inserted: {sheet['H1'].formula}")
How to use Application.FormulaBarHeight in the xlwings API way
The Application.FormulaBarHeight member in Excel’s object model is a property that allows developers to get or set the height of the formula bar in the Excel application window. This can be particularly useful for customizing the user interface to improve readability or accommodate specific workflow needs, such as when working with long formulas that require more vertical space. In xlwings, this property is accessed through the Application object, enabling Python scripts to programmatically adjust the formula bar’s appearance.
Syntax in xlwings:
In xlwings, the Application object is typically accessed via the app property of a workbook or by directly instantiating an application instance. The FormulaBarHeight property is used as follows:
- To get the current height:
app.api.FormulaBarHeight - To set a new height:
app.api.FormulaBarHeight = value
Here,apprepresents the xlwingsAppinstance connected to Excel, andapiprovides direct access to the underlying Excel object model. Thevalueparameter is an integer that specifies the height in points (a unit of measurement in Excel, where 1 point is approximately 1/72 inch). The height can range from a minimum value (typically 1 row) up to a maximum that depends on the Excel version and window size, but it is generally limited to avoid obscuring the worksheet area. If an invalid value is set, Excel may automatically adjust it to the nearest valid height.
Example Usage:
Below are xlwings code snippets demonstrating how to use the FormulaBarHeight property in practice. These examples assume you have an existing Excel instance or workbook opened via xlwings.
- Retrieving the Current Formula Bar Height:
This example connects to an active Excel instance and prints the current height of the formula bar.
import xlwings as xw
# Connect to the active Excel application
app = xw.apps.active
# Get the current formula bar height
current_height = app.api.FormulaBarHeight
print(f"Current formula bar height: {current_height} points")
- Setting a New Formula Bar Height:
This example opens a specific workbook and increases the formula bar height to 50 points for better visibility of lengthy formulas.
import xlwings as xw
# Start or connect to Excel and open a workbook
app = xw.App(visible=True)
workbook = app.books.open('example.xlsx')
# Set the formula bar height to 50 points
app.api.FormulaBarHeight = 50
# Save and close the workbook
workbook.save()
workbook.close()
app.quit()
- Dynamic Adjustment Based on Content:
In this scenario, the script checks if the active cell contains a formula with more than 100 characters and adjusts the formula bar height accordingly to prevent clipping.
import xlwings as xw
app = xw.apps.active
sheet = app.books.active.sheets.active
# Check the active cell for a long formula
active_cell = sheet.range('A1')
if active_cell.formula and len(active_cell.formula) > 100:
app.api.FormulaBarHeight = 60 # Increase height for long formulas
else:
app.api.FormulaBarHeight = 20 # Reset to a default height
How to use Application.FlashFillMode in the xlwings API way
The Application.FlashFillMode property in Excel, when accessed through the xlwings API, provides a powerful way to interact with Excel’s Flash Fill feature programmatically. Flash Fill is an intelligent data transformation tool that automatically fills in data when it detects a pattern in your actions, such as splitting full names into first and last names or formatting dates. The FlashFillMode property allows a developer to check whether Flash Fill is currently active and running, enabling the automation of workflows that depend on this feature’s state.
Functionality
This read-only property returns a Boolean value indicating the current operational status of the Flash Fill feature. It is primarily used for monitoring. When True, it signifies that Flash Fill is actively processing or suggesting a fill pattern based on user input in the worksheet. When False, Flash Fill is not currently engaged. This is useful in automation scripts where subsequent actions should only proceed after Flash Fill has completed its automatic data entry, ensuring data integrity.
Syntax and Parameters
In xlwings, the property is accessed through the Application object. The syntax is straightforward as it does not accept parameters:
app.flash_fill_mode
- Return Value: A Boolean (
bool). True: Flash Fill is active.False: Flash Fill is not active.
Code Examples
The primary use case is to wait for Flash Fill to finish before executing further code, which is crucial for automation reliability.
- Basic Check:
This example simply prints the current status of Flash Fill.
import xlwings as xw
app = xw.apps.active # Get the active Excel application
is_flash_fill_active = app.flash_fill_mode
print(f"Is Flash Fill currently active? {is_flash_fill_active}")
- Automation with Status Monitoring:
A more practical example simulates a scenario where data is entered, triggering Flash Fill, and the script waits for it to complete before saving.
import xlwings as xw
import time
# Connect to Excel and a specific workbook
app = xw.apps.active
wb = app.books['EmployeeData.xlsx']
sheet = wb.sheets['Sheet1']
# Simulate an action that triggers Flash Fill (e.g., entering a pattern)
# Let's assume column A has "John Doe", and we type "John" in B1.
sheet.range('B1').value = 'John'
# In the Excel UI, Flash Fill might now suggest filling down the first names.
# Monitor the FlashFillMode property until it becomes False
print("Waiting for Flash Fill to complete...")
while app.flash_fill_mode:
time.sleep(0.1) # Short pause to prevent excessive CPU usage
print("Flash Fill has finished. Proceeding to save the workbook.")
wb.save()
# Optional: Retrieve the data filled by Flash Fill
filled_data = sheet.range('B1:B10').value
print(filled_data)
How to use Application.FlashFill in the xlwings API way
The FlashFill member of the Application object in Excel is a powerful feature for automatically filling in data based on patterns it detects in your input. This functionality is particularly useful for cleaning and formatting data, such as splitting full names into first and last names, extracting numbers from text, or standardizing date formats. In xlwings, you can access this feature through the api property, which provides direct access to the underlying Excel object model. The FlashFill operation is typically applied to a range of cells, where Excel analyzes the examples provided in adjacent columns and fills the target range accordingly.
The syntax for using FlashFill in xlwings involves calling the FlashFill method on a Range object. Specifically, you first reference the target range where you want the filled data to appear, and then invoke the method. The method does not take any parameters directly in its basic form, as it relies on the adjacent source data for pattern recognition. However, it is often used in conjunction with other operations to ensure correct data alignment. In xlwings, the call is made through the Excel API, so the format is: range.api.FlashFill(). Here, range represents the xlwings Range object that corresponds to the target cells in Excel. It is important to note that FlashFill requires at least one example in the source column adjacent to the target range for pattern detection. If no clear pattern is found, Excel may not fill the data as expected, so users should verify the results.
For example, suppose you have a list of full names in column A of an Excel worksheet, such as “John Doe” and “Jane Smith”, and you want to extract the first names into column B. Using xlwings, you can write a script to apply FlashFill. First, you would manually enter the first example in cell B1 (e.g., “John” for “John Doe”) to provide a pattern. Then, in your Python code, you can use xlwings to trigger FlashFill on the range in column B where you want the first names to appear. Below is a code instance that demonstrates this:
import xlwings as xw
# Connect to the active Excel workbook
wb = xw.books.active
ws = wb.sheets['Sheet1']
# Define the target range for first names (e.g., B1:B10)
target_range = ws.range('B1:B10')
# Apply FlashFill to automatically fill based on adjacent data in column A
target_range.api.FlashFill()
# Save the workbook if needed
wb.save()