Writing Individual Bits in a Word Tag with WinCC HMI Buttons

David Krause12 min read
HMI ProgrammingSiemensTutorial / 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

1. Problem Overview

Engineers commissioning a Siemens SIMATIC HMI frequently need to expose a single PLC word (for example DB10.DBW0 with the symbolic name Steuerbits) as a panel of sixteen discrete switches. The PLC only allocates one WORD of memory, but the operator needs to read and toggle every single bit independently. The naive approach—binding each of the sixteen buttons to a separate %DB10.DBX0.0...%DB10.DBX1.7 address—works for read access but does not work for write access on a Word tag, because the HMI writes the entire 16-bit value atomically and overwrites sibling bits.

This reference covers the three production-grade patterns that solve the problem inside Siemens TIA Portal / WinCC V7 environments:

  1. CheckBox Control bound to the Word process tag with bit index.
  2. Operator button with VBScript using HMIRuntime.Tags.SysFct.SetBitInTag and ResetBitInTag.
  3. Compound approach with global tags and an auxiliary script that updates only the target bit.

Byte-swap and endianness pitfalls (the reason a bit-toggle sometimes lights the wrong LED) are documented in §6.

2. Word Tag Architecture and Bit Addressing

A 16-bit WORD consists of two BYTEs: the high byte holds bits 8–15 and the low byte holds bits 0–7. In SIMATIC S7 nomenclature the lowest address is always the low byte:

Bit Index Byte Absolute Address Symbolic (example)
0 Low (byte 0) %DB10.DBX0.0 Steuerbits.Bit0
1 Low (byte 0) %DB10.DBX0.1 Steuerbits.Bit1
7 Low (byte 0) %DB10.DBX0.7 Steuerbits.Bit7
8 High (byte 1) %DB10.DBX1.0 Steuerbits.Bit8
15 High (byte 1) %DB10.DBX1.7 Steuerbits.Bit15

WinCC Runtime stores the WORD in a single HMI tag, but it stores individual bit addresses as overlay tags of the same memory. Bind the HMI tag as:

  • Data type: WORD (UInt)
  • PLC tag: the 16-bit word in the controller data block
  • Acquisition mode: Cyclic in operation (default 1 s) for visibility, Event-driven for bit toggles

For the HMI to be allowed to write the tag, the PLC connection must include operator authorization for that area. The PLC block typically looks like this in SCL:

FUNCTION_BLOCK FB_ControlWord
VAR
    bSteuerbits : WORD;   // HMI writes, logic reads
END_VAR
bSteuerbits := 0; // initialise at first scan if needed
// Use bSteuerbits.X0..bSteuerbits.X15 in the program

3. Method 1 — CheckBox Control Bound to the Word Tag (Recommended)

The CheckBox graphic object inside the WinCC screen designer accepts a single 16-bit process tag and exposes a BitIndex property (0–15). When the operator clicks a checkbox, Runtime reads the current WORD, sets/clears the selected bit, and writes the WORD back to the PLC atomically. Sibling bits are never disturbed. Visual feedback is automatic: a checked box equals 1, unchecked equals 0.

3.1 Configuration Steps

  1. Open the WinCC screen in the TIA Portal graphics designer (or WinCC V7 Graphics Designer).
  2. Drag a CheckBox from the toolbox onto the screen.
  3. Repeat fifteen times so you have exactly sixteen checkboxes, or use the CheckBox Group object (WinCC Unified) which produces all sixteen in a single control.
  4. For every checkbox:
    • Process tag → your HMI tag of type WORD, e.g. Steuerbits.
    • BitIndex → 0 for the first, 1 for the second, … 15 for the last.
    • BitNumbered → enable if you want the bit number printed in the label.
    • Tooltip → enter the human-readable function (e.g. "Pump 1 enable").
  5. Arrange the sixteen checkboxes in a 4×4 or 2×8 grid, optionally using the Layered arrangement feature for a clean layout.
  6. Compile and download to the Runtime.
