There is an embedded excel file at the bottom currently reading as “Source: NielsenIQ RMS | L52 w/e…”
However, this is a display that uses some embedded formulas, the result should be something more like “Source: NielsenIQ RMS | YTD w/e…”
If I open the generated file and double click to open the object, it suddenly starts to read as expected. I generally refresh formulas using:
using Aspose.Cells;
using Aspose.Cells.Pivot;
using Aspose.Slides;
List<string> queryKeys = new() { "6780253.SLIDE2147483647_OBJECT 3" };
string directory = @"[directory omitted]\slide 4 not updating.pptx";
using FileStream ReportStream = File.Open(directory, FileMode.Open, FileAccess.ReadWrite);
using Aspose.Slides.Presentation ap = new(ReportStream);
foreach (ISlide slide in ap.Slides)
{
IEnumerable<IShape> potentialCharts = slide.Shapes.Where(s => s is OleObjectFrame);
foreach (IShape slideShape in potentialCharts)
{
if (slideShape is OleObjectFrame ole && !string.IsNullOrEmpty(slideShape.CustomData.Tags["ObjectName"]) && queryKeys.Contains(slideShape.CustomData.Tags["ObjectName"].ToUpper()))
{
ole.GraphicalObjectLock.AspectRatioLocked = false;
using MemoryStream imageStream = new();
using MemoryStream ms = new(ole.EmbeddedData.EmbeddedFileData);
imageStream.Position = 0;
Aspose.Cells.Workbook wb = new(ms);
int activeIndex = wb.Worksheets.ActiveSheetIndex;
CalculationOptions opts = new()
{
CalcStackSize = 5000,
Recursive = true,
IgnoreError = true
};
foreach (Aspose.Cells.Worksheet worksheet1 in wb.Worksheets)
{
worksheet1.RefreshPivotTables();
foreach (PivotTable pTable in worksheet1.PivotTables)
{
pTable.RefreshDataFlag = true;
pTable.RefreshData();
pTable.RefreshDataFlag = false;
pTable.CalculateData();
pTable.RefreshDataOnOpeningFile = true;
pTable.CalculateRange();
}
worksheet1.CalculateFormula(opts, true);
worksheet1.Shapes.UpdateSelectedValue();
foreach (Aspose.Cells.Charts.Chart chart1 in worksheet1.Charts)
{
chart1.RefreshPivotData();
chart1.Shapes.UpdateSelectedValue();
chart1.Calculate();
}
}
wb.CalculateFormula(opts);
}
ap.Save(@"[directory omitted]\abc.pptx", Aspose.Slides.Export.SaveFormat.Pptx);
}
}
is there a step I am missing to “force” the object to update its formula? I know the underlying data is already updated in the “Data” tab but its like the text box is “stuck” on the old value.
The workbook is being opened, recalculated and then discarded – the updated bytes are never written back to the OLE object.
After the calculations you must replace the original embedded file data with the new workbook data (and, for safety, mark the object as changed) before saving the presentation.
Minimal change
using (MemoryStream src = new MemoryStream(ole.EmbeddedData.EmbeddedFileData))
{
// open the embedded workbook
var wb = new Aspose.Cells.Workbook(src);
// recalculate everything you need
wb.CalculateFormula(new CalculationOptions { CalcStackSize = 5000, Recursive = true, IgnoreError = true });
// write the updated workbook back to a stream
using (var updated = new MemoryStream())
{
wb.Save(updated, SaveFormat.Xlsx); // or the original format (Xls/Xlsx)
ole.EmbeddedData.EmbeddedFileData = updated.ToArray(); // replace the OLE data
ole.IsObjectDataChanged = true; // optional – forces a refresh
}
}
Then call ap.Save(..., SaveFormat.Pptx); as you already do.
Why this works
ole.EmbeddedData.EmbeddedFileData holds the raw bytes of the embedded Excel file.
Changing the workbook in memory does not automatically update those bytes.
Re‑assigning the modified byte array (and optionally setting IsObjectDataChanged) tells Aspose.Slides that the OLE object has new content, so the displayed text box reflects the latest formula results without the user having to open the object manually.
If you still see the old value after applying the snippet, please provide:
The exact version of .NET you are targeting (e.g., .NET 6, .NET Framework 4.8).
A minimal reproducible PPTX (the one you attached is fine) – ensure it contains the same OLE object.
Any exception or warning messages that appear during wb.Save or ap.Save.
With that information we can verify whether any additional steps (e.g., refreshing linked data connections) are required.
@BK.Broiler.730,
I have reproduced the problem you described.
We have opened the following new ticket(s) in our internal issue tracking system and will investigate the case according to the terms mentioned in Free Support Policies.
Issue ID(s): SLIDESNET-45235
You can obtain Paid Support Services if you need support on a priority basis, along with the direct access to our Paid Support management team.
// write the updated workbook back to a stream
using (var updated = new MemoryStream())
{
wb.Save(updated, SaveFormat.Xlsx); // or the original format (Xls/Xlsx)
ole.EmbeddedData.EmbeddedFileData = updated.ToArray(); // replace the OLE data
ole.IsObjectDataChanged = true; // optional – forces a refresh
}
Two things here, EmbeddedData.EmbeddedFileData is read only at least with the version I am currently using
Property or indexer 'IOleEmbeddedDataInfo.EmbeddedFileData' cannot be assigned to -- it is read only
Also
'OleObjectFrame' does not contain a definition for 'IsObjectDataChanged' and no accessible extension method 'IsObjectDataChanged' accepting a first argument of type 'OleObjectFrame' could be found (are you missing a using directive or an assembly reference?)
It seems a ticket has been opened as a result of this, so I will wait to see the result of that.
EmbeddedFileData and IsObjectDataChanged are writable only in the recent Aspose.Slides for .NET releases.
In the version you are using the IOleEmbeddedDataInfo.EmbeddedFileData property is read‑only and the OleObjectFrame.IsObjectDataChanged flag does not exist, which is why the compiler reports the errors you see.
What to do
Upgrade to the latest Aspose.Slides for .NET package (e.g. 24.x).
In that version the API looks exactly like the snippet you posted:
using (var updated = new MemoryStream())
{
wb.Save(updated, SaveFormat.Xlsx); // or Xls
ole.EmbeddedData.EmbeddedFileData = updated.ToArray(); // writable
ole.IsObjectDataChanged = true; // forces a refresh
}
If you must stay on the older build, use the setter that is available on the embedded‑data object:
using (var updated = new MemoryStream())
{
wb.Save(updated, SaveFormat.Xlsx);
ole.EmbeddedData.SetData(updated.ToArray()); // replaces the OLE bytes
// No IsObjectDataChanged flag – the object will be refreshed
// when the presentation is saved.
}
(The SetData method is present in the older API; it writes the new byte array back to the OLE object.)
After updating the embedded workbook, call ap.Save(..., SaveFormat.Pptx) as you already do.
Next steps
Confirm the exact Aspose.Slides version you are currently referencing (e.g., 22.8, 23.3, etc.).
If you upgrade and still encounter issues, please attach a minimal PPTX that reproduces the problem and the full stack trace (if any) from ap.Save.
Once we have the version number and, if needed, a reproducible file, we can verify that the refresh works as expected.
Thank you, I believe we have some paid support but I need to talk to my managers about this.
I do want to ask, when something like this happens, like an element doesn’t update, is there any sort of error that can be thrown to alert us. The problem is if this is a 50+ Slide presentation with many elements, clients often don’t really have the time to check each and every element. I realize this is a long shot, but I had to tell my supervisors that I asked this question.
// write the updated workbook back to a stream
using (var updated = new MemoryStream())
{
wb.Save(updated, SaveFormat.Xlsx); // or the original format (Xls/Xlsx)
ole.EmbeddedData.EmbeddedFileData = updated.ToArray(); // replace the OLE data
ole.IsObjectDataChanged = true; // optional – forces a refresh
}
Same errors,
Property or indexer 'IOleEmbeddedDataInfo.EmbeddedFileData' cannot be assigned to -- it is read only
'OleObjectFrame' does not contain a definition for 'IsObjectDataChanged' and no accessible extension method 'IsObjectDataChanged' accepting a first argument of type 'OleObjectFrame' could be found (are you missing a using directive or an assembly reference?)
// write the updated workbook back to a stream
using (var updated = new MemoryStream())
{
wb.Save(updated, SaveFormat.Xlsx); // or the original format (Xls/Xlsx)
// Replace the embedded data object entirely
ole.SetEmbeddedData(
new OleEmbeddedDataInfo(
updated.ToArray(),
"xlsx"
)
);
}
which compiles with the latest versions I got from nuget
We evaluated your issue in details. Please note that PowerPoint automatically refreshes images only for linked OLE objects. Embedded objects are updated only after a double-click.
You are on the right track with refreshing and recalculating the workbook. To complete the process, the code also needs to recreate the image based on the updated data and refresh the OLE object data.
Please try the following extended code:
using Aspose.Cells;
using Aspose.Cells.Pivot;
using Aspose.Slides;
using Aspose.Slides.DOM.Ole;
List<string> queryKeys = new() { "6780253.SLIDE2147483647_OBJECT 3" };
string directory = @"[directory omitted]\slide 4 not updating.pptx";
using FileStream ReportStream = File.Open(directory, FileMode.Open, FileAccess.ReadWrite);
using Aspose.Slides.Presentation ap = new(ReportStream);
foreach (ISlide slide in ap.Slides)
{
IEnumerable<IShape> potentialCharts = slide.Shapes.Where(s => s is OleObjectFrame);
foreach (IShape slideShape in potentialCharts)
{
if (slideShape is OleObjectFrame ole && !string.IsNullOrEmpty(slideShape.CustomData.Tags["ObjectName"]) && queryKeys.Contains(slideShape.CustomData.Tags["ObjectName"].ToUpper()))
{
ole.GraphicalObjectLock.AspectRatioLocked = false;
using MemoryStream ms = new(ole.EmbeddedData.EmbeddedFileData);
using Workbook wb = new(ms);
int activeIndex = wb.Worksheets.ActiveSheetIndex;
CalculationOptions opts = new()
{
CalcStackSize = 5000,
Recursive = true,
IgnoreError = true
};
foreach (Worksheet worksheet1 in wb.Worksheets)
{
worksheet1.RefreshPivotTables();
foreach (PivotTable pTable in worksheet1.PivotTables)
{
pTable.CalculateData();
pTable.CalculateRange();
}
worksheet1.CalculateFormula(opts, true);
worksheet1.Shapes.UpdateSelectedValue();
foreach (Aspose.Cells.Charts.Chart chart1 in worksheet1.Charts)
{
chart1.RefreshPivotData();
chart1.Shapes.UpdateSelectedValue();
chart1.Calculate();
}
}
// updating the OleObjectFrame substitute image
if (wb.Worksheets.OleSize != null)
{
CellArea oleArea = (CellArea)wb.Worksheets.OleSize;
Worksheet activeSheet = wb.Worksheets[activeIndex];
Aspose.Cells.Range cellRange = activeSheet.Cells.CreateRange(oleArea.StartRow, oleArea.StartColumn,
oleArea.EndRow - oleArea.StartRow + 1, oleArea.EndColumn - oleArea.StartColumn + 1);
using MemoryStream imageStream = CreateOleImage(cellRange);
ole.SubstitutePictureFormat.Picture.Image.ReplaceImage(imageStream.ToArray());
}
// updating the OleObjectFrame embedded data
using var oleUpdatedData = new MemoryStream();
wb.Save(oleUpdatedData, Aspose.Cells.SaveFormat.Xlsx);
IOleEmbeddedDataInfo newData =
new OleEmbeddedDataInfo(oleUpdatedData.ToArray(), ole.EmbeddedData.EmbeddedFileExtension);
ole.SetEmbeddedData(newData);
}
}
}
ap.Save(@"[directory omitted]\abc.pptx", Aspose.Slides.Export.SaveFormat.Pptx);
static MemoryStream CreateOleImage(Aspose.Cells.Range cellRange)
{
cellRange.Worksheet.IsVisible = true;
var pageSetup = cellRange.Worksheet.PageSetup;
pageSetup.PrintArea = cellRange.Address;
pageSetup.LeftMargin = 0;
pageSetup.RightMargin = 0;
pageSetup.TopMargin = 0;
pageSetup.BottomMargin = 0;
pageSetup.ClearHeaderFooter();
var imageStream = new MemoryStream();
new Aspose.Cells.Rendering.SheetRender(cellRange.Worksheet,
new Aspose.Cells.Rendering.ImageOrPrintOptions
{
OnePagePerSheet = true,
OnlyArea = true,
ImageType = Aspose.Cells.Drawing.ImageType.Emf
})
.ToImage(0, imageStream);
imageStream.Position = 0;
return imageStream;
}
I have tested the above code using the Aspose.Slides for .NET 25.12 and it works fine. Please find attached the output PPTX file for your reference. abc.zip (5.1 MB)
Thank you, it does help, but I am running into the client still having problems and the client service team escalating to me over the matter. I think we ran into the same problem but in a more “complex” case. Consider the following, I am using these libraries
It seems to be doing the same thing where the preview images are not updating or are somehow using a different object’s preview image for its own. The same thing where clicking to open actually does refresh the object, the best example to hyper focus on: first slide; Salty Snacks - Category Shr Chg that says NO ROM but opening the file should result in something numeric. I believe this is related to something where the client copies and pasts a lot of these objects, maybe that has something to do with it, but with this latest code sample and including the step of replacing the preview image, I believe this may be a similar situation outlined originally in “SLIDESNET-45235” (we added it to paid support).
Interesting, if I remove the second slide, in our production environment, this updates just fine.
Thank you for sharing your scenario/case along with the sample presentation file and code snippet. I tested and reviewed your new test case using the provided solution, but it seems it is not functioning as expected. Specifically, I noticed that on the first slide, “Salty Snacks - Category Shr Chg” displays “NOROM,” but when opening the file and double-clicking on the shape/link, it shows a numeric value instead. I have documented this issue, along with the resource files and relevant details, under your existing ticket “SLIDESNET-45235” in our database. Since you have already escalated this to “Business Support,” so, it will be prioritized accordingly and hopefully it will be addressed soon. We will keep you updated as soon as we receive any further information.