summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMateusz Piekos <mateuszpiekos@gmail.com>2012-06-21 18:05:56 (GMT)
committerMateusz Piekos <mateuszpiekos@gmail.com>2012-06-21 18:05:56 (GMT)
commit286a3d119ec95b235b09935296450ec36e640aeb (patch)
tree9146c0ebb21745bb985d24378829929ce92529e2 /Swiften
parente0c79b3b885f126a2a2a34cb0d5df90796821130 (diff)
downloadswift-contrib-286a3d119ec95b235b09935296450ec36e640aeb.zip
swift-contrib-286a3d119ec95b235b09935296450ec36e640aeb.tar.bz2
Added parsing and serialization of freehand path element
Diffstat (limited to 'Swiften')
-rw-r--r--Swiften/Base/String.cpp18
-rw-r--r--Swiften/Base/String.h3
-rw-r--r--Swiften/Parser/PayloadParsers/WhiteboardParser.cpp87
-rw-r--r--Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.cpp58
-rw-r--r--Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.h4
-rw-r--r--Swiften/Whiteboard/Elements/Color.cpp45
-rw-r--r--Swiften/Whiteboard/Elements/Color.h2
-rw-r--r--Swiften/Whiteboard/Elements/WhiteboardElementVisitor.h4
-rw-r--r--Swiften/Whiteboard/Elements/WhiteboardFreehandPathElement.h67
-rw-r--r--Swiften/Whiteboard/Elements/WhiteboardLineElement.h2
10 files changed, 227 insertions, 63 deletions
diff --git a/Swiften/Base/String.cpp b/Swiften/Base/String.cpp
index 7ddf614..242b8e5 100644
--- a/Swiften/Base/String.cpp
+++ b/Swiften/Base/String.cpp
@@ -6,6 +6,8 @@
#include <cassert>
#include <algorithm>
+#include <sstream>
+#include <iomanip>
#include <Swiften/Base/String.h>
@@ -95,4 +97,20 @@ std::vector<std::string> String::split(const std::string& s, char c) {
return result;
}
+std::string String::convertIntToHexString(int h) {
+ std::stringstream ss;
+ ss << std::setbase(16);
+ ss << h;
+ return ss.str();
+}
+
+int String::convertHexStringToInt(const std::string& s) {
+ std::stringstream ss;
+ int h;
+ ss << std::setbase(16);
+ ss << s;
+ ss >> h;
+ return h;
+}
+
}
diff --git a/Swiften/Base/String.h b/Swiften/Base/String.h
index db6c28b..1dd303f 100644
--- a/Swiften/Base/String.h
+++ b/Swiften/Base/String.h
@@ -27,6 +27,9 @@ namespace Swift {
inline bool endsWith(const std::string& s, char c) {
return s.size() > 0 && s[s.size()-1] == c;
}
+
+ std::string convertIntToHexString(int h);
+ int convertHexStringToInt(const std::string& s);
};
class makeString {
diff --git a/Swiften/Parser/PayloadParsers/WhiteboardParser.cpp b/Swiften/Parser/PayloadParsers/WhiteboardParser.cpp
index d0fa9f9..7182a8c 100644
--- a/Swiften/Parser/PayloadParsers/WhiteboardParser.cpp
+++ b/Swiften/Parser/PayloadParsers/WhiteboardParser.cpp
@@ -6,9 +6,11 @@
#include <Swiften/Parser/PayloadParsers/WhiteboardParser.h>
#include <Swiften/Whiteboard/Elements/WhiteboardLineElement.h>
+#include <Swiften/Whiteboard/Elements/WhiteboardFreehandPathElement.h>
#include <Swiften/Whiteboard/Elements/Color.h>
#include <boost/optional.hpp>
#include <boost/smart_ptr/make_shared.hpp>
+#include <boost/lexical_cast.hpp>
namespace Swift {
WhiteboardParser::WhiteboardParser() : level_(0) {
@@ -19,24 +21,93 @@ namespace Swift {
getPayloadInternal()->setType(stringToType(attributes.getAttributeValue("type").get_value_or("")));
} else if (level_ == 1) {
if (element == "line") {
- int x1 = std::atoi(attributes.getAttributeValue("x1").get_value_or("0").c_str());
- int y1 = std::atoi(attributes.getAttributeValue("y1").get_value_or("0").c_str());
- int x2 = std::atoi(attributes.getAttributeValue("x2").get_value_or("0").c_str());
- int y2 = std::atoi(attributes.getAttributeValue("y2").get_value_or("0").c_str());
+ int x1 = 0;
+ int y1 = 0;
+ int x2 = 0;
+ int y2 = 0;
+ try {
+ x1 = boost::lexical_cast<int>(attributes.getAttributeValue("x1").get_value_or("0"));
+ y1 = boost::lexical_cast<int>(attributes.getAttributeValue("y1").get_value_or("0"));
+ x2 = boost::lexical_cast<int>(attributes.getAttributeValue("x2").get_value_or("0"));
+ y2 = boost::lexical_cast<int>(attributes.getAttributeValue("y2").get_value_or("0"));
+ } catch (boost::bad_lexical_cast&) {
+ }
WhiteboardLineElement::ref whiteboardElement = boost::make_shared<WhiteboardLineElement>(x1, y1, x2, y2);
- Color color(attributes.getAttributeValue("stroke").get_value_or("#00000"));
+ Color color(attributes.getAttributeValue("stroke").get_value_or("#000000"));
std::string opacity = attributes.getAttributeValue("opacity").get_value_or("1");
if (opacity.find('.') != std::string::npos) {
opacity = opacity.substr(opacity.find('.')+1, 2);
- color.setAlpha(std::atoi(opacity.c_str())*255/100);
+ try {
+ color.setAlpha(boost::lexical_cast<int>(opacity)*255/100);
+ } catch (boost::bad_lexical_cast&) {
+ }
}
-
whiteboardElement->setColor(color);
- int penWidth = std::atoi(attributes.getAttributeValue("stroke-width").get_value_or("1").c_str());
+ int penWidth = 1;
+ try {
+ penWidth = boost::lexical_cast<int>(attributes.getAttributeValue("stroke-width").get_value_or("1"));
+ } catch (boost::bad_lexical_cast&) {
+ }
+ whiteboardElement->setPenWidth(penWidth);
+
+ getPayloadInternal()->setElement(whiteboardElement);
+ } else if (element == "path") {
+ WhiteboardFreehandPathElement::ref whiteboardElement = boost::make_shared<WhiteboardFreehandPathElement>();
+ std::string pathData = attributes.getAttributeValue("d").get_value_or("");
+ std::vector<std::pair<int, int> > points;
+ if (pathData[0] == 'M') {
+ int pos = 1;
+ int npos;
+ int x, y;
+ if (pathData[pos] == ' ') {
+ pos++;
+ }
+ try {
+ npos = pathData.find(' ', pos);
+ x = boost::lexical_cast<int>(pathData.substr(pos, npos-pos));
+ pos = npos+1;
+ npos = pathData.find('L', pos);
+ y = boost::lexical_cast<int>(pathData.substr(pos, npos-pos));
+ pos = npos+1;
+ if (pathData[pos] == ' ') {
+ pos++;
+ }
+ points.push_back(std::pair<int, int>(x, y));
+ while (pos < pathData.size()) {
+ npos = pathData.find(' ', pos);
+ x = boost::lexical_cast<int>(pathData.substr(pos, npos-pos));
+ pos = npos+1;
+ npos = pathData.find(' ', pos);
+ y = boost::lexical_cast<int>(pathData.substr(pos, npos-pos));
+ pos = npos+1;
+ points.push_back(std::pair<int, int>(x, y));
+ }
+ } catch (boost::bad_lexical_cast&) {
+ }
+ }
+ whiteboardElement->setPoints(points);
+
+ int penWidth = 1;
+ try {
+ penWidth = boost::lexical_cast<int>(attributes.getAttributeValue("stroke-width").get_value_or("1"));
+ } catch (boost::bad_lexical_cast&) {
+ }
whiteboardElement->setPenWidth(penWidth);
+ Color color(attributes.getAttributeValue("stroke").get_value_or("#000000"));
+
+ std::string opacity = attributes.getAttributeValue("opacity").get_value_or("1");
+ if (opacity.find('.') != std::string::npos) {
+ opacity = opacity.substr(opacity.find('.')+1, 2);
+ try {
+ color.setAlpha(boost::lexical_cast<int>(opacity)*255/100);
+ } catch (boost::bad_lexical_cast&) {
+ }
+ }
+ whiteboardElement->setColor(color);
+
getPayloadInternal()->setElement(whiteboardElement);
}
}
diff --git a/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.cpp b/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.cpp
index f02791c..b5a4c49 100644
--- a/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.cpp
+++ b/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.cpp
@@ -7,24 +7,54 @@
#include <Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.h>
#include <boost/smart_ptr/make_shared.hpp>
+#include <boost/lexical_cast.hpp>
#include <Swiften/Serializer/XML/XMLTextNode.h>
namespace Swift {
- void WhiteboardElementSerializingVisitor::visit(const WhiteboardLineElement* line) {
+ void WhiteboardElementSerializingVisitor::visit(WhiteboardLineElement& line) {
element = boost::make_shared<XMLElement>("line");
- element->setAttribute("x1", intToStr(line->x1()));
- element->setAttribute("y1", intToStr(line->y1()));
- element->setAttribute("x2", intToStr(line->x2()));
- element->setAttribute("y2", intToStr(line->y2()));
- element->setAttribute("id", line->getID());
- element->setAttribute("stroke", line->getColor().toHex());
- element->setAttribute("stroke-width", intToStr(line->getPenWidth()));
- int alpha = line->getColor().getAlpha();
- int opacity = 100*alpha/254;
- if (opacity == 100) {
- element->setAttribute("opacity", "1");
- } else {
- element->setAttribute("opacity", "."+intToStr(opacity));
+ try {
+ element->setAttribute("x1", boost::lexical_cast<std::string>(line.x1()));
+ element->setAttribute("y1", boost::lexical_cast<std::string>(line.y1()));
+ element->setAttribute("x2", boost::lexical_cast<std::string>(line.x2()));
+ element->setAttribute("y2", boost::lexical_cast<std::string>(line.y2()));
+ element->setAttribute("id", line.getID());
+ element->setAttribute("stroke", line.getColor().toHex());
+ element->setAttribute("stroke-width", boost::lexical_cast<std::string>(line.getPenWidth()));
+ int alpha = line.getColor().getAlpha();
+ int opacity = 100*alpha/254;
+ if (opacity == 100) {
+ element->setAttribute("opacity", "1");
+ } else {
+ element->setAttribute("opacity", "."+boost::lexical_cast<std::string>(opacity));
+ }
+ } catch (boost::bad_lexical_cast&) {
+ }
+ }
+
+ void WhiteboardElementSerializingVisitor::visit(WhiteboardFreehandPathElement& path) {
+ element = boost::make_shared<XMLElement>("path");
+ element->setAttribute("id", path.getID());
+ element->setAttribute("stroke", path.getColor().toHex());
+ try {
+ element->setAttribute("stroke-width", boost::lexical_cast<std::string>(path.getPenWidth()));
+ int alpha = path.getColor().getAlpha();
+ int opacity = 100*alpha/254;
+ if (opacity == 100) {
+ element->setAttribute("opacity", "1");
+ } else {
+ element->setAttribute("opacity", "."+boost::lexical_cast<std::string>(opacity));
+ }
+ std::string pathData;
+ if (path.getPoints().size() != 0) {
+ std::vector<std::pair<int, int> >::const_iterator it = path.getPoints().begin();
+ pathData = "M"+boost::lexical_cast<std::string>(it->first)+" "+boost::lexical_cast<std::string>(it->second)+"L";
+ for (; it != path.getPoints().end(); ++it) {
+ pathData += boost::lexical_cast<std::string>(it->first)+" "+boost::lexical_cast<std::string>(it->second)+" ";
+ }
+ }
+ element->setAttribute("d", pathData);
+ } catch (boost::bad_lexical_cast&) {
}
}
diff --git a/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.h b/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.h
index 50cf252..25642d0 100644
--- a/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.h
+++ b/Swiften/Serializer/PayloadSerializers/WhiteboardSerializer.h
@@ -8,6 +8,7 @@
#include <Swiften/Elements/WhiteboardPayload.h>
#include <Swiften/Whiteboard/Elements/WhiteboardLineElement.h>
+#include <Swiften/Whiteboard/Elements/WhiteboardFreehandPathElement.h>
#include <Swiften/Whiteboard/Elements/WhiteboardElementVisitor.h>
#include <Swiften/Serializer/GenericPayloadSerializer.h>
#include <Swiften/Serializer/XML/XMLElement.h>
@@ -15,7 +16,8 @@
namespace Swift {
class WhiteboardElementSerializingVisitor : public WhiteboardElementVisitor {
public:
- void visit(const WhiteboardLineElement* line);
+ void visit(WhiteboardLineElement& line);
+ void visit(WhiteboardFreehandPathElement& path);
XMLElement::ref getResult() const;
private:
diff --git a/Swiften/Whiteboard/Elements/Color.cpp b/Swiften/Whiteboard/Elements/Color.cpp
index b614a2a..51b8460 100644
--- a/Swiften/Whiteboard/Elements/Color.cpp
+++ b/Swiften/Whiteboard/Elements/Color.cpp
@@ -5,6 +5,7 @@
*/
#include <Swiften/Whiteboard/Elements/Color.h>
+#include <Swiften/Base/String.cpp>
#include <cstdio>
#include <iomanip>
#include <sstream>
@@ -18,39 +19,18 @@ namespace Swift {
}
Color::Color(const std::string& hex) : alpha_(255) {
- if (hex.size() == 7) {
- char temp[3];
- hex.copy(temp, 2, 1);
- temp[2] = 0;
- std::sscanf(temp, "%x", &red_);
- hex.copy(temp, 2, 3);
- temp[2] = 0;
- std::sscanf(temp, "%x", &green_);
- hex.copy(temp, 2, 5);
- temp[2] = 0;
- std::sscanf(temp, "%x", &blue_);
- }
+ int value = String::convertHexStringToInt(hex.substr(1));
+ red_ = (value >> 16)&0xFF;
+ green_ = (value >> 8)&0xFF;
+ blue_ = value&0xFF;
}
std::string Color::toHex() const {
- std::string result = "#";
- std::string hex;
- hex = intToStr(red_, 16);
- if (hex.size() == 1) {
- result += "0";
- }
- result += hex;
- hex = intToStr(green_, 16);
- if (hex.size() == 1) {
- result += "0";
- }
- result += hex;
- hex = intToStr(blue_, 16);
- if (hex.size() == 1) {
- result += "0";
+ std::string value = String::convertIntToHexString((red_ << 16) + (green_ << 8) + blue_);
+ while (value.size() < 6) {
+ value.insert(0, "0");
}
- result += hex;
- return result;
+ return "#"+value;
}
int Color::getRed() const {
@@ -72,11 +52,4 @@ namespace Swift {
void Color::setAlpha(int alpha) {
alpha_ = alpha;
}
-
- std::string Color::intToStr(int t, int base) const {
- std::stringstream ss;
- ss << std::setbase(base);
- ss << t;
- return ss.str();
- }
}
diff --git a/Swiften/Whiteboard/Elements/Color.h b/Swiften/Whiteboard/Elements/Color.h
index b7cca5a..7227eca 100644
--- a/Swiften/Whiteboard/Elements/Color.h
+++ b/Swiften/Whiteboard/Elements/Color.h
@@ -22,8 +22,6 @@ namespace Swift {
void setAlpha(int alpha);
private:
- std::string intToStr(int t, int base = 10) const;
-
int red_, green_, blue_;
int alpha_;
};
diff --git a/Swiften/Whiteboard/Elements/WhiteboardElementVisitor.h b/Swiften/Whiteboard/Elements/WhiteboardElementVisitor.h
index b5fd546..d546e7f 100644
--- a/Swiften/Whiteboard/Elements/WhiteboardElementVisitor.h
+++ b/Swiften/Whiteboard/Elements/WhiteboardElementVisitor.h
@@ -8,10 +8,12 @@
namespace Swift {
class WhiteboardLineElement;
+ class WhiteboardFreehandPathElement;
class WhiteboardElementVisitor {
public:
virtual ~WhiteboardElementVisitor() {}
- virtual void visit(const WhiteboardLineElement* /*element*/) = 0;
+ virtual void visit(WhiteboardLineElement& /*element*/) = 0;
+ virtual void visit(WhiteboardFreehandPathElement& /*element*/) = 0;
};
}
diff --git a/Swiften/Whiteboard/Elements/WhiteboardFreehandPathElement.h b/Swiften/Whiteboard/Elements/WhiteboardFreehandPathElement.h
new file mode 100644
index 0000000..9b69dc4
--- /dev/null
+++ b/Swiften/Whiteboard/Elements/WhiteboardFreehandPathElement.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2012 Mateusz Piękos
+ * Licensed under the simplified BSD license.
+ * See Documentation/Licenses/BSD-simplified.txt for more information.
+ */
+
+#pragma once
+
+#include <Swiften/Whiteboard/Elements/WhiteboardElement.h>
+#include <Swiften/Whiteboard/Elements/Color.h>
+
+#include <vector>
+#include <utility>
+
+namespace Swift {
+ class WhiteboardFreehandPathElement : public WhiteboardElement {
+ typedef std::pair<int, int> Point;
+ public:
+ typedef boost::shared_ptr<WhiteboardFreehandPathElement> ref;
+ public:
+ WhiteboardFreehandPathElement() {
+ }
+
+ void setPoints(const std::vector<Point>& points) {
+ points_ = points;
+ }
+
+ const std::vector<Point>& getPoints() const {
+ return points_;
+ }
+
+ const Color& getColor() const {
+ return color_;
+ }
+
+ void setColor(const Color& color) {
+ color_ = color;
+ }
+
+ std::string getID() const {
+ return id_;
+ }
+
+ void setID(const std::string& id) {
+ id_ = id;
+ }
+
+ int getPenWidth() const {
+ return penWidth_;
+ }
+
+ void setPenWidth(const int penWidth) {
+ penWidth_ = penWidth;
+ }
+
+ void accept(WhiteboardElementVisitor& visitor) {
+ visitor.visit(*this);
+ }
+
+ private:
+
+ std::vector<Point> points_;
+ Color color_;
+ int penWidth_;
+ std::string id_;
+ };
+}
diff --git a/Swiften/Whiteboard/Elements/WhiteboardLineElement.h b/Swiften/Whiteboard/Elements/WhiteboardLineElement.h
index 0088189..20455b6 100644
--- a/Swiften/Whiteboard/Elements/WhiteboardLineElement.h
+++ b/Swiften/Whiteboard/Elements/WhiteboardLineElement.h
@@ -62,7 +62,7 @@ namespace Swift {
}
void accept(WhiteboardElementVisitor& visitor) {
- visitor.visit(this);
+ visitor.visit(*this);
}
private: