Ejemplo n.º 1
0
Layer *VariantToMapConverter::toLayer(const QVariant &variant)
{
    const QVariantMap variantMap = variant.toMap();
    Layer *layer = nullptr;

    if (variantMap[QLatin1String("type")] == QLatin1String("tilelayer"))
        layer = toTileLayer(variantMap);
    else if (variantMap[QLatin1String("type")] == QLatin1String("objectgroup"))
        layer = toObjectGroup(variantMap);
    else if (variantMap[QLatin1String("type")] == QLatin1String("imagelayer"))
        layer = toImageLayer(variantMap);
    else if (variantMap[QLatin1String("type")] == QLatin1String("group"))
        layer = toGroupLayer(variantMap);

    if (layer) {
        layer->setProperties(extractProperties(variantMap));

        const QPointF offset(variantMap[QLatin1String("offsetx")].toDouble(),
                             variantMap[QLatin1String("offsety")].toDouble());
        layer->setOffset(offset);
    }

    return layer;
}
Ejemplo n.º 2
0
Map *VariantToMapConverter::toMap(const QVariant &variant,
                                  const QDir &mapDir)
{
    mGidMapper.clear();
    mMapDir = mapDir;

    const QVariantMap variantMap = variant.toMap();
    const QString orientationString = variantMap[QLatin1String("orientation")].toString();

    Map::Orientation orientation = orientationFromString(orientationString);

    if (orientation == Map::Unknown) {
        mError = tr("Unsupported map orientation: \"%1\"")
                .arg(orientationString);
        return nullptr;
    }

    const QString staggerAxisString = variantMap[QLatin1String("staggeraxis")].toString();
    Map::StaggerAxis staggerAxis = staggerAxisFromString(staggerAxisString);

    const QString staggerIndexString = variantMap[QLatin1String("staggerindex")].toString();
    Map::StaggerIndex staggerIndex = staggerIndexFromString(staggerIndexString);

    const QString renderOrderString = variantMap[QLatin1String("renderorder")].toString();
    Map::RenderOrder renderOrder = renderOrderFromString(renderOrderString);

    const int nextObjectId = variantMap[QLatin1String("nextobjectid")].toInt();

    QScopedPointer<Map> map(new Map(orientation,
                            variantMap[QLatin1String("width")].toInt(),
                            variantMap[QLatin1String("height")].toInt(),
                            variantMap[QLatin1String("tilewidth")].toInt(),
                            variantMap[QLatin1String("tileheight")].toInt()));
    map->setHexSideLength(variantMap[QLatin1String("hexsidelength")].toInt());
    map->setStaggerAxis(staggerAxis);
    map->setStaggerIndex(staggerIndex);
    map->setRenderOrder(renderOrder);
    if (nextObjectId)
        map->setNextObjectId(nextObjectId);

    mMap = map.data();
    map->setProperties(extractProperties(variantMap));

    const QString bgColor = variantMap[QLatin1String("backgroundcolor")].toString();
    if (!bgColor.isEmpty() && QColor::isValidColor(bgColor))
        map->setBackgroundColor(QColor(bgColor));

    const auto tilesetVariants = variantMap[QLatin1String("tilesets")].toList();
    for (const QVariant &tilesetVariant : tilesetVariants) {
        SharedTileset tileset = toTileset(tilesetVariant);
        if (!tileset)
            return nullptr;

        map->addTileset(tileset);
    }

    const auto layerVariants = variantMap[QLatin1String("layers")].toList();
    for (const QVariant &layerVariant : layerVariants) {
        Layer *layer = toLayer(layerVariant);
        if (!layer)
            return nullptr;

        map->addLayer(layer);
    }

    // Try to load the tileset images
    auto tilesets = map->tilesets();
    for (SharedTileset &tileset : tilesets) {
        if (!tileset->imageSource().isEmpty() && tileset->fileName().isEmpty())
            tileset->loadImage();
    }

    return map.take();
}
Ejemplo n.º 3
0
ObjectGroup *VariantToMapConverter::toObjectGroup(const QVariantMap &variantMap)
{
    typedef QScopedPointer<ObjectGroup> ObjectGroupPtr;
    ObjectGroupPtr objectGroup(new ObjectGroup(variantMap[QLatin1String("name")].toString(),
                                               variantMap[QLatin1String("x")].toInt(),
                                               variantMap[QLatin1String("y")].toInt()));

    const qreal opacity = variantMap[QLatin1String("opacity")].toReal();
    const bool visible = variantMap[QLatin1String("visible")].toBool();

    objectGroup->setOpacity(opacity);
    objectGroup->setVisible(visible);

    objectGroup->setColor(variantMap.value(QLatin1String("color")).value<QColor>());

    const QString drawOrderString = variantMap.value(QLatin1String("draworder")).toString();
    if (!drawOrderString.isEmpty()) {
        objectGroup->setDrawOrder(drawOrderFromString(drawOrderString));
        if (objectGroup->drawOrder() == ObjectGroup::UnknownOrder) {
            mError = tr("Invalid draw order: %1").arg(drawOrderString);
            return nullptr;
        }
    }

    const auto objectVariants = variantMap[QLatin1String("objects")].toList();
    for (const QVariant &objectVariant : objectVariants) {
        const QVariantMap objectVariantMap = objectVariant.toMap();

        const QString name = objectVariantMap[QLatin1String("name")].toString();
        const QString type = objectVariantMap[QLatin1String("type")].toString();
        const int id = objectVariantMap[QLatin1String("id")].toInt();
        const int gid = objectVariantMap[QLatin1String("gid")].toInt();
        const qreal x = objectVariantMap[QLatin1String("x")].toReal();
        const qreal y = objectVariantMap[QLatin1String("y")].toReal();
        const qreal width = objectVariantMap[QLatin1String("width")].toReal();
        const qreal height = objectVariantMap[QLatin1String("height")].toReal();
        const qreal rotation = objectVariantMap[QLatin1String("rotation")].toReal();

        const QPointF pos(x, y);
        const QSizeF size(width, height);

        MapObject *object = new MapObject(name, type, pos, size);
        object->setId(id);
        object->setRotation(rotation);

        if (gid) {
            bool ok;
            object->setCell(mGidMapper.gidToCell(gid, ok));

            if (const Tile *tile = object->cell().tile()) {
                const QSizeF &tileSize = tile->size();
                if (width == 0)
                    object->setWidth(tileSize.width());
                if (height == 0)
                    object->setHeight(tileSize.height());
            }
        }

        if (objectVariantMap.contains(QLatin1String("visible")))
            object->setVisible(objectVariantMap[QLatin1String("visible")].toBool());

        object->setProperties(extractProperties(objectVariantMap));
        objectGroup->addObject(object);

        const QVariant polylineVariant = objectVariantMap[QLatin1String("polyline")];
        const QVariant polygonVariant = objectVariantMap[QLatin1String("polygon")];
        const QVariant textVariant = objectVariantMap[QLatin1String("text")];

        if (polygonVariant.isValid()) {
            object->setShape(MapObject::Polygon);
            object->setPolygon(toPolygon(polygonVariant));
        }
        if (polylineVariant.isValid()) {
            object->setShape(MapObject::Polyline);
            object->setPolygon(toPolygon(polylineVariant));
        }
        if (objectVariantMap.contains(QLatin1String("ellipse")))
            object->setShape(MapObject::Ellipse);
        if (textVariant.isValid()) {
            object->setTextData(toTextData(textVariant.toMap()));
            object->setShape(MapObject::Text);
        }
    }

    return objectGroup.take();
}
Ejemplo n.º 4
0
SharedTileset VariantToMapConverter::toTileset(const QVariant &variant)
{
    const QVariantMap variantMap = variant.toMap();

    const int firstGid = variantMap[QLatin1String("firstgid")].toInt();

    // Handle external tilesets
    const QVariant sourceVariant = variantMap[QLatin1String("source")];
    if (!sourceVariant.isNull()) {
        QString source = resolvePath(mMapDir, sourceVariant);
        QString error;
        SharedTileset tileset = TilesetManager::instance()->loadTileset(source, &error);
        if (!tileset) {
            // Insert a placeholder to allow the map to load
            tileset = Tileset::create(QFileInfo(source).completeBaseName(), 32, 32);
            tileset->setFileName(source);
            tileset->setLoaded(false);
        } else {
            mGidMapper.insert(firstGid, tileset.data());
        }
        return tileset;
    }

    const QString name = variantMap[QLatin1String("name")].toString();
    const int tileWidth = variantMap[QLatin1String("tilewidth")].toInt();
    const int tileHeight = variantMap[QLatin1String("tileheight")].toInt();
    const int spacing = variantMap[QLatin1String("spacing")].toInt();
    const int margin = variantMap[QLatin1String("margin")].toInt();
    const QVariantMap tileOffset = variantMap[QLatin1String("tileoffset")].toMap();
    const QVariantMap grid = variantMap[QLatin1String("grid")].toMap();
    const int tileOffsetX = tileOffset[QLatin1String("x")].toInt();
    const int tileOffsetY = tileOffset[QLatin1String("y")].toInt();
    const int columns = tileOffset[QLatin1String("columns")].toInt();
    const QString bgColor = variantMap[QLatin1String("backgroundcolor")].toString();

    if (tileWidth <= 0 || tileHeight <= 0 ||
            (firstGid == 0 && !mReadingExternalTileset)) {
        mError = tr("Invalid tileset parameters for tileset '%1'").arg(name);
        return SharedTileset();
    }

    SharedTileset tileset(Tileset::create(name,
                                          tileWidth, tileHeight,
                                          spacing, margin));

    tileset->setTileOffset(QPoint(tileOffsetX, tileOffsetY));
    tileset->setColumnCount(columns);

    if (!grid.isEmpty()) {
        const QString orientation = grid[QLatin1String("orientation")].toString();
        const QSize gridSize(grid[QLatin1String("width")].toInt(),
                             grid[QLatin1String("height")].toInt());

        tileset->setOrientation(Tileset::orientationFromString(orientation));
        if (!gridSize.isEmpty())
            tileset->setGridSize(gridSize);
    }

    if (!bgColor.isEmpty() && QColor::isValidColor(bgColor))
        tileset->setBackgroundColor(QColor(bgColor));

    QVariant imageVariant = variantMap[QLatin1String("image")];

    if (!imageVariant.isNull()) {
        const int imageWidth = variantMap[QLatin1String("imagewidth")].toInt();
        const int imageHeight = variantMap[QLatin1String("imageheight")].toInt();

        ImageReference imageRef;
        imageRef.source = resolvePath(mMapDir, imageVariant);
        imageRef.size = QSize(imageWidth, imageHeight);

        tileset->setImageReference(imageRef);
    }

    const QString trans = variantMap[QLatin1String("transparentcolor")].toString();
    if (!trans.isEmpty() && QColor::isValidColor(trans))
        tileset->setTransparentColor(QColor(trans));

    tileset->setProperties(extractProperties(variantMap));

    // Read terrains
    QVariantList terrainsVariantList = variantMap[QLatin1String("terrains")].toList();
    for (int i = 0; i < terrainsVariantList.count(); ++i) {
        QVariantMap terrainMap = terrainsVariantList[i].toMap();
        Terrain *terrain = tileset->addTerrain(terrainMap[QLatin1String("name")].toString(),
                                               terrainMap[QLatin1String("tile")].toInt());
        terrain->setProperties(extractProperties(terrainMap));
    }

    // Read tiles (everything except their properties)
    const QVariantMap tilesVariantMap = variantMap[QLatin1String("tiles")].toMap();
    QVariantMap::const_iterator it = tilesVariantMap.constBegin();
    for (; it != tilesVariantMap.end(); ++it) {
        bool ok;
        const int tileId = it.key().toInt();
        if (tileId < 0) {
            mError = tr("Invalid (negative) tile id: %1").arg(tileId);
            return SharedTileset();
        }

        Tile *tile = tileset->findOrCreateTile(tileId);

        const QVariantMap tileVar = it.value().toMap();

        tile->setType(tileVar[QLatin1String("type")].toString());

        QList<QVariant> terrains = tileVar[QLatin1String("terrain")].toList();
        if (terrains.count() == 4) {
            for (int i = 0; i < 4; ++i) {
                int terrainId = terrains.at(i).toInt(&ok);
                if (ok && terrainId >= 0 && terrainId < tileset->terrainCount())
                    tile->setCornerTerrainId(i, terrainId);
            }
        }

        float probability = tileVar[QLatin1String("probability")].toFloat(&ok);
        if (ok)
            tile->setProbability(probability);

        imageVariant = tileVar[QLatin1String("image")];
        if (!imageVariant.isNull()) {
            QString imagePath = resolvePath(mMapDir, imageVariant);
            tileset->setTileImage(tile, QPixmap(imagePath), imagePath);
        }

        QVariantMap objectGroupVariant = tileVar[QLatin1String("objectgroup")].toMap();
        if (!objectGroupVariant.isEmpty())
            tile->setObjectGroup(toObjectGroup(objectGroupVariant));

        QVariantList frameList = tileVar[QLatin1String("animation")].toList();
        if (!frameList.isEmpty()) {
            QVector<Frame> frames(frameList.size());
            for (int i = frameList.size() - 1; i >= 0; --i) {
                const QVariantMap frameVariantMap = frameList[i].toMap();
                Frame &frame = frames[i];
                frame.tileId = frameVariantMap[QLatin1String("tileid")].toInt();
                frame.duration = frameVariantMap[QLatin1String("duration")].toInt();
            }
            tile->setFrames(frames);
        }
    }

    // Read tile properties
    QVariantMap propertiesVariantMap = variantMap[QLatin1String("tileproperties")].toMap();
    QVariantMap propertyTypesVariantMap = variantMap[QLatin1String("tilepropertytypes")].toMap();
    for (it = propertiesVariantMap.constBegin(); it != propertiesVariantMap.constEnd(); ++it) {
        const int tileId = it.key().toInt();
        const QVariant propertiesVar = it.value();
        const QVariant propertyTypesVar = propertyTypesVariantMap.value(it.key());
        const Properties properties = toProperties(propertiesVar, propertyTypesVar);
        tileset->findOrCreateTile(tileId)->setProperties(properties);
    }

    if (!mReadingExternalTileset)
        mGidMapper.insert(firstGid, tileset.data());

    return tileset;
}
Ejemplo n.º 5
0
bool SGFNode::makeNode(string sb)
{
	// separate property string
	string propertyString;
	char c='\0';
	int insideSBracket=0;

	// read properties up to first '(' or ';'
	// allowing '(' ')' inside '[' ']'
	for(int i=0;i<sb.length();i++) {
		c = sb.at(i);
		if(!insideSBracket && c=='[') insideSBracket++;
		else if(c==']' && (!(i>0&&sb.at(i-1)=='\\'))) insideSBracket--;
		if (insideSBracket==0) {
			if (c=='(' || c==';' || c==')') {
				propertyString = sb.substr(0, i);
				sb.erase(0, i);
				break;
			}
		}
	}
	
	// extract properties
	if(!extractProperties(propertyString)) {
		string message = "Bad node: ";
		message+=propertyString;
		message+="\n";
		LogWriter::printerr(message, "SGF");
		return false;
	}

/*	SGFNode* node;
	try {
		node = new SGFNode();
	} catch(exception& e) {
		cerr << e.what();
		return false;
	}*/
	SGFNode node;

	if (c=='(') {
		string pb;
		int bcount, i;
		char b;
		
		while (c=='(') {
			// remove up to matching ')' from sb 
			// and put into pb
			bcount = 0;
			insideSBracket = 0;
			
			for(i=0;i<sb.length();i++) {
				// WARNING: Don't count '(' or ')' inside comments!
				// and check for escaped ']' i.e. "C[This is some comment \](blah blah) ]"
				b = sb.at(i);
				if(!insideSBracket && b=='[') 
					insideSBracket++;
				else if(b==']' && (!(i>0&&sb.at(i-1)=='\\'))) {
					insideSBracket--;
					// error check
					if(insideSBracket<0) {
						// The stupid program that wrote this sgf 
						// has not escaped a ']' inside a comment
						insideSBracket = 0;
						// NOTE: We should really just quit parsing this sgf
						// and say's it's got an invalid node
						string message = "Bad node (mismatched brackets '[', ']'): ";
						message+=sb.substr(0, i);
						message+="\n";
						LogWriter::printerr(message, "SGF");
						return false;
					}
				}
				if(!insideSBracket) {
					if(b=='(')
						bcount++;
					else if(b==')' && bcount<=1)
						break;
					else if(b==')')
						bcount--;
				}
			}
			
			// remove '(;' from start by starting after it
			//pb = *(new string(sb.substr(2, i).trim()));
			pb = string(sb.substr(2, i));
			sb.erase(0, i);
		
			if (pb.length()>0) {
				// run make node
				if(!node.makeNode(pb))
					return false;

				// add as child
				addChild(node);
			}
			
			// see whats next
			c = sb.at(0);
		}
	}
	else if (c==';') {
		// copy all sb from after ';' to end
		string pb = string(sb.substr(1));
		//pb.deleteCharAt(pb.length()-1);
		
		if (pb.length()>0) {
			// make sure this isn't the end of a variation
			// or an empty node e.g. '(;W[pp];B[pl];)'
			if(pb.at(0)!=')') {
				// run make node
				if(!node.makeNode(pb))
					return false;
				// add as child
				addChild(node);
			}
		}			
	}
	return true;
}