Archive for September 2007

MRU(”Most Recently Used”) file list in Excel 2007

Hi all

There is no built-in option to disable the MRU(”Most Recently Used”) file list in the Office button menu.
A few weeks ago Excel guru Jim Rech send me a test file to disable the MRU list in Excel 2007.
After a few test versions I upload the last version from Jim to my site.

Try this example file with XML to create a new tab on the ribbon and hide/disable a few controls
and the VBA code from Jim Rech to disable/hide the MRU list.

Part from the comments in the code from Jim:
Because there is apparently no way to disable the MRU list on the Office Menu directly
we clear it by setting Application.RecentFiles.Maximum to 0. Since this action clears
the MRU list in the registry we first backup its contents to the registry as well
as number of files the user is showing in it. We use the registry in case VB variables are cleared.

Download the example file from my site in the “Ribbon Tips section”
http://www.rondebruin.nl/ribbon.htm

Or the direct link
http://www.rondebruin.nl/files/Dictator-MRU-ListJR.zip

Please give feedback if you have problems with the code or suggestions.

Tip: check out also the new Add-in from Jim Rech to find the names of all Office 2007 button images
on my site, see point 4.

Ron de Bruin and Jim Rech
http://www.rondebruin.nl/tips.htm

2007 Calculation Bug

Via Slashdot:

It seems that any formula that should evaluate to 65,535 will act strangely.

Slashdot article references this newsgroup post.

Office Football Pool

Chris York comments:

trying to put together a football pool, 100 squares, 10 rows x 10 rows. Cant find the format to fit this idea

Here’s one version I’ve seen.

Here’s how it works:

1. Type the Home and Visitor team names in P1 and P2.
2. Hide the numbers using the option button to the right.
3. Print the worksheet.
4. Go collect 100 initials, one per box.
5. Type the initials in the boxes.
6. Show the numbers using the option button.
7. Print the final worksheet.

The numbers will change every time the worksheet calculates, and that includes when you show/hide the numbers. So be careful that you only show the numbers right before you’re ready to print. The final printed form will have the correct numbers, but the worksheet will not have those numbers if you do anything else that causes a recalc.

Not familiar with this type of pool? Take the sheet you printed in Step 3 around your office and sell each of the 100 squares. When a person buys a square (or squares), he writes his initials in the purchased squares. When all 100 squares are sold, the numbers are inserted in the top row and down the side. At the end of every quarter of the game, you find the winning square based on the last digit of each teams score. If, at the end of the first quarter, Nebraska is beating Iowa State by a score of 19 to 15, the person whose initials are in the top left square would be the winner for that quarter and get 25% of the pot. Do the same for the remaining three quarters.

Of course you should never do this where it is prohibited by law.

Download FootballSquares.zip

Update: Chip added some macros to lock in the numbers and report the winners. You can download FootballSquares20.zip for the macro version. Thanks Chip.

Performance Monitor

Professional Excel Development

Professional Excel Development has a chapter on optimization that discusses the PerfMon utility (available on the companion CD). I used it for the first time on a 40 second process and I thought I would share the results. Thrilling, I know.

One hundred fifty thousand calls to class properties? Yikes! Noting that FillFinals was the biggest culprit, I manually added some perfmon calls inside that procedure to see what I could see.

Inserting the final reports consists of adding sheets to the final report workbooks, among other things. In this case it adds nine sheets to six different workbooks. I decided to break up that block of code even further. Specifically, I wanted to isolate the Sheets.Add line.

I guess adding sheets takes a lot of time. Maybe I should create a report with some ‘final reports’ already in it so I can limit the amount of sheets that I have to add. Of course I’ll have to delete extraneous sheets, so I’ll have to weigh the costs of that. Well, nothing earth shattering here. It was just the first time I used it on a real program and it was fun.

A couple of bugs I noted in the utility:
It puts PerfMonProcEnd statements before any Exit Sub statements, but when it deletes them it doesn’t respect my original tabbing.
My manual lines looked like PerfMonProcEnd “FireAssay.MProcess.FillFinals.HeaderData”. I don’t think I was supposed to put a period after FillFinals (the procedure name) because the output file added another column. That’s OK, but it didn’t adjust the headers. In the screen shots above, I manually adjusted the headers and added a Section header. It’s probably user error rather than a bug.

Preventing Event Conflicts

I have two custom add-ins loaded that use application-level events. I only want those events to run when a workbook associated with my application is active. Otherwise, the events in my purchase order application will try and do stuff to my invoices and vice versa. Not good.

For every application, the first thing I do is test to make sure I'm dealing with an appropriate object; be it a sheet, workbook, or whatever. I use two utilities to do the testing. The first utility verifies an open workbook and the second verifies a closed one.

As described in Custom Document Properties, I use custom document properties in my templates to identify the workbook as being part of the application. The utilities check the property and return True if it's there.

Function IsOpenInvoice(ByRef Wb As Workbook, _
    Optional ByVal sProperty As String = gsCDPINVAPP) As Boolean
   
    Dim bTemp As Boolean
   
    On Error Resume Next
        bTemp = Wb.CustomDocumentProperties(sProperty).Value
    On Error GoTo 0
   
    IsOpenInvoice = bTemp
   
End Function
 
Function IsInvoice(ByVal sName As String, _
    Optional ByVal sProperty As String = gsCDPINVAPP) As Boolean
       
    With Application.FileSearch
        .NewSearch
        .FileType = msoFileTypeAllFiles
        .Filename = Dir(sName)
        If Not sName = Dir(sName) Then
            .LookIn = Replace(sName, Dir(sName), "")
        End If
        .PropertyTests.Add sProperty, msoConditionIsYes
       
        .Execute
       
        IsInvoice = .FoundFiles.Count> 0
    End With
   
End Function

In IsOpenInvoice, the property value from the supplied workbook is set to a Boolean variable. If the property value is False or if the property doesn't exist, the variable is False. Of course the property value will never be false. I created the properties in the template and set the value to True. It will either exist or not.

For closed workbooks, IsInvoice uses FileSearch to find a file with the proper name and with the correct property. The argument sName is the full path and name of the file. If the file exists in the directory and has the property, True is returned. This is typically used before a file is opened, such as after GetOpenFilename is used but before the file is actually opened.

Both functions have an optional second argument, sProperty, that defaults to the property name that identifies the application in general. I also use these utilities to identify particular templates within my app. I may need to know, for instance, if the open workbook is an invoice, a sales order, or a report in particular, rather than just part of my app in general. I have constants set up for each template type that I want to test.

Here's an example of an application level event in a custom class module that uses IsOpenInvoice:

Private Sub mApp_SheetChange(ByVal Sh As Object, ByVal Target As Range)
   
    If IsOpenInvoice(Sh.Parent, gsINVOICE) Then
        'Do stuff
    End If
   
End Sub

Excel Easter Eggs

My Web site has a page that describes how to access the Easter Eggs in Excel 95, 97, 2000, and 2002. Greg Schultz, at Tech Republic, takes it one step further and provides lots of screen captures: Looking back at Microsoft Excel Easter Eggs.

In the past, Microsoft's developers used to go to great lengths when it came to secretly embedding Easter Eggs into their products. I stress the word past, because Microsoft now officially bans the practice for security reasons as part of their Trustworthy Computing initiative.

The increase in the prevalence of malware led to the notion that undocumented code embedded into a major application could be used to compromise sensitive or confidential data. In fact, many companies and government offices forbid the use of software containing Easter Eggs for security reasons.

Here's an example: The Hall of Tortured Souls, featured in Excel 95.