protected void toXMLImpl(XMLStreamWriter out, Player player,
                             boolean showAll, boolean toSavedGame)
        throws XMLStreamException {
        // Start element:
        out.writeStartElement(getXMLElementTagName());

        if (toSavedGame && !showAll) {
            throw new IllegalArgumentException("showAll must be set to true when toSavedGame is true.");
        }

        out.writeAttribute(ID_ATTRIBUTE, getId());
        out.writeAttribute("UUID", getUUID().toString());
        out.writeAttribute("turn", Integer.toString(getTurn().getNumber()));
        out.writeAttribute("spanishSuccession", Boolean.toString(spanishSuccession));

        writeAttribute(out, "currentPlayer", currentPlayer);

        if (toSavedGame) {
            out.writeAttribute("nextID", Integer.toString(nextId));
        }

        specification.toXMLImpl(out);

        if (citiesOfCibola == null) initializeCitiesOfCibola();
        for (String cityName : citiesOfCibola) {
            out.writeStartElement(CIBOLA_TAG);
            out.writeAttribute(ID_ATTRIBUTE_TAG, cityName);
            out.writeEndElement();
        }
        nationOptions.toXML(out);

        // serialize players
        Iterator<Player> playerIterator = getPlayerIterator();
        while (playerIterator.hasNext()) {
            Player p = playerIterator.next();
            p.toXML(out, player, showAll, toSavedGame);
        }
        Player enemy = getUnknownEnemy();
        if (enemy != null) enemy.toXML(out, player, showAll, toSavedGame);

        // serialize map
        if (map != null) map.toXML(out, player, showAll, toSavedGame);

        /* Moved to within player.  Last used in 0.9.x.
        // serialize messages
        playerIterator = getPlayerIterator();
        while (playerIterator.hasNext()) {
            Player p = playerIterator.next();
            if (showAll || p.equals(player)) {
                for (ModelMessage message : p.getModelMessages()) {
                    message.toXML(out);
                }
            }
        }
        */

        out.writeEndElement();
    }