obectjViewport viewportSz in microsoft ML

jad maqdah 21 Reputation points
2022-11-29T15:11:49.113+00:00

Hello, I have been trying to programmatically write 3D GLB objects in PowerPoint using C++. I have figured out all the camera settings and options, but the only thing I need to calculate is the objViewport Sz.

Here is the link of the element and its attribute: https://video2.skills-academy.com/en-us/openspecs/office_standards/ms-odrawxml/c20ace8b-ea42-4d0f-9f7e-e0bbd467152b

I cannot find an equation anywhere to calculate the viewportSz attribute. This is important because when the 3d GLB object is written to PowerPoint, the viewport is either too zoomed in (some parts of it don't fit in the viewport) or zoomed out (the object is very small).

Does it have to do with the object's extents (i.e., the bounding box extents) (max extent in X, max extent in Y, max extent in Z)?

Can someone help me please?

Thank you!

Office Open Specifications
Office Open Specifications
Office: A suite of Microsoft productivity software that supports common business tasks, including word processing, email, presentations, and data management and analysis.Open Specifications: Technical documents for protocols, computer languages, standards support, and data portability. The goal with Open Specifications is to help developers open new opportunities to interoperate with Windows, SQL, Office, and SharePoint.
127 questions
{count} votes

Accepted answer
  1. Hung-Chun Yu 976 Reputation points Microsoft Employee
    2022-12-03T20:14:04.123+00:00

    Hi @jad maqdah

    Calculation of viewportSz is, unfortunately, too complex to be reduced to mathematical equations. There are two basic steps that are run after a 3D Model is first inserted into Office: calculating the frame bounds, and then calculating the full frame size. We also run variations on these steps after any Office commands that change the camera settings.

    Let’s refer to the bounds stored in the p:xfrm (transform) element of the p:graphicFrame element as the “3D Model Frame Rect”. Each app (PowerPoint, Excel, Word) have their own default Frame Rect dimensions for newly inserted 3D Models. PowerPoint chooses a default starting frameRect such that the width = slideWidth*2/3, the height = slideWidth*4/9, and the anchor is centered in the slide. I didn’t research the Excel or Word starting frame rect logic; they are probably similar.

    1. Update the 3D Model Frame Rect to match the aspect ratio of the 3D model
      a. Start with originalFrameRect, the original 3D Model Frame Rect as described above (some fixed size relative to the doc slide/page).
      b. Calculate originalFrameSize as the min of originalFrameRect's width or height.
      c. Measure visibleBoundsRatios – A 2D ratio vector where visibleBoundsRatios.dx is the ratio of the how much of the (square) 3D camera viewport is filled on the x-axis, and visibleBoundsRatios.dy reflects the y-axis. We actually render the 3D model to a small texture and scan the image to measure this. For example, a value of (1.0,0.5) means the 3D scene fully fills the camera on the x-axis, but only fills 50% of the y-axis.
      i. Note: We init our cameras to leave buffer around the 3D scene, and the scene is probably bigger on one axis than the other, so both values in the ratio vector are almost always smaller than 0.9 on each axis.
      ii. Note: For an example seahorse model, which is tall and skinny, we measure this visible bounds ratio as (0.125, 0.858).
      d. Calculate adjustedFrameRect = originalFrameSize * visibleBoundsRatios. This effectively shrinks originalFrameRect to have the aspect ratio of the camera output, but inscribed within and slightly smaller than the original/default frame rect.
    2. Calculate “fullFrameSize”, which will then be stored in attribute viewportSz inside element am3d:objViewport:

    a. Measure visibleBoundsRatios (same as described in part 1, and it should be the same exact value until the camera is changed or scene is rotated)
    b. Inflate visibleBoundsRatios on whichever axis (x or y) allows its aspect ratio (visibleBoundsRatios.x / visibleBoundsRatios.y) to equal (adjustedFrameRect.width / adjustedFrameRect.height).
    c. Calculate fullFrameSize = adjustedFrameRect.height / visibleBoundsRatios.dy

    This is a complex algorithm, and could be challenging to emulate exactly like Office does it. The hardest part to emulate is probably 1.c and 2.a, which involve rasterization and image scanning. Perhaps you could approximate these steps instead, given some knowledge of how your camera and 3D scene were programmatically assembled.

    Let me know if this helped

    Hung-Chun Yu

    0 comments No comments

5 additional answers

Sort by: Most helpful
  1. Hung-Chun Yu 976 Reputation points Microsoft Employee
    2022-11-30T17:08:34.127+00:00

    Hi @jad maqdah

    I did some research and I found the following:

    1. ViewPortSize = ScreenPixelResolution / DevicePixelRatio Source: https://stackoverflow.com/questions/37481224/how-to-calculate-viewport-width-based-on-device-specification
    2. Window to Viewport Transformation in Computer Graphics with Implementation - https://www.geeksforgeeks.org/window-to-viewport-transformation-in-computer-graphics-with-implementation/
    3. C++ Viewports Examples - https://cpp.hotexamples.com/examples/-/Viewport/-/cpp-viewport-class-examples.html

    Let me know if this helped.

    Hung-Chun Yu
    Microsoft Open Specifications Support

    0 comments No comments

  2. jad maqdah 21 Reputation points
    2022-12-01T10:53:48.52+00:00

    Hi @Hung-Chun Yu

    I am not sure if this will give me the correct answer in the PowerPointML.

    This is a snippet of my powerpointML in slide1.xml:

    <am3d:objViewport viewportSz="5418666"/>

    This element sits within <a:graphic> and <am3d:model3d>.

    The definition of viewportSz in video2.skills-academy.com is: An ST_PositiveCoordinate ([ISO/IEC29500-1:2016] section A.4.1) attribute that specifies the size of the square viewport that contains the full field of view. The size of the viewport is used to update the size of the graphicFrame to fit the visible portions of the scene. This viewport is centered around the look-at point.

    I am not sure what that means in a mathematical sense, does it depend on the width and height of the shape? do you know how I can find this if I have the width and height of the shape in mm in which the GLB object will sit?

    Thank you! :)

    Jad


  3. jad maqdah 21 Reputation points
    2022-12-02T14:36:22.33+00:00

    Hi @Hung-Chun Yu

    Thank you very much for your answer! Yes, this helps alot.

    I now understand what the object viewport is, but still confused on how its size is calculated in the PowerPointML.

    Is there an equation I can use to find the answer depending on the shape properties of the model3d for example (cx, cy) or maybe any of the camera setting variables? I can never get it to the number that PowerPoint has, it's always either too zoomed in or too zoomed out.

    In my case, I programmatically choose the model3d shape properties (cx, cy), calculate all the required camera settings (which I get identical to those of PowerPoint) but still unsure what equation to use for calculating viewportSz.

    Thank you,
    Jad Maqdah

    0 comments No comments

  4. Hung-Chun Yu 976 Reputation points Microsoft Employee
    2022-12-02T05:34:09.86+00:00

    Hi @jad maqdah

    Here is what I find:

    The camera settings (type CT_Model3DCamera) specify where the camera is relative to the 3D model, in 3D space, and what it is looking at. These settings alone describe how much of the model is visible, and how the scene the camera is pointing at will be captured on a Projection plane. This camera output image can also be described as the front clipping plane of a Viewing Frustum. The output of the 3D camera in Office is always square.

    In a typical 3D view (for example, in a 3D game or a CAD program), the camera’s output fills a full window. But in Office, the 3D model is being composited/embedded on a 2D document surface. The properties you are asking about are defining how the camera output is mapped to this 2D document surface.

    A 3D Model in Office can be in either “Object Mode” (the model is not clipped as it is rotated, and the 2D rectangular selection box around the model expand or shrink to be larger than the model) or “Window Mode” (the model is clipped to a fixed-size rectangular selection box). Object Mode is the default for newly inserted 3D Models, but you could also programmatically build models that are in Window mode.

    The objViewport element is used in Object Mode, and its viewportSz attribute describes the size of a square, in document units, that the camera output will be mapped to. The “look at point” of the camera will always be mapped to the center of this square. And this square itself is always centered in turn on the center of the Model3D shape (these shape properties are defined in element spPr of type CT_Model3D).

    The units for viewportSz are in EMUs (defined here), which are super-high-resolution units; you can divide by 914400.0 to convert to inches. This is the same unit space used to define most other 2D graphical shapes in Office. It is possible to zoom the 3D model in/out by making viewportSz larger/smaller. But you probably want your camera settings (CT_Model3DCamera) to define a viewing frustum fully contains your 3D model without having much buffer.

    Note that Office should honor the viewportSz and other XML settings of a 3D model when a document is first loaded and drawn. But when a customer interacts with model through UI, Office will update the 3D settings. It is probably obvious that the “pan” and “zoom” UI change the camera position and FOV, respectively. It is less obvious that:
    • When pan or zoom are used, the 3D model will switch from Object mode to Window mode.
    • If a customer drags the bounding box handles that are around the model, the viewportSz will be re-calculated so that the camera output can be mapped to a different-sized area on the document.
    • When a 3D model is rotated, Office may recalculate viewportSz, but typically the newly calculated viewportSz is very close to the last value, sans some math roundoff errors…I notice rotation can cause viewportSz to jump around by about 1 EMU.

    I hope this helps!

    0 comments No comments