Fix converstion of ByteArray and String

master
Jos van den Oever 2017-08-12 00:18:10 +02:00
parent e468359100
commit e93cb80d26
8 changed files with 135 additions and 51 deletions

View File

@ -85,8 +85,8 @@ enum VariantType {
#[repr(C)]
pub struct QVariant<'a> {
type_: c_uint,
len: c_int,
type_: VariantType,
value: c_int,
data: *const uint8_t,
phantom: PhantomData<&'a u8>,
}
@ -96,9 +96,22 @@ impl<'a> QVariant<'a> {
self.type_ as u32
}
pub fn convert(&self) -> Variant {
match (self.type_) {
10 => {
Variant::String(String::new())
match self.type_ {
VariantType::Bool => {
Variant::Bool(self.value != 0)
},
VariantType::String => {
let data = unsafe {
let d = self.data as *const uint16_t;
slice::from_raw_parts(d, self.value as usize)
};
Variant::String(String::from_utf16_lossy(data))
}
VariantType::ByteArray => {
let data = unsafe {
slice::from_raw_parts(self.data, self.value as usize)
};
Variant::ByteArray(Vec::from(data))
}
_ => Variant::None
}
@ -111,32 +124,32 @@ impl<'a> From<&'a Variant> for QVariant<'a> {
Variant::None => {
QVariant {
data: null(),
len: 0,
type_: VariantType::Invalid as c_uint,
value: 0,
type_: VariantType::Invalid,
phantom: PhantomData,
}
}
Variant::Bool(v) => {
QVariant {
data: null(),
len: v as c_int,
type_: VariantType::Bool as c_uint,
value: v as c_int,
type_: VariantType::Bool,
phantom: PhantomData,
}
}
Variant::String(ref v) => {
QVariant {
data: v.as_ptr(),
len: v.len() as c_int,
type_: VariantType::String as c_uint,
value: v.len() as c_int,
type_: VariantType::String,
phantom: PhantomData,
}
}
Variant::ByteArray(ref v) => {
QVariant {
data: v.as_ptr(),
len: v.len() as c_int,
type_: VariantType::ByteArray as c_uint,
value: v.len() as c_int,
type_: VariantType::ByteArray,
phantom: PhantomData,
}
}

View File

@ -457,8 +457,9 @@ namespace {
};
QVariant variant(const qvariant_t& v) {
switch (v.type) {
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::String: return QString::fromUtf8(static_cast<const char*>(v.data), v.value);
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::ByteArray: return QVariant(QByteArray(v.data, v.value));
default:;
}
return QVariant();

View File

@ -43,8 +43,9 @@ namespace {
};
QVariant variant(const qvariant_t& v) {
switch (v.type) {
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::String: return QString::fromUtf8(static_cast<const char*>(v.data), v.value);
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::ByteArray: return QVariant(QByteArray(v.data, v.value));
default:;
}
return QVariant();

View File

@ -85,8 +85,8 @@ enum VariantType {
#[repr(C)]
pub struct QVariant<'a> {
type_: c_uint,
len: c_int,
type_: VariantType,
value: c_int,
data: *const uint8_t,
phantom: PhantomData<&'a u8>,
}
@ -96,8 +96,25 @@ impl<'a> QVariant<'a> {
self.type_ as u32
}
pub fn convert(&self) -> Variant {
// TODO
Variant::None
match self.type_ {
VariantType::Bool => {
Variant::Bool(self.value != 0)
},
VariantType::String => {
let data = unsafe {
let d = self.data as *const uint16_t;
slice::from_raw_parts(d, self.value as usize)
};
Variant::String(String::from_utf16_lossy(data))
}
VariantType::ByteArray => {
let data = unsafe {
slice::from_raw_parts(self.data, self.value as usize)
};
Variant::ByteArray(Vec::from(data))
}
_ => Variant::None
}
}
}
@ -107,32 +124,32 @@ impl<'a> From<&'a Variant> for QVariant<'a> {
Variant::None => {
QVariant {
data: null(),
len: 0,
type_: VariantType::Invalid as c_uint,
value: 0,
type_: VariantType::Invalid,
phantom: PhantomData,
}
}
Variant::Bool(v) => {
QVariant {
data: null(),
len: v as c_int,
type_: VariantType::Bool as c_uint,
value: v as c_int,
type_: VariantType::Bool,
phantom: PhantomData,
}
}
Variant::String(ref v) => {
QVariant {
data: v.as_ptr(),
len: v.len() as c_int,
type_: VariantType::String as c_uint,
value: v.len() as c_int,
type_: VariantType::String,
phantom: PhantomData,
}
}
Variant::ByteArray(ref v) => {
QVariant {
data: v.as_ptr(),
len: v.len() as c_int,
type_: VariantType::ByteArray as c_uint,
value: v.len() as c_int,
type_: VariantType::ByteArray,
phantom: PhantomData,
}
}

View File

@ -85,8 +85,8 @@ enum VariantType {
#[repr(C)]
pub struct QVariant<'a> {
type_: c_uint,
len: c_int,
type_: VariantType,
value: c_int,
data: *const uint8_t,
phantom: PhantomData<&'a u8>,
}
@ -97,13 +97,22 @@ impl<'a> QVariant<'a> {
}
pub fn convert(&self) -> Variant {
match self.type_ {
10 => {
VariantType::Bool => {
Variant::Bool(self.value != 0)
},
VariantType::String => {
let data = unsafe {
let d = self.data as *const uint16_t;
slice::from_raw_parts(d, self.len as usize)
slice::from_raw_parts(d, self.value as usize)
};
Variant::String(String::from_utf16_lossy(data))
}
VariantType::ByteArray => {
let data = unsafe {
slice::from_raw_parts(self.data, self.value as usize)
};
Variant::ByteArray(Vec::from(data))
}
_ => Variant::None
}
}
@ -115,32 +124,32 @@ impl<'a> From<&'a Variant> for QVariant<'a> {
Variant::None => {
QVariant {
data: null(),
len: 0,
type_: VariantType::Invalid as c_uint,
value: 0,
type_: VariantType::Invalid,
phantom: PhantomData,
}
}
Variant::Bool(v) => {
QVariant {
data: null(),
len: v as c_int,
type_: VariantType::Bool as c_uint,
value: v as c_int,
type_: VariantType::Bool,
phantom: PhantomData,
}
}
Variant::String(ref v) => {
QVariant {
data: v.as_ptr(),
len: v.len() as c_int,
type_: VariantType::String as c_uint,
value: v.len() as c_int,
type_: VariantType::String,
phantom: PhantomData,
}
}
Variant::ByteArray(ref v) => {
QVariant {
data: v.as_ptr(),
len: v.len() as c_int,
type_: VariantType::ByteArray as c_uint,
value: v.len() as c_int,
type_: VariantType::ByteArray,
phantom: PhantomData,
}
}

View File

@ -43,8 +43,9 @@ namespace {
};
QVariant variant(const qvariant_t& v) {
switch (v.type) {
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::String: return QString::fromUtf8(static_cast<const char*>(v.data), v.value);
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::ByteArray: return QVariant(QByteArray(v.data, v.value));
default:;
}
return QVariant();

View File

@ -1,29 +1,52 @@
#include "test_object_types_rust.h"
#include <QTest>
#include <QSignalSpy>
#include <QDebug>
class TestRustObject : public QObject
class TestRustObjectTypes : public QObject
{
Q_OBJECT
private slots:
void testConstructor();
void testStringGetter();
void testStringSetter();
void testInvalid();
void testBool();
void testString();
void testByteArray();
};
void TestRustObject::testConstructor()
void TestRustObjectTypes::testInvalid()
{
// GIVEN
Person person;
const QVariant userName;
QSignalSpy spy(&person, &Person::userNameChanged);
// WHEN
person.setUserName(userName);
// THEN
QVERIFY(spy.isValid());
QCOMPARE(spy.count(), 1);
QCOMPARE(person.userName().type(), userName.type());
QCOMPARE(person.userName(), userName);
}
void TestRustObject::testStringGetter()
void TestRustObjectTypes::testBool()
{
// GIVEN
Person person;
person.setUserName("Konqi");
const QVariant userName(true);
QSignalSpy spy(&person, &Person::userNameChanged);
// WHEN
person.setUserName(userName);
// THEN
QVERIFY(spy.isValid());
QCOMPARE(spy.count(), 1);
QCOMPARE(person.userName().type(), userName.type());
QCOMPARE(person.userName(), userName);
}
void TestRustObject::testStringSetter()
void TestRustObjectTypes::testString()
{
// GIVEN
Person person;
@ -40,5 +63,23 @@ void TestRustObject::testStringSetter()
QCOMPARE(person.userName(), userName);
}
QTEST_MAIN(TestRustObject)
void TestRustObjectTypes::testByteArray()
{
// GIVEN
Person person;
const char data[10] = {0x0,0x1,0x2,0x3,0x4,0x5,0x6,0x7,0x8,0x9};
const QVariant userName(QByteArray(data, 10));
QSignalSpy spy(&person, &Person::userNameChanged);
// WHEN
person.setUserName(userName);
// THEN
QVERIFY(spy.isValid());
QCOMPARE(spy.count(), 1);
QCOMPARE(person.userName().type(), userName.type());
QCOMPARE(person.userName(), userName);
}
QTEST_MAIN(TestRustObjectTypes)
#include "test_object_types.moc"

View File

@ -43,8 +43,9 @@ namespace {
};
QVariant variant(const qvariant_t& v) {
switch (v.type) {
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::String: return QString::fromUtf8(static_cast<const char*>(v.data), v.value);
case QVariant::Bool: return QVariant((bool)v.value);
case QVariant::ByteArray: return QVariant(QByteArray(v.data, v.value));
default:;
}
return QVariant();