MCPcopy Index your code
hub / github.com/simstudioai/sim / resolveGradient

Function resolveGradient

apps/sim/lib/pptx-renderer/renderer/style-resolver.ts:431–501  ·  view source on GitHub ↗

* Parse a gradient fill into a CSS gradient string.

(
  gradFill: SafeXmlNode,
  ctx: RenderContext,
  placeholderColorNode?: SafeXmlNode
)

Source from the content-addressed store, hash-verified

429 * Parse a gradient fill into a CSS gradient string.
430 */
431function resolveGradient(
432 gradFill: SafeXmlNode,
433 ctx: RenderContext,
434 placeholderColorNode?: SafeXmlNode
435): string {
436 // Parse gradient stops
437 const gsLst = gradFill.child('gsLst')
438 const stops: { position: number; color: string }[] = []
439
440 for (const gs of gsLst.children('gs')) {
441 const pos = gs.numAttr('pos') ?? 0
442 const posPercent = pctToDecimal(pos) * 100
443 const { color, alpha } = resolveColorWithPlaceholder(gs, ctx, placeholderColorNode)
444 stops.push({ position: posPercent, color: toCssColor(color, alpha) })
445 }
446
447 if (stops.length === 0) {
448 return ''
449 }
450
451 // Sort stops by position
452 stops.sort((a, b) => a.position - b.position)
453
454 const stopsStr = stops.map((s) => `${s.color} ${s.position.toFixed(1)}%`).join(', ')
455
456 // Determine gradient type
457 const lin = gradFill.child('lin')
458 if (lin.exists()) {
459 const angle = angleToDeg(lin.numAttr('ang') ?? 0)
460 // OOXML angle 0 = top-to-bottom in the gradient coordinate system
461 // CSS angle 0 = bottom-to-top, so we need to adjust
462 const cssAngle = (angle + 90) % 360
463 return `linear-gradient(${cssAngle.toFixed(1)}deg, ${stopsStr})`
464 }
465
466 const path = gradFill.child('path')
467 if (path.exists()) {
468 const pathType = path.attr('path')
469 if (pathType === 'circle' || pathType === 'shape' || pathType === 'rect') {
470 // OOXML path gradients: stop pos=0 = fillToRect center, pos=100000 = shape edge.
471 // CSS radial-gradient: 0% = center, 100% = edge.
472 // Conventions match — no reversal needed.
473
474 // Resolve fillToRect center point
475 const ftr = path.child('fillToRect')
476 let cx = 50
477 let cy = 50
478 if (ftr.exists()) {
479 const l = (ftr.numAttr('l') ?? 0) / 100000
480 const t = (ftr.numAttr('t') ?? 0) / 100000
481 const r = (ftr.numAttr('r') ?? 0) / 100000
482 const b = (ftr.numAttr('b') ?? 0) / 100000
483 cx = ((l + (1 - r)) / 2) * 100
484 cy = ((t + (1 - b)) / 2) * 100
485 }
486
487 if (pathType === 'rect') {
488 // Rectangular gradient (L∞ norm / Chebyshev distance): creates cross/X contour

Callers 2

resolveFillFunction · 0.85

Calls 11

pctToDecimalFunction · 0.90
toCssColorFunction · 0.90
angleToDegFunction · 0.90
childMethod · 0.80
childrenMethod · 0.80
numAttrMethod · 0.80
joinMethod · 0.80
existsMethod · 0.80
attrMethod · 0.80
pushMethod · 0.45

Tested by

no test coverage detected