InTouch Web Client Show/Hide Tags Button Not Working
Symptom: In an AVEVA (formerly Wonderware) InTouch deployment, a "Show/Hide tags" button placed on a project window (commonly stored in a shared library such as @Buttons11.PDL) toggles correctly on OS Clients and OS Servers but stops responding after a small number of clicks when the same window is opened through the InTouch Web Client. After the failure, all instruments on the page render without tag overlays, and the button no longer toggles state. The button is implemented through internal (memory) tags that drive object visibility on the graphics page.
This article documents the root cause (memory tag scope mismatched to the web client execution model), the architectural constraints of the InTouch Web Client, the correct tag scoping rules, and a verified procedure to restore toggle behavior across all web client sessions.
1. Problem Summary and Environment
| Item | Observed Value |
|---|---|
| Affected component | InTouch Web Client (browser-hosted thin client served by InTouch Web Server over IIS) |
| Affected feature | Show/Hide tags toggle (visibility of tagname overlay on instruments) |
| Symptom location | OS Server + Web Client, OS Client + Web Client, remote Web Client browsers |
| Symptom not present on | Native OS Client (InTouch WindowViewer), OS Server console |
| Failure mode | Button works for 2-5 clicks, then state sticks or all tags disappear |
| Commonly affected files |
@Buttons11.PDL, *.PDL windows using tagname overlay |
2. Root Cause Analysis
The InTouch Web Client executes a thin-client session against the WindowViewer logic running on the Web Server host. Unlike native WindowViewer sessions, every web browser tab is a stateless HTTP/ASP.NET session that maps onto a single shared in-memory tag namespace on the Web Server. Memory (internal) tags in InTouch are scoped as one of two types:
- Shared (Project-wide): The tag value is part of the project database and is the same value for every InTouch runtime process connected to that project. Updates propagate to all I/O servers, clients, and web sessions.
- Local (Memory-mapped, client-only): The tag value exists in the local WindowViewer process of each client. Each client has its own independent copy and updates are not distributed.
The Show/Hide tags button is almost always implemented with one or more internal tags that store the current toggle state (for example, ViewTag, bShowTag, TagVisible). When those tags are configured as Shared, the same value is visible to all web clients and the native OS clients. The failure emerges from the following sequence:
- User A clicks the button in a web browser tab. The shared memory tag flips to
1and the visibility animation runs. - The web client re-establishes its session, or a polling cycle resets the transient UI script, and the shared tag is read back as
0by the WindowViewer on the web host. - Two competing write paths (one from the button script, one from the synchronization logic on the web host) clobber the shared value, leaving the tag in an undefined state and the visibility expression evaluating to FALSE for all overlays.
- Subsequent clicks no longer produce a visible state change because the underlying tag is being overwritten faster than the user-driven script can set it.
Native OS Clients do not exhibit the failure because each WindowViewer has its own process, and the shared tag value is only being driven by a single client at any moment. Web clients multiplex through one Web Server process, which is the conflict point.
3. InTouch Web Client Architecture
Understanding the runtime topology is required to make the fix durable.
Key architectural rules:
- Only the OS Client hosting the Web Server runs the Web Client web application. Web browsers never connect to the OS Server directly.
- The Web Server process is multiplexed: every browser tab is a logical session that reuses the same underlying WindowViewer on the Web Server host.
- Memory tags of scope Local are stored in the WindowViewer process of the client runtime. For a web session, the client runtime is the Web Server host, so all web sessions share the same Local memory unless the runtime is partitioned per session.
4. Internal Tag Scope Configuration
The fix requires that any tag used as a per-user or per-view state holder be marked Local, and that scripts reference it through the @local:: namespace.
| Tag Category | Tagname Dictionary (DB) field | Recommended Scope for Show/Hide State |
|---|---|---|
| Memory tag (integer/discrete) | Access Name = (none / Memory) |
Local with @local::TagName reference |
| Memory tag (integer/discrete) | Access Name = (none / Memory) | Shared only if every client must display the identical toggle state |
| I/O tag (PLC/DCS) | Access Name = PLC/DCS topic | Never used for UI toggle state |
| System tag | n/a (built-in) | Use $ShowTag only if you want the built-in global overlay; not per-view |
4.1 Setting a tag to Local in WindowMaker
- Open WindowMaker and select Special > Tagname Dictionary (or Configure > Tagname Dictionary depending on build).
- Select the tag driving the visibility expression (typical names:
View_tag,ShowTags,bTagVis). - In the Tag form, change Scope from Shared to Local. The field is a radio / drop-down under the tag's Type & Scope group.
- Click Save. WindowMaker warns that Local tags are not distributed to other nodes; acknowledge.
- Re-save the project database (the
.DBfile). The change only takes effect at runtime after a clean restart of WindowViewer on every client.
4.2 Referencing a Local tag from a script or animation
When the tag is Local, the script and any animation link must use the @local:: prefix, or the runtime will resolve the wrong copy and silently fall back to a zero value.
// Quick script attached to the Show/Hide tags button
// Toggles the local visibility state and re-applies it to all overlays
IF @local::View_tag == 0 THEN
@local::View_tag = 1;
ELSE
@local::View_tag = 0;
ENDIF;
// Force re-evaluation of the visibility expression on all selected instruments
// (select-all-in-window pattern)
INTEGER i;
FOR i = 1 TO 200 DO
// Replace MyObjectPrefix with the user-defined animation tag prefix used
// for the tagname visibility expression, e.g. TagVisObj01 .. TagVisObj200
// Each object reads @local::View_tag, so the toggle is independent per session
END_FOR;
If the script is attached to a window-script or a button's Action property under On Mouse Click, the same @local:: reference must be used. Do not mix the prefix with a non-prefixed reference in the same script.
5. Step-by-Step Resolution
Prerequisites
- Full Administrator rights on the development station, the Web Server host, and the OS Server.
- InTouch development license on the engineering station.
- Read access to the project directory on the OS Server for the live
.DBfile. - Stop the WindowViewer on every node before modifying the tag dictionary (to avoid the DB out of sync warning).
Procedure
-
Identify the toggle tag. Open the affected
.PDL(for example@Buttons11.PDL) in WindowMaker. Inspect the button's On Mouse Click quick script and the visibility expression on the instruments. Note the tag name used as the visibility driver (typical:View_tagorShowAllTags). - Change the tag scope to Local. Open Special > Tagname Dictionary, locate the tag, set Scope = Local, and save.
-
Update all references to use
@local::TagName. In every script, animation link, and indirect tag reference that touches the toggle tag, prepend@local::. Use Find & Replace across all.PDLfiles in the project to catch orphan references (search stringView_tagin WindowMaker's script editor). -
Save and validate. In WindowMaker, run File > Validate on every
.PDLthat referenced the tag. A reference without the@local::prefix produces a warning that the tag cannot be found at runtime. -
Rebuild and re-publish. In the Publish to Web wizard, mark the modified
.PDLfiles for incremental publish. The wizard generates the corresponding web-rendered views and the*.wdgtartifacts used by the web client. This step is required only when the affected window is in a published set. -
Restart the Web Server host. Restart WindowViewer on the OS Client that hosts the Web Server, then restart the IIS application pool (
iisreset /restartfrom an elevated command prompt). This forces the Web Server to load the updated.DBand the new.PDLcache. -
Reload the browser tab. Hard refresh (
Ctrl+Shift+R) every web client to clear the cached.PDLfragment. - Verify in native WindowViewer first. Confirm the button still works on a native OS Client connected to the OS Server, then verify on the Web Client.
6. Redundant OS Server + Single Web Server Topology
The deployment pattern matters: a single Web Server connected to a redundant pair of OS Servers is fragile because the standby OS Server does not serve web sessions, and a switchover drops the in-flight Web Client state. The supported, field-proven pattern is to install the Web Server on the OS Client that participates in the redundant pair's active view, not on a third dedicated machine.
| Topology | Publish Required | Switchover Behavior | Recommendation |
|---|---|---|---|
| Dedicated Web Server (3rd host) + redundant OS Server pair | Per OS Server, twice (primary and standby) | Web sessions drop on failover; reconnection window of 30-90 s | Avoid for Show/Hide and other Local-state features |
| OS Client hosts the Web Server + redundant OS Server pair | Once (the Web Server is the active OS Client) | OS Client's local tag copy persists on the same node | Preferred for Local-state UI features |
| OS Client as Web Server + single OS Server | Once | No redundancy needed for web sessions | Simplest for small plants |
For the recommended topology (OS Client = Web Server):
- Install the InTouch Web Server component on the OS Client node during the InTouch setup. Select Custom and enable Web Client.
- Configure the OS Client in the InTouch Node Properties dialog to point to the OS Server cluster. The OS Client is the redundant pair's view client; it does not host shared memory, only its Local copy.
- Publish once from WindowMaker on the engineering station, selecting the OS Client node as the publish target. The wizard copies the published artifacts to the Web Server's InTouch Web Client publication directory.
- Confirm IIS has a dedicated application pool for the InTouch Web Client, with Idle Timeout = 0 and Recycling disabled during operational hours. Idle timeouts reset the Web Server's in-memory state and re-introduce the same symptom.
7. Verification Procedure
After applying the fix, perform these checks before declaring the issue resolved.
- Open the published page in two different web browsers on two different PCs. Click the Show/Hide tags button 20 times in each. Tags should toggle correctly in each browser independently of the other.
- Open a native OS Client WindowViewer and the Web Client side by side. Toggle in one, confirm the other is unaffected (because the tag is now Local, the two runtimes no longer share the toggle state).
- Force a redundant OS Server switchover (use the OS Server Control Panel or the engineering utility that promotes the standby). Verify the Web Client sessions reconnect within 60 s and the button still responds.
- Inspect the InTouch diagnostic log (
wwLogger.login the InTouch install directory) for any "Tag not found", "DB out of sync", or "Tagname Dictionary mismatch" entries. The log should be free of these for the toggle tag. - From an elevated command prompt on the Web Server host, run
iisreset /statusand confirm the InTouch application pool is Started. Then runtasklist /FI "IMAGENAME eq wwindow.exe"to confirm the WindowViewer process is running on the Web Server host. - Re-publish the affected
.PDLfiles from a clean state: in the Publish to Web wizard, choose Remove all, then Add all and re-publish. This clears stale cached fragments in the Web Client publication directory.
8. Troubleshooting Matrix
| Symptom | Likely Cause | Action |
|---|---|---|
| Button works 2-3 times then stops | Toggle tag is Shared, web session state clobbered | Change tag scope to Local, use @local::
|
| Tags disappear but button still clicks | Visibility expression references the shared tag without @local:: prefix |
Update all animation links to use @local::View_tag
|
| Works on OS Client, fails on Web Client only | Web Server on dedicated host, no Local tag persistence per session | Move Web Server onto the OS Client host |
| Works on Web Client briefly, breaks after IIS app pool recycle | IIS idle timeout or recycle kills Local memory | Set Idle Timeout = 0, disable periodic recycling |
| All web clients toggle identically | Tag still Shared across web sessions on the same Web Server host | Verify tag scope is Local in the live .DB, restart WindowViewer |
| Tags flicker on/off continuously | Script writes the tag from two places (e.g., quick script + animation link) | Use a single writer; read-only on the animation link side |
| Tags show once on page load, then disappear | Initial value of @local::View_tag is 0 and a startup script forces 0 |
Initialize the Local tag in Window Script > On Show explicitly |
| Web Client shows blank page | Published artifacts missing or stale | Re-publish the affected .PDL from the Publish to Web wizard |
| Button missing entirely in Web Client | Wizard button was not on a published window or symbol | Confirm the host .PDL is in the published set |
| DB out of sync warning at startup | WindowViewer on Web Server host loaded a stale .DB
|
Stop WindowViewer, copy the latest .DB, restart |
9. Additional Notes
.DB on the OS Server. They live in the WindowViewer process memory of each client. If you back up only the OS Server's project directory, you will not preserve Local tag initial values; document any required default values in Window Script > On Show or in a startup quick script.
.PDL fragments aggressively. After any tag or script change, perform a hard refresh (Ctrl+F5) and, if necessary, clear the browser cache for the Web Client host name. A stale cached fragment will continue to use the old script even after the server is updated.
For broader information on tag visibility configuration and display cues in AVEVA Plant SCADA and InTouch graphics, refer to the AVEVA documentation set on tag display and object visibility.
10. FAQ
Why does the Show/Hide tags button work on the OS Client but not the Web Client?
The button is driven by a memory tag. When the tag is configured as Shared, all web sessions multiplexed through the same Web Server WindowViewer overwrite each other and the state is lost after a few clicks. Native OS Clients each have their own WindowViewer process, so the conflict does not occur.
What is the correct way to make a per-view toggle state work in the Web Client?
Set the driving tag's scope to Local in the Tagname Dictionary and reference it as @local::TagName in every script, animation link, and visibility expression. The Local copy is held in the Web Server's WindowViewer process and is not synchronized to other nodes.
How many publishments are required for one redundant OS Server and one Web Server?
One publishment, provided the Web Server runs on the OS Client that participates in the redundant pair's active view. If the Web Server is on a third dedicated machine, publish twice (once for each OS Server) and accept the switchover reconnection window.
Does changing the tag scope to Local require updating every script that references it?
Yes. Any reference that does not use the @local:: prefix will fail to resolve the Local copy at runtime. Use WindowMaker's Find & Replace across the project to update all references in one pass, then run File > Validate to catch stragglers.
Why does the button break again after an IIS application pool recycle?
Local memory tags live in the WindowViewer process tied to the IIS application pool. When the pool recycles (idle timeout, periodic recycle, or manual iisreset), the in-memory Local tag values are reset. Disable periodic recycling and set the idle timeout to 0 to keep the state alive.