PowerPoint vba BeforeSaveAs - vba

I have a PowerPoint template, which is links up with Excel. Some of the areas in Excel has been copied with links, so that it will automatically update.
Whenever this PowerPoint template will be Saved As, I need to remove these links to external Excel Workbooks.
Is there somehow to do this in PowerPoint just like
Private Sub Workbook_Before Save(ByVal SaveAsUI As Boolean, Cancel As Boolean) in Excel?
So far
I tried the below-mentioned answer, without any luck. The code somehow seems to not run - here I don't know if I'm doing it wrong. I tried running it in a normal module and a class module - without any way of provoking it to happen. Then I tried running it as a normal sub, and here I got errors on the HasRevisionInfoand alsoApplication.PresentationBeforeSave.

Yes there is, look into Application.PresentationBeforeSave event which Occurs before a presentation is saved.
Here is vb example
Private Sub PPTApp_PresentationBeforeSave(ByVal Pres As Presentation, _
Cancel As Boolean)
Dim intResponse As Integer
Set Pres = ActivePresentation
If Pres.HasRevisionInfo Then
intResponse = MsgBox(Prompt:="The presentation contains revisions. " & _
"Do you want to accept the revisions before saving?", Buttons:=vbYesNo)
If intResponse = vbYes Then
Cancel = True
MsgBox "Your presentation was not saved."
End If
End If
End Sub

I got it to work after a lot of research, #0m3R provided me with some of the right answer.
Somehow I found somewhere, that I had to combine a class module with a regular module.
Here's the code for the Class Module:
Private Sub PPTApp_PresentationBeforeSave(ByVal Pres As Presentation, Cancel As Boolean)
Dim sld As Slide
Dim shp As Shape
Dim TextValue As String
Dim intResponse As Integer
Set Pres = ActivePresentation
TextValue = "You're about to save this PowerPoint." & Chr(10) & "This Powerpoint is programmed to break all links" & _
" meaning that all of the content will not be updated automatically anymore." & Chr(10) & Chr(10) & _
"Do you wish to break all links?"
If Pres.Name <> "A3.potm" Then
intResponse = MsgBox(TextValue, Buttons:=vbYesNo)
If intResponse = vbYes Then
For Each sld In Pres.Slides
For Each shp In sld.Shapes
On Error Resume Next
shp.LinkFormat.BreakLink
On Error GoTo 0
Next shp
Next sld
Else
MsgBox "You didn't break all links - the presentation may be overwritten in the future..."
End If
End If
End Sub
Here's the code for the regular Module
Option Explicit
Dim cPPTObject As New cEventClass
Sub InitializeApp()
Set cPPTObject.PPTApp = Application
End Sub
I chose to make a "Command Button" in my PowerPoint, to have the user run a code before viewing the presentation. Then whenever they will save this presentation, the have to choose if they want to delete the links or not :)
Thank you for your assistance :)

Related

Add row-break to PowerPoint add-in

I've created a custom Powerpoint add-in (ppam) using the following code (from this tutorial https://www.rdpslides.com/pptfaq/FAQ00031_Create_an_ADD-IN_with_TOOLBARS_that_run_macros.htm):
Sub Auto_Open()
Dim oToolbar As CommandBar
Dim oButton As CommandBarButton
Dim MyToolbar As String
MyToolbar = "My toolbar"
On Error Resume Next
Set oToolbar = CommandBars.Add(Name:=MyToolbar, _
Position:=msoBarFloating, Temporary:=True)
If Err.Number <> 0 Then
Exit Sub
End If
On Error GoTo ErrorHandler
Set oButton = oToolbar.Controls.Add(Type:=msoControlButton)
With oButton
'repeat code for each button'
End With
oToolbar.Visible = True
NormalExit:
Exit Sub
ErrorHandler:
MsgBox Err.Number & vbCrLf & Err.Description
Resume NormalExit:
End Sub
It works well, and I've been able to add multiple buttons to the Add-in toolbar. However, all buttons crowd on the same row, and I would really like to have a row-break, in order to fit more buttons in the toolbar overview.
I've tried to create separate add-in's for them to display on separate rows, but that just leads to one of the add-ins not showing. Is there a way to add a row-break to the add-in?

