VBA Calculations Turning Back On Mid Execution - vba

I'm running a large macro that includes various sub queries and functions.
Despite having the standard code to turn off calculations while the macro is running, somehow calculations are turned back on during the code execution.
Application.ScreenUpdating = False
Application.Calculation = xlCalculationManual
I've added the above code the beginning of each major sub but still have the same issue. There's one point in the macro where I calculate the application to update a worksheet stored value, but I can't imagine that's what's causing it.
application.Calculate
Trying to find if there's a work around.

Related

Application.ScreenUpdating = False not working switching between Excel sheets or workbooks

The function Application.ScreenUpdating = False is not working whenever switching between worksheets or workbooks in Excel. This function alone worked fine in Excel 2010, but doesn't work in later versions from what I can tell. I am now using the office 365 desktop version of excel. In these later versions, the command only prevents updating when selecting cells or doing things within a specific worksheet, but for my purposes I need a form to pull data from a second worksheet which causes flickering.
Is there a way to prevent the screen from updating/flickering with SheetB briefly when it gets activated in this macro?
Sub ActivateSheetB()
Application.EnableEvents = False
Application.ScreenUpdating = False
Application.Calculation = xlCalculationManual
Sheets("SheetB").Activate
End Sub
I've had the same thing happen to me forever and it's fairly annoying but from my own observation, I believe that application.screenupdating = false is still working. What I mean by that is your code is still being sped up. Other than it visually being annoying and making users think they broke excel this is still an effective method for speeding up your workbook even when switching between sheets.
Hopefully someone comes along with a better answer than mine because I'd love to know what that answer is as well xD

Running a VBA Excel Macro and getting screen flickering even after rightly setting Application.ScreenUpdating to True and False

I have written a macro which is quite big and has several Sub functions. The macro pulls external data and perform Calculations on them and produces results on the sheet along with a graph.
The problem is that the macro runs absolutely fine with smaller data. But when I pull a databank of say 1500 entries, the screen starts flickering and the program hangs. It doesn't even give any error message.
Had it been any faults in loop, the program shouldn't have worked for 200 entries. But it does for a lot of datas except the very long ones. Also the size of arrays used are set up to 2000, and Application.ScreenUpdating has been turned False at the start and True at the end in every Sub.
Another important information as to how the program works:
The codes are connected to a Userform. So if one optionbutton and another entry is true, a particular process (Sub) is happening one at a time. So for each sub I have given Application.ScreenUpdating as False and True. Technically out of 15 subs, perhaps only 5 are running at a time in a module. I have kept every case in the same module as it is easier to handle that way. However, few subs run at a time.

Closing a userform that is in workbook A from workbook B