Note: In WinCC Unified (V16+), the CheckBox Group control is the canonical implementation; it binds to a UInt16 process tag and accepts Bit0..Bit15 as member properties. See the Siemens WinCC Unified Help for the property schema.

4. Method 2 — Operator Button with VBScript and SetBitInTag

Where the design requires a tactile push-button (not a checkbox) you can attach VBScript to a Button object's Click event. WinCC Runtime exposes two dedicated bit-level helpers in the HMIRuntime.Tags.SysFct namespace:

Function Signature Behaviour
SetBitInTag SetBitInTag(ByVal TagName As String, ByVal Bit As Long) Sets the addressed bit to 1; all other bits of the tag are preserved.
ResetBitInTag ResetBitInTag(ByVal TagName As String, ByVal Bit As Long) Clears the addressed bit to 0; sibling bits are preserved.
ToggleBitInTag ToggleBitInTag(ByVal TagName As String, ByVal Bit As Long) Inverts the addressed bit.
GetBit GetBit(ByVal Value As Long, ByVal Bit As Long) As Boolean Returns the state of a single bit inside a value already read into the script.

The functions are documented in the Siemens WinCC V7 / WinCC Professional Scripting Reference under the VBScript reference manual. The function names and namespace match the COM automation model used by WinCC Runtime.

4.1 Toggle a Single Bit on Click

Add this VBScript to the Click event of a button labelled, for example, "Toggle Bit 15":

Option Explicit

Sub OnClick(ByVal Item)
    Dim sTag
    sTag = "Steuerbits"        ' HMI tag name (must exist in tag management)
    Dim iBit
    iBit = 15                  ' Bit number 0..15 for a WORD

    ' Read current value
    Dim hmiTag
    Set hmiTag = HMIRuntime.Tags(sTag)
    hmiTag.Read

    If (hmiTag.Value And (2 ^ iBit)) = 0 Then
        ' Bit is currently 0 → set it to 1
        HMIRuntime.Tags.SysFct.SetBitInTag sTag, iBit
    Else
        ' Bit is currently 1 → clear it to 0
        HMIRuntime.Tags.SysFct.ResetBitInTag sTag, iBit
    End If
End Sub

4.2 The Original Symptom — Wrong Bit Getting Set

The user reported the following call seemingly setting a bit other than bit 15:

HMIRuntime.Tags.SysFct.SetBitInTag "Steuerbits", 15

This is almost always a byte-swap symptom, not a bug in SetBitInTag. See §6 for the full root-cause analysis. The most common causes are:

  1. The same data is also written through a checkbox or by a separate script that re-orders the bits, causing the bit that is "set" to be displayed at a different visual index.
  2. Two HMI tags (Steuerbits on one connection, Steuerbits_HMI on another) point at adjacent or byte-swapped memory.
  3. OPC DA / OPC UA clients are reading the tag with reversed byte order (little-endian vs. big-endian).

To prove that the function itself is correct, run this diagnostic once and verify the result on the PLC (e.g. with VAT or a watch table):

Sub OnClick(ByVal Item)
    ' Force bit 15 ON and log
    HMIRuntime.Tags.SysFct.SetBitInTag "Steuerbits", 15
    HMIRuntime.Trace "Steuerbits = " & _
        Hex(HMIRuntime.Tags("Steuerbits").Value) & vbCrLf, _
        "BitDiag", 1
End Sub

If the trace line reads 0x8000 (i.e. bit 15 is set) and the PLC VAT confirms the same value, the script is correct and the issue is purely visual/byte-ordering.

5. Method 3 — Compound Approach with Internal Tags

For panels that need to perform bit-wise logic (e.g. "set bits 0, 3, 7 simultaneously") you can read the WORD into an internal HMI tag, manipulate it locally, and write it back. This is rarely needed for a simple toggle but is the most flexible pattern.