How to insert images as per slide title through vba code

I want to write VBA code for inserting the image as per the slide name from the folder means after running the VBA it automatically inserts the images as per the slide name
For eg: if the slide contains "Top View" in the text box then by running the VBA script it should automatically pick the picture having name "Top View" from the particular folder.
As shown in the attached images.
Slide having by text box as top view
Folder Path
I have posted one of the question some days ago but I didn't find the exact solution here is the link of my previous question which I have asked
Previous question
One of member has shared one code but its working properly also I modified it little bit though its not working properly if possible pl. help me
Option Explicit
Sub image_insert()
Dim objPresentaion As Presentation
Dim objSlide As Slide
Dim objImageBox As Shape
Dim sSlideTitle As String
Dim sFolder As String
Set objPresentaion = ActivePresentation
sFolder = "C:\Users\mehta\Desktop\Folder for ppt images\Top
View.jpg"
For Each objSlide In objPresentaion.Slides
sSlideTitle = GetTitleText(objSlide)
' WAS there a title on the slide?
If Len(sSlideTitle) > 0 Then
' make sure the image exists
If Len(Dir$(sFolder & sSlideTitle & ".JPG")) > 0 Then
Set objImageBox = objSlide.Shapes.AddPicture(sFolder &
sSlideTitle & ".JPG", _
msoCTrue, msoCTrue, 25, 25)
Else
' Comment this out later
' MsgBox "Image missing: " & sSlideTitle
End If
Else
' comment this out later:
MsgBox "This slide has no title"
End If
Next ' Slide
End Sub
Function GetTitleText(oSl As Slide) As String
Dim sTemp As String
With oSl
' handle errors in case there's no slide title
On Error Resume Next
sTemp = .Shapes.Title.TextFrame.TextRange.Text
If Err.Number <> 0 Then
sTemp = ""
End If
End With
GetTitleText = sTemp
End Function
Regards.

VB.Net VSTO PowerPoint Addin

I'm making an Add-in for PowerPoint 2013. My goal is to convert all equations that I find on slides to normal text, to change the font of those equations.
Because it won't let me change font while they are equations. I managed to find the equations, by iterating through text ranges and finding font name, they use "Cambria Math". So my question is how can programmatically change equations to normal text, Like the button in equation tools does? And it seems for some reason they removed "record macro" from PowerPoint, so I couldn't get help from that.
I tried recording macro in word and doing the same thing, and i got: Selection.OMaths(1).ConvertToMathText, but it doesn't seem to be OMaths in PowerPoint.
Dim Application As PowerPoint.Application = New PowerPoint.Application
Dim Presentation As PowerPoint.Presentation = Application.ActivePresentation
Dim Windows As PowerPoint.DocumentWindows = Application.Windows
For Each Slide As PowerPoint.Slide In Presentation.Slides
For Each Shape As PowerPoint.Shape In Slide.Shapes
For Each Paragraph As PowerPoint.TextRange In Shape.TextFrame.TextRange
For Each Line As PowerPoint.TextRange In Paragraph.Lines
If Line.Font.Name = "Cambria Math" Then
With Line.Font
.Name = "Calibri"
.Bold = True
End With
ElseIf Line.Font.Name = "Calibri" Then
With Line.Font
.Name = "Palatino"
End With
End If
Next Line
Next Paragraph
Next Shape
Next Slide
End Sub
Other text here is changed normally, but equations the ones with "Math Cambria" font, are unchanged.
I also tried to get selection, then something with OMaths, like in Word Vsto, but, it seems OMaths is not part of the PowerPoint. This next code is actually supposed to change it to equation, but i guess if it worked, could have find a way to reverse it.
For Each Window As PowerPoint.DocumentWindow In Windows
Selection.OMaths(1).ConvertToMathText
Next Window
I got it to work with PowerPoint 2016 in VBA. I didn't have "Calibri" in my list of fonts, so I changed it to "Calibri (Body)" and it works. It may be the same issue you're having with the .NET VSTO Addin. If I have time, I'll build a example of the VSTO Addin and post the results as well.
Video
VBA Code
Public Sub UpdateShapeFont()
On Error GoTo ErrTrap
Dim Application As PowerPoint.Application: Set Application = New PowerPoint.Application
Dim Presentation As PowerPoint.Presentation: Set Presentation = Application.ActivePresentation
Dim Windows As PowerPoint.DocumentWindows: Set Windows = Application.Windows
Dim Slide As PowerPoint.Slide
Dim Shape As PowerPoint.Shape
Dim Paragraph As PowerPoint.TextRange
Dim line As PowerPoint.TextRange
For Each Slide In Presentation.Slides
For Each Shape In Slide.Shapes
For Each Paragraph In Shape.TextFrame.TextRange
For Each line In Paragraph.Lines
Select Case line.Font.Name
Case "Cambria Math"
With line.Font
.Name = "Calibri (Body)" 'check if the font exists in your list of fonts; it did not work for "Calibri"
.Bold = True
End With
Case "Calibri"
With line.Font
.Name = "Palatino"
End With
End Select
Next line
Next Paragraph
Next Shape
Next Slide
ExitProcedure:
On Error Resume Next
Exit Sub
ErrTrap:
Select Case Err.number
Case Else
Debug.Print "Error #: " & Err.number & " |Error Description: " & Err.description
End Select
Resume ExitProcedure
Resume 'for debugging
End Sub

