WinCC C Script: Update Picture Window on Tag Change

David Krause11 min read
HMI / SCADASiemensTutorial / How-to
Licensed PE Working through this on a live machine? A Maine-licensed engineer can take it from here — included with IMD hardware, by the hour for everything else. Book an engineer

Overview

Siemens WinCC (TIA Portal and WinCC V7.x) picture windows let a single display container host multiple faceplates, but a common engineering problem is that graphics inside the picture window fail to refresh until the window is closed and reopened. The root cause is almost always a polling-based update cycle combined with a property binding that only re-evaluates when the container is reloaded. This reference covers three C-script and one VBS approach for forcing immediate picture updates, and explains how to consolidate start/stop controls into one reusable faceplate that drives any motor or valve tag.

Prerequisites

  • Siemens WinCC Professional (TIA Portal V16 or later) or WinCC V7.4 SP3 / V7.5 with the C scripting option enabled
  • Configured PLC connection tags (e.g. Motor1_state, Motor1_ctrl)
  • One source PDL containing the picture window object and one or more faceplate PDLs (e.g. start.pdl, motor.pdl, valve.pdl)
  • Knowledge of the project's tag naming convention; this guide assumes a <TAG>_state and <TAG>_ctrl pair
  • WinCC Graphics Designer with the C compiler configured (Project Properties > Options > C-Script Compiler)

Understanding the Update Cycle Problem

Picture window content refresh is tied to the configured update cycle of the host picture. When an internal tag drives a dynamic property (such as the PictureName property of a Picture Window), the property is only re-evaluated when the host picture's update event fires. If the update cycle is set to a fixed interval (e.g. 1 s) and the tag is also a polled value, a change of value will not be visible until the next cycle boundary. Configuring the update to Upon change is supported for picture-level update events, but only triggers a repaint of objects that have their own dynamic bindings; picture windows reloading their PictureName still depend on the host picture's redraw.

Engineering note: The C-script Upon change trigger fires on a tag value transition, not on a graphical property transition. To repaint a child picture window when a bit changes, you must explicitly invoke a property-write from a C action tied to the tag, not rely on the picture's update event alone.

C Script API for Picture Window Control

WinCC exposes the following C functions for picture window manipulation. All three are declared in the project header and resolve at compile time.

Function Purpose Typical Use
SetPropChar() Writes a string to a property of a named object in a named picture Change picture name, visibility, or caption of a picture window from a C action
SetTagPrefix() Sets the tag namespace prefix used to resolve SetTagWord() etc. within a function Switch the active tag prefix when a button click selects a different motor
SetPictureName() Loads a new PDL into a picture window at runtime Open a different faceplate PDL inside the picture window
SetTagChar() Writes a string value to a WinCC tag Drive a PictureName binding that is connected to an internal text tag
GetTagChar() Reads a string value from a WinCC tag Build dynamic tag names from a current selection

Method 1: SetPropChar Function

The most direct approach. Declare the function with its full prototype and call it from a button click event or a tag-change C action.

Function prototype:

void SetPropChar(LPCTSTR lpszPictureName, LPCTSTR lpszObjectName, LPCTSTR lpszPropertyName, char* szValue);

Example call from a button's C action:

SetPropChar("butexam.pdl", "mainpw", "PictureName", "pict1.pdl");

Where:

  • butexam.pdl - the host picture containing the picture window
  • mainpw - the name of the picture window object inside that picture
  • PictureName - the property of the picture window to modify (string)
  • pict1.pdl - the target faceplate to load into the picture window

To also toggle visibility (required if the picture window was hidden), chain a second call:

SetPropChar("butexam.pdl", "mainpw", "Visible", "1");
Case sensitivity: PDL filenames and object names are case-sensitive. Mismatched casing causes the function to return silently with no error dialog. Always verify with the WinCC Tag Simulation runtime before assuming the function failed.

Method 2: Internal Text Tag for PictureName

This is the cleanest approach for projects that use the picture window as a faceplate host. It removes the need to call SetPropChar from a button; the picture window's PictureName property is bound to an internal text tag and updated from any C action via SetTagChar.

Step-by-Step

  1. In the Graphics Designer, create an internal text tag named SelectedFaceplate.
  2. Select the picture window object, open the Miscellaneous folder in the Properties dialog, and assign SelectedFaceplate to the Picture Name attribute.
  3. From any button C action, write the desired PDL name to the tag:
    SetTagChar("SelectedFaceplate", "motor1.pdl");
  4. To close the faceplate, write an empty string:
    SetTagChar("SelectedFaceplate", "");