Sub OnClick(ByVal Item)
    Dim oTag, lValue
    Set oTag = HMIRuntime.Tags("Steuerbits")
    oTag.Read
    lValue = CLng(oTag.Value)

    ' Set bit 4, clear bit 5, toggle bit 6 in one transaction
    lValue = lValue Or (2 ^ 4)          ' Set bit 4
    lValue = lValue And Not (2 ^ 5)     ' Clear bit 5
    lValue = lValue Xor (2 ^ 6)         ' Toggle bit 6

    oTag.Value = lValue
    oTag.Write
End Sub

Always Read immediately before Write to avoid race conditions if other HMI clients are also writing the tag.

6. Byte-Swap and Endianness Pitfalls

SIMATIC S7 PLCs store multi-byte values in big-endian format (high byte first). WinCC Runtime, OPC DA servers, and most Windows-based visualisation tools can interpret the same WORD as little-endian when it crosses a PC-side boundary. The result is that bit 0 and bit 8 swap visual positions, and the user reports "I'm setting bit 15 but bit 14 lights up".

Cause Symptom Fix
Two tags configured on overlapping memory (e.g. one reads DBW0, another DBW2) Visual bit position does not match PLC Re-create tags, ensure unique addresses
OPC DA client connects to WinCC and reads the same tag in a different byte order External SCADA shows mirrored bits Force "Word swap" / "Motorola byte order" off in the OPC server
HMI tag bound as INT but data block declares WORD Sign bit (bit 15) reads as bit 0 in I/O field Change HMI tag type to UInt / WORD
Checkbox BitIndex shifted by 8 because designer assumes byte 0 is the high byte First eight checkboxes mirror last eight Use CheckBox Group (Unified) which auto-corrects; manually verify BitIndex in V7
Diagnostic tip: Add a numeric I/O field bound to the same HMI tag and display it in Hexadecimal. A value of 0x8000 means bit 15 is set; 0x0001 means bit 0. The diagnostic value stays correct regardless of checkbox layout, so it is the ground truth.

7. Configuration Reference Table

Parameter CheckBox Control VBScript Button Compound Script
Best for 16 independent on/off states Single-bit toggle, momentary action Multi-bit set/clear/toggle in one event
Visual feedback Automatic, per checkbox Manual (re-read tag and drive graphic) Manual
Atomicity Word-level, Runtime-managed Word-level, Runtime-managed Read-Modify-Write window (race risk)
Tag type WORD / UInt16 WORD / UInt16 WORD / UInt16
Bit range 0–15 0–15 0–15
Commissioning effort Low Medium High

8. S7-1200 / S7-1500 Symbol Exposure for HMI

When the source tag lives on an S7-1200 or S7-1500, expose the data block to the HMI connection:

  1. In TIA Portal, open the DB that contains Steuerbits as WORD.
  2. Right-click the DB → Properties → Attributes → tick "Accessible from HMI".
  3. Disable "Optimised block access" if the HMI is older than V14 or if the connection is S7-300/400 compatible.
  4. Drag the variable from the project tree into the HMI tag table; the type is preserved as WORD.
  5. Verify the symbolic bit accessors ("Steuerbits".X0...X15) by opening the DB and confirming the row is unchecked in "Not accessible from HMI".

Refer to the Siemens S7-1200 / S7-1500 System Manual for the canonical rules on optimised data blocks and HMI visibility. Word tags marked as non-optimised keep their byte order predictable for the HMI.