I'm new to VBA so there might be a simple answer to this question but if there is I sure haven't found it. What I am doing is copying data from several workbooks into one master workbook. I have writen the code for this and it works fine. The only problem is the workbooks where I'm retriving the data have userforms that automatically initiate when the workbook is accesed. This means that when I run my code to copy the data it hangs at each userform and wont continue until I've physically closed each userform. So my question is: Is there a way to remotely close the userforms in the raw data workbooks from my master workbook VBA code? Thanks in advance.
to close all userforms, (if you want a specific one , change my code)
sub Close_Userforms()
Dim Form as VBA.Userform 'if not work change to Object
For each Form in VBA.Userform
'can add a condition, like : if Form.name ="Whatever" then
unload Form 'if you don't want to lose the data from the userforms, Form.Hide, and later re-loop and Form.Show
next Form
edit : can also if Typename (Form)="Whatever" then , for the condition
Assuming you mean that the forms pop up when you open the workbooks, disable events before doing so:
Application.Enableevents = False
Workbooks.Open ...
Application.Enableevents = True
for example.
I would suggest trying
Application.EnableEvents = False
Further reading.
Short description: All events (Workbook_Open, Workbook_BeforeSave etc), that usually fires upon opening or closing a workbook, will be ignored.
I have written the following functions to make all macros a bit simpler (and faster). Simply place these functions in a regular module.
Public Function CalcOff()
Application.Calculation = xlCalculationManual
Application.ScreenUpdating = False
Application.EnableEvents = False
End Function
Public Function CalcOn()
Application.Calculation = xlCalculationAutomatic
Application.ScreenUpdating = True
Application.EnableEvents = True
End Function
Begin your macro with:
CalcOff
And then end your macro with:
CalcOn
Remember that you need to put "CalcOn" in all places that exits the running macro.
Disabling ScreenUpdating makes the code "run in background" (nothing will be displayed).
Setting Calculation to manual improves the speed of the code, since no calculations will be made when changing data. But it's very important to exit all macros with "CalcOn", otherwise your sheet won't calculate (and that's not funny), and it will look like Excel has frozen (since ScreenUpdating would still be turned off).
However, if you by any chance happen to break a running code without exiting it the proper way (running "CalcOn"), simply close the Excel application and reopen it. Or run a macro that ends with the "CalcOn" code. Or create a new macro with that simple line.

Cutting a column and then inserting with excel vba

Columns("DV").Cut
Columns("P").Insert Shift:=xlToRight
I am using this code above to basically move a column, but every time I run the macro, it slows the process so much. Is there a more efficient way to do this so my macro isn't bogged down?
Thanks.
You might try inserting this line at the beginning of the macro:
Application.Calculation = xlCalculationManual
And insert this at the end:
Application.Calculation = xlCalculationAutomatic
If you have a lot of formulas in the data you are moving around it is attempting to recalculate while the macro is running. The above lines will tell Excel to not calculate during the macro run.

Excel, VBA: Clear memory

I have a macro for Excel, nothing too fancy, no objects, just plain old cycles with formulas. Basically it's this:
I cycle through rows in one column, assigning pretty big SUMPRODUCT functions to the cells without executing them. Once I cycled through the row I do Range.Value = Range.Value twice to execute the formulas and to save result as value. Then I go for the next column.
With each column memory used by Excel increases significantly and after the macro is done and I save the file - the memory is still used (if I can trust Task Manager). After I close and reopen the file - all memory is, of course, freed and I can continue to work. I've reached a point where I can't process all the columns I need on a 32 bit Excel due to memory limit.
I was wondering, maybe there's some trick I could implement between the columns to make Excel forget whatever it keeps remembering? I don't really care if it will hit performance (in case it has cached anything useful for further calculations), I just need to keep memory usage from growing too huge to process. I googled a bit but all the advises are related to setting big objects to nothing - I don't really set much of anything to anything, just cycle through, so that probably won't apply to my case.
Code is like this (don't have it on me right now, but it's a general simplified version of what is in it):
for i = 1 to 12
ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Font.Color = vbWhite
for m = 1 to x
ThisWorkbook.ActiveWorksheet.Cells(m, i).Formula = "'=SUMPRODUCT(blah)"
next m
ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Value = ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Value
ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Value = ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Value
ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Font.Color = vbBlack
next i
Basically, I color them white so I don't see the messy function text, add function, execute it, save as values, color text black.
Important addition: I use SUMPRODUCT to sum some cells from closed files.
This isn't really enough code to help you improve the efficiency. I can point out a few tips for you now though.
The first thing to remember is to switch application screen updating to false at the start of the macro.
Application.ScreenUpdating = False
then switch it back just before the end of the macro code
Application.ScreenUpdating = True
Changing the font color is unnecessary now. Your screen will be locked for refreshing while the macro is being executed so you will not be seeing the changes until the macro has finished working.
Consider, disabling Events too.
Application.EnableEvents = False and Application.EnableEvents = true same idea as with the screen updating.
The second thing is to make use of Evaluate() function. Please google it and read about how efficient that function can be.
Instead of putting a function into cell and then doing .Value = .Value you can just Evaluate() an expression and return the result straight to the cell which is much faster!
So you could do something like
for i = 1 to 12
ThisWorkbook.ActiveWorksheet.Range(Cells(1,i),Cells(x,i)).Value = Evaluate("=SUM(blah)")
next i
I hope you get the idea.
Here are a few links with tips on how to speed up your macro:
http://msdn.microsoft.com/en-us/library/office/ff193019.aspx
http://fastexcel.wordpress.com/2011/11/02/evaluate-functions-and-formulas-fun-how-to-make-excels-evaluate-method-twice-as-fast/
http://www.soa.org/news-and-publications/newsletters/compact/2012/january/com-2012-iss42-roper.aspx
http://xlvba.fr.yuku.com/topic/278/The-Evaluate-Method#.UmZP6Pmkp8s
I know this is an old question but a way that seems to work is saving the Workbook. Run ThisWorkbook.Save every once in a while and if you monitor EXCEL in the Task Manager you will notice that it clears up a significant amount of memory.
It seems as though Excel may be caching certain function calls or something and saving clears this cache.