This method is recommended for production code because it allows both manual and tag-driven faceplate selection without C recompilation, and it survives Hot-Build cycles in TIA Portal V17 and later.

Method 3: SetTagPrefix and SetPictureName Pair

Use this approach when a button or script must load a different picture in the picture window without disturbing other parts of the runtime. The classic two-line pattern is:

SetTagPrefix("start.PDL", "overview", "");
SetPictureName("start.PDL", "overview", "my.PDL");

Where:

  • start.PDL - the source picture that contains the picture window
  • overview - the name of the picture window object
  • my.PDL - the destination faceplate to load

SetTagPrefix establishes the tag-resolution context for the subsequent calls in the same function. If the picture window is being driven by a tag prefix that differs from the current project prefix (common in multi-area projects), call SetTagPrefix first to avoid runtime errors caused by tag resolution failures.

VBScript Alternative for Runtime Tag Manipulation

For purely button-driven flows (clicking a motor icon to write the selected tag name), VBScript inside the Graphics Designer is often faster to author than C. The pattern below implements a reusable motor control faceplate driven by a single internal 8-bit text tag POSITIO:

Sub OnClick(Byval Item)
    Dim mtrtag1
    Set mtrtag1 = HMIRuntime.ActiveScreen.ScreenItems("mtr1text")
    Dim mtrtag2
    Set mtrtag2 = HMIRuntime.Tags("POSITIO")
    mtrtag2.Write mtrtag1.Text
End Sub

The companion control faceplate's START button reads the selection and appends a suffix to build the target control tag dynamically:

Sub OnClick(Byval Item)
    Dim positio, strConc, ctrl
    Set positio = HMIRuntime.Tags("POSITIO")
    positio.Read
    strConc = positio.Value & "_ctrl"
    Set ctrl = HMIRuntime.Tags(strConc)
    ctrl.Write "1"     ' write start command
End Sub

The _ctrl and _state suffix convention is the standard way to consolidate N motor/valve faceplates into one physical picture window, provided every tag in the project follows the same naming rule.

Reusable Faceplate Pattern

Combining the above techniques yields a single faceplate that can drive any motor in the plant:

  1. One central picture motor_control.pdl contains a picture window named PWMotor and a START / STOP button pair.
  2. The picture window's PictureName property is bound to internal text tag SelectedFaceplate.
  3. When a user clicks a motor icon in any overview screen, a C action writes the motor's base tag name (e.g. Motor3) to SelectedFaceplate, which loads motor_zoom.pdl into the picture window.
  4. The START button reads Motor3, appends _ctrl, and writes the start command; the STOP button writes the stop command to the same tag.
  5. Status displays (text, color, animation) inside motor_zoom.pdl are bound to Motor3_state and refresh on the standard 250 ms update cycle.

This pattern is what allows one physical faceplate to control all motors in the plant, rather than maintaining N copies of the same PDL with hard-coded tag names.

Forcing a Refresh on a Bit Change

If a particular display element inside the picture window still does not repaint when the underlying bit changes, the cause is typically a property that is bound to a calculated expression rather than a direct tag. There are two proven fixes:

Fix A: Use SetTagChar to force a re-evaluation

// In a C action triggered on the tag change event of Motor3_state
char buf[64];
sprintf(buf, "%d", GetTagWord("Motor3_state"));
SetTagChar("Motor3_dispCache", buf);

Binding the display to Motor3_dispCache (a separate tag) instead of the direct source tag forces a value change that the Graphics Designer will repaint on the next update tick.

Fix B: Use SetPropChar to write the same value back

// On a tag change C action tied to the bit
char* prop = (GetTagBit("Motor3_state") ? "1" : "0");
SetPropChar("motor_zoom.pdl", "StatusIndicator", "ProcessValue", prop);

This bypasses the picture-level update event entirely and writes the new property value directly to the object.

Update Cycle Configuration

Property Path Recommended Setting
Picture update (general) Picture properties > Update > Cycle 250 ms for status, 1 s for non-critical
Picture update (events) Picture properties > Update > Events > Upon change Enable for bit-driven status
C action trigger Action configuration > Trigger > Tag change Bind to the source tag, not the display tag
Internal tag update Tag properties > Update Upon change for picture-name tags
Performance impact: Setting the global picture update to Upon change for high-frequency tags (greater than 1 Hz) may cause CPU spikes on WinCC Runtime Professional panels. For tag-change actions on tags faster than 500 ms, add a debounce internal tag or a time-delay C action.