With Block Variable not Set -- Error when workbook Opened

This macro is one that was not written by me, so I'm having trouble understanding the source of the error. I have a macro that's supposed to run on startup to adjust the ribbon to add a button, and another part to remove styles when you select that button. Currently, I get the message: Object variable or With block variable not set. When I select "Debug" it goes to the VBA screen and immediately gives me 3 more error pop-ups that say: Can't execute code in break mode.
The first part of this is the two subs that are to run on startup, which are:
Dim WithEvents app As Application
Private Sub App_WorkbookActivate(ByVal Wb As Workbook)
Module1.MyRibbon.Invalidate
End Sub
Private Sub Workbook_Open()
Set app = Application
End Sub
It highlights the Module1.MyRibbon.Invalidateas the problematic bit. Personally I don't see anything wrong with this per se, but perhaps the problem is in the Module 1? That code contains three subs, as follows:
Public MyRibbon As IRibbonUI
'Callback for customUI.onLoad
Sub CallbackOnLoad(Ribbon As IRibbonUI)
Set MyRibbon = Ribbon
End Sub
'Callback for customButton getLabel
Sub GetButtonLabel(control As IRibbonControl, ByRef returnedVal)
If ActiveWorkbook Is Nothing Then
returnedVal = "Remove Styles"
Else
returnedVal = "Remove Styles" & vbCr &
Format(ActiveWorkbook.Styles.Count, "#" & Application.International(xlThousandsSeparator) & "##0")
End If
End Sub
Sub RemoveTheStyles(control As IRibbonControl)
Dim s As Style, i As Long, c As Long
On Error Resume Next
If ActiveWorkbook.MultiUserEditing Then
If MsgBox("You cannot remove Styles in a Shared workbook." & vbCr & vbCr & _
"Do you want to unshare the workbook?", vbYesNo + vbInformation) = vbYes Then
ActiveWorkbook.ExclusiveAccess
If Err.Description = "Application-defined or object-defined error" Then
Exit Sub
End If
Else
Exit Sub
End If
End If
c = ActiveWorkbook.Styles.Count
Application.ScreenUpdating = False
For i = c To 1 Step -1
If i Mod 600 = 0 Then DoEvents
Set s = ActiveWorkbook.Styles(i)
Application.StatusBar = "Deleting " & c - i + 1 & " of " & c & " " & s.Name
If Not s.BuiltIn Then
s.Delete
If Err.Description = "You cannot use this command on a protected sheet. To use this command, you must first unprotect the sheet (Review tab, Changes group, Unprotect Sheet button). You may be prompted for a password." Then
MsgBox Err.Description & vbCr & "You have to unprotect all of the sheets in the workbook to remove styles.", vbExclamation, "Remove Styles AddIn"
Exit For
End If
End If
Next
Application.ScreenUpdating = True
Application.StatusBar = False
End Sub
I've never written any Activation or Ribbon-related macro, so I have no idea where the error could be. The addin works just find regardless of this message, as the button gets added and it functions as it should when the file isn't a blank file, but I get the error pop-up and the button doesn't get created right on new, blank files. How could I fix this?
I simply deleted:
Private Sub App_WorkbookActivate(ByVal Wb As Workbook)
Module1.MyRibbon.Invalidate
End Sub
No runtime errors on start of excel and no issues when using the script; counts fine and deletes fine. Windows 7, Excel 2010.

