com.vaadin.server.communication.LegacyUidlWriter Maven / Gradle / Ivy
/*
* Copyright (C) 2000-2024 Vaadin Ltd
*
* This program is available under Vaadin Commercial License and Service Terms.
*
* See for the full
* license.
*/
package com.vaadin.server.communication;
import java.io.IOException;
import java.io.Serializable;
import java.io.Writer;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.logging.Logger;
import com.vaadin.server.ClientConnector;
import com.vaadin.server.LegacyPaint;
import com.vaadin.server.PaintTarget;
import com.vaadin.ui.Component;
import com.vaadin.ui.LegacyComponent;
import com.vaadin.ui.UI;
/**
* Serializes legacy UIDL changes to JSON.
*
* @author Vaadin Ltd
* @since 7.1
*/
public class LegacyUidlWriter implements Serializable {
/**
* Writes a JSON array containing the changes of all dirty
* {@link LegacyComponent}s in the given UI.
*
* @param ui
* The {@link UI} whose legacy changes to write
* @param writer
* The {@link Writer} to write the JSON with
* @param target
* The {@link PaintTarget} to use
* @throws IOException
* If the serialization fails.
*/
public void write(UI ui, Writer writer, PaintTarget target)
throws IOException {
Collection dirtyVisibleConnectors = ui
.getConnectorTracker().getDirtyVisibleConnectors();
List legacyComponents = new ArrayList<>(
dirtyVisibleConnectors.size());
for (ClientConnector connector : dirtyVisibleConnectors) {
// All Components that want to use paintContent must implement
// LegacyComponent
if (connector instanceof LegacyComponent) {
legacyComponents.add((Component) connector);
}
}
sortByHierarchy(legacyComponents);
writer.write("[");
for (Component c : legacyComponents) {
getLogger()
.fine("Painting LegacyComponent " + c.getClass().getName()
+ "@" + Integer.toHexString(c.hashCode()));
target.startTag("change");
final String pid = c.getConnectorId();
target.addAttribute("pid", pid);
LegacyPaint.paint(c, target);
target.endTag("change");
}
writer.write("]");
}
private void sortByHierarchy(List paintables) {
// Vaadin 6 requires parents to be painted before children as component
// containers rely on that their updateFromUIDL method has been called
// before children start calling e.g. updateCaption
Collections.sort(paintables, (Component c1, Component c2) -> {
int depth1 = 0;
while (c1.getParent() != null) {
depth1++;
c1 = c1.getParent();
}
int depth2 = 0;
while (c2.getParent() != null) {
depth2++;
c2 = c2.getParent();
}
if (depth1 < depth2) {
return -1;
}
if (depth1 > depth2) {
return 1;
}
return 0;
});
}
private static final Logger getLogger() {
return Logger.getLogger(LegacyUidlWriter.class.getName());
}
}