Verification

  1. Compile the C action (Build > Compile All) and verify there are no warnings related to SetPropChar or unresolved tag references.
  2. Start WinCC Runtime and open the Graphics Designer with Tag Simulation enabled.
  3. Force the source tag to change with Tag Simulation; confirm the picture window content updates within one update cycle (default 250 ms).
  4. Click each motor icon and verify the picture window loads the correct faceplate PDL, then click START and confirm the corresponding <TAG>_ctrl writes the expected value.
  5. Inspect the WinCC Diagnostic Viewer (ApDiag.exe) for any SETPROPCHAR errors; a return code other than zero indicates an invalid PDL name or object name.
  6. Stress-test by cycling the source tag at 2 Hz for 60 seconds; the picture window must not drop updates or freeze.

Troubleshooting Matrix

Symptom Likely Cause Corrective Action
Picture window does not load new PDL on button click Wrong object name or picture name in SetPropChar call Verify spelling and case in the Graphics Designer; use Tag Simulation with logging
Status display updates only after closing and reopening the faceplate Display bound to a calculated expression with static caching Bind to a dedicated internal cache tag; use Fix A above
VBScript error: "Object variable not set" on HMIRuntime.Tags(...) Internal tag not declared or has wrong data type Confirm the tag exists in WinCC Explorer; use 8-bit text type for tag name variables
Tag change C action fires but picture does not repaint Trigger tag is correct but the action writes to a property that is not dynamic Enable the dynamic flag on the target property in the Properties dialog
Picture window loads but contains stale data Picture-level update cycle is set too long for the source tag Lower the host picture update cycle to 250 ms or use a tag-change action
High CPU on runtime when using Upon change Source tag changes faster than 1 Hz Add a debounce internal tag, or switch to a fixed 250 ms cycle

Field-Commissioning Checklist

  • Confirm the C compiler is installed and the project options point to a valid WinCC include directory (typically C:\Program Files\Siemens\Automation\WinCC\aplib\include).
  • Document the tag naming convention (<TAG>_state / <TAG>_ctrl) in the project HMI tag dictionary.
  • For every picture window, decide whether the binding will be to an internal text tag (Method 2) or to a direct C action (Method 1) and document the choice.
  • Run the full picture-change scenario on the target runtime (PC Runtime or Comfort Panel) before PLC integration, to isolate HMI defects from PLC defects.
  • Capture the WinCC version in the project notes; the function signatures are stable from WinCC V7.0 onward, but the TIA Portal V16+ project tree stores them in Scripts\Libraries\WinCC\apdefap.h.

How do I change the update cycle to "Upon change" in a WinCC C script?

Open the picture properties in the Graphics Designer, navigate to the Update tab, and set the cycle to Upon change. For C actions that must trigger on a tag transition, configure the action's trigger as a tag-change event bound to the source tag; the action then fires whenever the tag value changes, regardless of the picture update cycle.

Why does my picture window content not update until I close and reopen it?

Most often the display property is bound to a calculated expression or to a tag whose update cycle does not match the source tag's cycle. Bind the display to a dedicated internal cache tag and write to it from a tag-change C action, or use SetPropChar to write the new property value directly to the named object.

Can one faceplate control all motors in the project?

Yes. Use a single picture window with its PictureName property bound to an internal text tag. When the operator clicks a motor icon, write the motor's base tag name to the internal text tag and load a generic motor_zoom.pdl. The faceplate's start/stop buttons read the base tag, append _ctrl or _state, and write the command or read the status, allowing N motors to be driven from one physical faceplate.

What is the difference between SetPropChar, SetTagPrefix, and SetPictureName?

SetPropChar writes a property value to a named object in a named picture and is the most general-purpose function. SetTagPrefix sets the tag namespace context for the current C function. SetPictureName directly loads a new PDL into a picture window and is the most concise when only the picture content needs to change. Use SetTagPrefix + SetPictureName together when the active tag prefix is not the project default.

Does this work in TIA Portal WinCC Professional the same as WinCC V7?

Yes, the function signatures and usage are identical between WinCC V7.x and TIA Portal WinCC Professional V16+. The only differences are project tree location (TIA stores scripts under PLC_1\HMI_1\Scripts) and the absence of the legacy VBScript compatibility shim on TIA V17+ projects targeting S7-1500 panels.

Back to blog