How to run VBA (macro) code in PowerPoint 2010 without opening the developer

This issues is a bit of quirk - and it may be a systematic issue that just won't work. My overall project is that I need to have a presentation playing on loop 24/7 and it has some linked charts from an excel file that it needs to pull data from. I wrote the basic code to do this.
However when I first open PowerPoint and run the presentation -> No code is run (verified with Debug.Prints and MsgBoxes). However if I just open up the code in developer (But don't edit) and run the presentation, everything works as planned. I've turned all the Trust Center Security settings to allow all macros and setup my network files as automatically trusted as well. I've also verified that this occurs with another of the laptops here. Any help is greatly appreciated. For reference, this is my simple code that needs to run.
Sub updateCharts()
Dim i As Integer
Dim sld As Slide
Dim shp As Shape
If IsFileOpen(filePath) = False Then
If ActivePresentation.SlideShowWindow.View.Slide.SlideIndex = 1 Then
For Each sld In ActivePresentation.Slides
For Each shp In sld.Shapes
If shp.HasChart Then
On Error Resume Next
shp.LinkFormat.Update
shp.Chart.Refresh
On Error GoTo 0
End If
Next shp
Next sld
End If
End If
End Sub
Sub OnSlideShowPageChange(ByVal Win As SlideShowWindow)
Call updateCharts
End Sub
Thanks for the opportunity. There are 3 main parts that can allow you to do that.
Need a way to auto run a macro upon presentation launch
Need a way to handle PowerPoint Application Events
A regular module for calls from Event Handler
Solution:
Follow instructions from PPT Alchemy, objective is to add UI element: <customUI xmlns="http://schemas.microsoft.com/office/2006/01/customui"
onLoad="onLoadCode" >
</customUI>
where onLoadCode is a sub you will create in a Module
According to MS How to: Use Events with the Application Object, you need to create a Class Module, have it initialized by a Sub. Here we want the onLoadCode to do initialization.
A Sub in a Module will do the Chart updates.
Ensure the Presentation is set to Kiosk mode for your purpose:
CODES
Class Module: EventClassModule
Public WithEvents App As Application
Private Sub App_SlideShowBegin(ByVal Wn As SlideShowWindow)
Debug.Print Now & vbTab & "App_SlideShowBegin"
updateCharts Wn
End Sub
Private Sub App_SlideShowNextSlide(ByVal Wn As SlideShowWindow)
Debug.Print Now & vbTab & "App_SlideShowNextSlide"
updateCharts Wn
End Sub
Module: Player
Dim X As New EventClassModule
Sub OnLoadCode()
InitializeApp
End Sub
Sub InitializeApp()
Set X.App = Application
ActivePresentation.SlideShowSettings.Run
End Sub
Sub updateCharts(ByRef Win As SlideShowWindow)
Dim sld As Slide
Dim shp As Shape
Debug.Print Now & vbTab & "Playing slide with index: " & Win.View.Slide.SlideIndex
If Win.View.Slide.SlideIndex = 1 Then
Debug.Print Now & vbTab & "Update charts on other slides!"
For Each sld In Win.Presentation.Slides
For Each shp In sld.Shapes
If shp.HasChart Then
Debug.Print Now & vbTab & "Update chart """ & shp.Chart.Name & """ on slide index " & sld.SlideIndex
On Error Resume Next
shp.LinkFormat.Update
shp.Chart.Refresh
If Err.Number <> 0 Then
Debug.Print Now & vbTab & "ERR(" & Err.Number & ") " & Err.Description
Err.Clear
End If
On Error GoTo 0
End If
Next
Next
End If
End Sub
You should remove the Debug lines for production environment. Have fun!