I use VSTO Excel template based solutions frequently. One of the things I like about this project type is that I can use cached data sets in the Excel template or worksheet to handle application state that persists after the user saves the file. However, cached data sets create a problem: the schema of the document is bound to the application version.
This hasn't been a big problem, but I've realized it would be a good idea to create a mechanism that will read the version of the Excel document when it opens in order to detect and handle version incompatibilities. For example, if my 2.1 plugin opens a 1.5 document, the schema of the cached data will not match what is expected.
Is there a standard or recommended way to version stamp the Excel template or worksheet? If not, does anyone have suggestions on how to do this?
I usually use the Worksheet.CustomProperties to persist information like this into my worksheet. Any information you put into the CustomProperties collection gets saved along with the worksheet and is loaded back along with the worksheet information when you reload the worksheet.
Workbooks also support custom properties, but I think in your case Worksheet.CustomProperties is the way to go.
I don't know any standard, but you can consider:
The use of a custom document property accessible by Microsoft.Office.Core.DocumentProperties (How to: Read from and Write to Document Properties);
A protected cell in the worksheet
itself;
With the first approach the user could manually change this property or delete it. However the second approach you would have protected cells in the worksheet which, if I recall correctly, will introduce some problems if you want to sort any data in that worksheet.
I had a similar issue (how to determine the Excel version from within VSTO code). I found your question while search for a solution. What worked for me was the Version property of the Excel Application object. From within a worksheet:
Me.Application.Version
or maybe, depending on where you're at
Globals.ThisWorkbook.Application.Version
Anyway, the value is "11.0" for Excel 2003 and "12.0" for 2007.
However, on re-reading your issue, you need to know the version that created a workbook. You might try Workbook.CalculationVersion, which "Gets a number that indicates the version of Excel that the workbook was last fully recalculated by. The rightmost four digits are the minor calculation engine version number, and the other digits (on the left) are the major version of Microsoft Office Excel." as per http://msdn.microsoft.com/en-us/library/microsoft.office.tools.excel.workbook.calculationversion.aspx
Related
I recently created an automated Excel utility (using Microsoft Office 2019), in which I've extensively used data validations, VBA code, named ranges and formatting. It was working well until one day I received an Excel prompt message that read:
When I click on Yes, it gives me another pop-up where it says it recovered the file, and also gives me a link to the error log XML file. I click on it and open the .xml file using my default browser, and it shows the following details:
Looks like it is removing data validations from a particular sheet, and I realize that is true when I navigate to that sheet in the UI. To work around this unwarranted and repeated data-validation removal that Excel application is enforcing, I created a macro code that will re-instate all these data validations as required. The real problem arises when this Excel file is opened on a different computer with Microsoft Office 365. Looks like it is removing not just data-validations but also other components like named ranges and buttons. There could be other things that it might be removing, which I am unaware of at the moment. So the macro created to re-instate the data-validations is no longer useful.
Why does this problem arise? And why is different version of Excel behaving differently? How do I solve this? Appreciate your kind help. Thank you!
As rightly suggested by Ron Rosenfeld and e_conomics, the issue was with the data validation lists, whose sources were strings of comma separated values that were going beyond 255 characters. Apparently, that is a limitation with Excel.
When I replaced the sources of data validation lists (string of comma separated values) with the ranges containing the corresponding values, the problem resolved itself. The repair dialogue never appeared again.
I have an Excel sheet which is used for bug-tracking. Each client has their own .xlsx and each application for that client has its own sheet within the .xlsx. So multiple Excel files with multiple sheets, all in the same format.
All sheets have the same headings and some columns have data validation and conditional formatting. Occasionally, however, the layout/headings or values allowed in data-validated cells, etc. must change and I have to go through each sheet and manually make the changes.
Is it possible to have a master sheet from which other sheets will inherit headings and heading styles with all cells under particular headings having data validation and conditional formatting?
(Before this is suggested, I used to simply put everything in one sheet and use filters to show a particular client/application, but this became impractical when sharing and versioning the sheets with multiple people)
The term you are looking for is a template. You create the template and give that to your 'clients' to track bugs. If you make an update to the template and give it to the client, they can just copy/paste data into the new form.
In my opinion, you're going about this the wrong way. Excel is a spreadsheet programme, while it CAN be used as a 'list' of sorts, it is a poor choice for bug tracking. If you're stuck on Office applications, use an Access database or something that can actually give you a 'front end display' separate from the 'back end data'. There are many free bug tracking software programmes on the internet. Set one of them up and just have your clients log a bug there.
Using a template and then getting the clients to copy+paste the old data is one way, but its not exactly the safest method.
If you did want to distribute a new template to your users it would be a good idea to add some import functionality. So VBA handles copying the old data across.
If you (personally) could do the changes to the template manually, then you might also be able to create a workbook+macros to "patch" the source (or a copy of the source) data in-place.
With either approach you'd probably need to add something to the source workbook to keep track of what version they have and make sure they they import from and to the correct version to prevent unhappiness in the future.
Could you show an example of a change? before and after etc
As far as I understand cells with formulas in Microsoft Office Excel can contain calculated values when serialized and saved in Office Open XML formats (specifically SpreadsheetML). This most likely applies to other types of dependencies and functions of values from other cells (like charts, pivot tables, etc.). I most likely do something wrong, but when processing this XML documents (SpreadsheetML) by external tools, that do not use any .Net components or similar APIs provided by MS, but just directly manipulating XML, I get into a problem that when I modify some content of one of worksheets Excel will still use last generated values in cells containing formulas. So when user opens generated spreadsheet he sees modified data but all the calculated fields are outdated. Now the only thing that I could find (these days) on internet was this:
http://openxmldeveloper.org/discussions/formats/f/14/p/1561/4164.aspx
This is really not a preferable solution especially if it applies to any kind of calculated cells and objects (charts, etc.) as it means partially reimplementing some SpreadsheetML processor when you do not know exactly the structure of all worksheets.
I would hope there would certainly be either an option in Excel or a configuration in one of the SpreadsheetML parts to force recalculations or to mark cells dirty, but I couldn't find one yet.
There is an assumption that scripting would help, but my lack of knowledge of that area didn't brought me to any successful results yet as I'm not sure how to include scripts into SpreadsheetML worksheet. Though I found quite some examples how to trigger recalculation and how to add open event listeners.
The easiest way is to remove the calculated value from the cell (as also noted in the link you provided).
You do not have to know the exact structure of worksheets. Just remove all occurrences of <v>#VALUE!</v> in worksheets/sheet1.xml (so that other functions will not be affected).
press F9 to recalculate all open workbooks
Excel Recalculation
Perhaps your Calculation Mode for the workbook is getting set to manual. Force this mode to Automatic when you open the workbook by setting it to null in the code with the following:
public void SetAutomaticCalculationMode(WorkbookPart workbookPart1)
{
Workbook workbook1 = workbookPart1.Workbook;
CalculationProperties calculationProperties1=workbook1.GetFirstChild<CalculationProperties>();
calculationProperties1.CalculationMode = null;
}
This will correspond to Automatic calculation mode as seen in the Options of Excel 2007 client:
I want from VBA to start/stop "Track changes" functionality in Excel.
Searching thru the Net I saw a property called TrackRevisions of ActiveDocument object. Supposedly in MS Word writing ActiveDocument.TrackRevisions = True should turn on "Track changes".
But in MS Excel this line gives 424 Object required run-time error. Same error is returned when trying with ThisWorkbook. Changing it to ActiveSheet brings 438 Object doesn't support this property or method error.
For a shared workbook you can use VBA from these links (the method is ActiveWorkbook.HighlightChangesOptions)
HighlightChangesOptions Method Excel 2003 VBA Language Reference
Workbook.HighlightChangesOptions Method
Office 2007
Workbook.HighlightChangesOptions Method (Excel)
Office 2010
This doesn't offer the same depth of tracking as available in Word, for example from the first link in my post,in Excel:
Change tracking differs from undo and backup
Some types of changes are not tracked Changes that you make to cell contents are tracked, but other changes, such as formatting changes, are not tracked.
Change history is kept only for a specific interval
Change history is periodically deleted
If that isn't what you were chasing you may be able to employ specific VBA to track
certain cells, or
compare versions
But if that is the case we will need more information from you as to what you are chasing.
You can use the following code. You will see this code when you record a macro.
With ActiveWorkbook
.HighlightChangesOptions When:=xlAllChanges
.ListChangesOnNewSheet = False
.HighlightChangesOnScreen = True
End With
The questions is really what do you want to achieve. If you want to track changes in a spreadsheet, I assume you have some other users editing the workbook, and you want to record who changed what, as well as review/approve any modifications later on. Well, you don't actually need a triggering macros for that.
... instead of Track Changes, try comparing two workbooks using the Microsoft's Spreadsheet compare (application is limited to Excel 2013, Excel 2016 , Office 365 Professional).
... instead of Track Changes, you can record history of changes made to the workbook (who changed what and when) - XLTools Version Control.
I use both depending on the task.
We've created an API in IronPython that wraps most of the COM functionality w/r/t Excel (and Powerpoint). One of the things we have not yet implemented is the option to change the order of worksheets within a workbook once they've been created. The workflow is basically, create an Excel workbook, then add a bunch of sheets. They become out of order because we loop over similar data segments in the same loop (obviously). So, after all the worksheets are created, how can I modify the order of the sheets?
if you can even point me in the direction of an MSDN page that shows how to do this in .NET I'd appreciate it.
this also helped a great deal:
http://www.cpearson.com/excel/sortws.aspx
Did you try the Worksheets.Move method?
http://msdn.microsoft.com/en-us/library/microsoft.office.tools.excel.worksheet.move%28v=vs.80%29.aspx
Looks like exactly what you need