9. Verification and Commissioning Procedure

  1. Compile the HMI project (Build → Rebuild all) and resolve any tag errors. The tag table must show Steuerbits with the same name used in the script.
  2. Start the Runtime in simulation mode. The Tag Simulator should show Steuerbits starting at 0.
  3. Click each checkbox in turn. The corresponding bit LED on the simulated PLC should illuminate and the HMI tag value should switch between 0x0001, 0x0002, 0x0004, … 0x8000.
  4. Bind a numeric I/O field in Hex display. Set all sixteen checkboxes; the field must read 0xFFFF. Clear all; the field must read 0x0000.
  5. From a VAT / watch table on the PLC, write a value (e.g. W#16#1234) into the data block. The HMI checkboxes must reflect the binary breakdown 0001 0010 0011 0100 within one acquisition cycle.
  6. Test race condition: click two checkboxes in rapid succession. Both must end up in the requested state and the I/O field must match the value reported by the PLC.
  7. Test byte-swap scenario described in §6: temporarily change the HMI tag type to INT and observe the I/O field. Restore to WORD / UInt for production.

10. Troubleshooting Matrix

Symptom Likely Root Cause Action
Checkbox shows correct state but writing it does nothing HMI has no write privilege on the tag area Check PLC connection → Operator authorisations; add tag to a write-allowed area
Clicking a checkbox sets a different bit Byte-swap or duplicate tag address Bind a Hex I/O field to the same tag for ground truth; remove duplicate tag definitions
SetBitInTag returns no error but PLC value unchanged Tag name mismatch between script and tag management Confirm casing and namespace; use HMIRuntime.Tags("Steuerbits").Name in a trace
Two operators toggling the same bit overwrite each other Read-Modify-Write race in compound scripts Use SetBitInTag / ResetBitInTag instead of read-modify-write
Script error: "Object doesn't support this property or method" Calling SysFct from the wrong Runtime (Unified uses different API) For WinCC Unified use HMIRuntime.UI.SysFct or the JavaScript wrapper
All sixteen checkboxes appear pressed Wrong data type (DWORD interpreted as WORD) or signed-int sign extension Change HMI tag to UInt16 / WORD and reload Runtime
Button click toggles bit on the HMI but PLC stays at 0 PLC connection uses "Read only" put/get direction Change connection properties to "Read/Write" on the affected DB

11. Performance and Safety Notes

  • Avoid running SetBitInTag in a 100 ms cyclic script. Each call performs a Read-Modify-Write cycle on the HMI tag and round-trips to the PLC; excessive polling starves the S7 connection. Use event-driven acquisition.
  • Bit toggles via HMI should always go through authorised operator areas. Combine with SIMATIC Logon for traceability.
  • If the WORD drives safety-relevant outputs, treat the HMI as a non-safety interface. The PLC must contain its own plausibility checks (e.g. AND-mask of allowed bit combinations) before acting on the HMI word.
  • For 32-bit DWORDs the same APIs apply; the bit range becomes 0–31. Mind the byte-swap risk, which doubles.

Why does my checkbox write a different bit than I selected?

The most common reason is a duplicate HMI tag pointing at overlapping PLC memory, or the HMI tag being declared as INT instead of WORD/UInt16. Bind a numeric I/O field in Hex display to the same tag; if the hex value matches the PLC VAT, the script is correct and the issue is visual layout or a second tag definition.

Can SetBitInTag address bits 16–31 in a DWORD?

Yes. SetBitInTag and ResetBitInTag accept any bit index 0–31 when the HMI tag is a DWORD. Pass 16 for the lowest bit of the high word, 31 for the highest. Sibling bits are always preserved.

Does the CheckBox Control work in WinCC Unified the same as in WinCC V7?

The control is conceptually identical, but in WinCC Unified the VBScript namespace HMIRuntime.Tags.SysFct is replaced by the JavaScript / C# API HMIRuntime.UI.SysFct (or the unified Tags object). Use the CheckBox Group control in Unified for a single UI element that exposes all sixteen bits of a UInt16 process tag.

What is the safest method to write a single bit in a critical application?

Use the dedicated SetBitInTag / ResetBitInTag functions, which perform a read-modify-write atomically inside Runtime and preserve the other bits. Avoid raw Read-Modify-Write in custom scripts because they open a race window if two HMI stations write the same tag concurrently.

How do I display the bit state on the button face when using a script-driven button?

Bind the button's Pressed / Background flash property to the bit address (Steuerbits.Bit0 for bit 0, etc.) or use a separate graphic I/O field next to the button driven by the same bit. The CheckBox Control handles this automatically.

Back to blog