A Microsoft extension to the ANSI SQL language that includes procedural programming, local variables, and various support functions.
You first need to unpivot the fields and then pivot on the date:
; WITH unpiv AS (
SELECT a.ID, a.date, V.name, V.value
FROM @data a
CROSS APPLY (VALUES ('Field1', a.Field1),
('Field2', a.Field2),
('Field3', a.Field3),
('Field4', a.Field4)) AS V(name, value)
)
SELECT ID, name,
MIN(CASE date WHEN '10/07/21' THEN value END) AS [10/07/21],
MIN(CASE date WHEN '19/06/21' THEN value END) AS [19/06/21],
MIN(CASE date WHEN '29/05/21' THEN value END) AS [29/05/21]
FROM unpiv
GROUP BY ID, name
Now, I can guess that you will say that the dates can be dynamic, both in values and in how many dates there are. But a query in SQL always returns a fixed number of columns with fixed column names. You can build a query dynamically, but before there, you should ask yourself, if this operation can be performed better elsewhere. A dynamic pivot is a presentational device, and may be better performed in the presentation layer.
By the way, while this is just a demo table, I still like to point out that storing dates in string columns is a exquisitely bad idea, and is very likely to cause you trouble.