SEIntList SEIntList::split(const SEString& str, char sep, char esc) { SEIntList ret; size_t from = 0; size_t cur = 0; size_t len = str.length(); // skip trailing separators while (str[cur] == sep) { from++; cur++; } cur++; while (cur <= len) { // the case when we go out of bounds is when we have escaped separator // before end of the string if (cur == len) { ret.append(str.substr(from, cur - 1).toInt()); break; } if (str[cur] == sep) { // here we may go out of bounds (handled above) if (esc && (str[cur - 1] == esc)) { cur++; continue; } ret.append(str.substr(from, cur - 1).toInt()); while ((str[cur] == sep) && (cur < len)) cur++; if (cur >= (len - 1)) break; from = cur++; continue; } if (cur == (len - 1)) { ret.append(str.substr(from, cur).toInt()); break; } cur++; } return ret; }
Poco::SharedPtr<ContactData> Util::dataFromContact(const ContactRef &contact) { /* As we are only interested in some data about the Contact, let's fill * a small structure with everything we need and then return. */ Poco::SharedPtr<ContactData> newData = Poco::SharedPtr<ContactData>(new ContactData); newData->canSMS = false; SEString value; // Get the Skype Name from the Contact. Contact::TYPE type; contact->GetPropType(type); switch (type) { case Contact::SKYPE: contact->GetPropSkypename(value); break; case Contact::PSTN: contact->GetPropPstnnumber(value); newData->canSMS = true; break; default: value = "Unrecognized"; } newData->skypeName = value; // Get the Display Name from the Contact. contact->GetPropDisplayname(value); newData->displayName = value; if (!newData->canSMS) { // See if the contact has a mobile number set. contact->GetPropPhoneMobile(value); if (value.length() > 0) newData->canSMS = true; } /* Get the availability from the Contact and translate it to a readable * string. */ Contact::AVAILABILITY availability; contact->GetPropAvailability(availability); std::pair<ContactAvailability, std::string> ret = convertAvailability(availability); newData->status = ret.first; newData->availability = ret.second; //Get the contact Avatar. bool hasAvatar = false; SEBinary rawData; contact->GetAvatar(hasAvatar, rawData); // Check if the contact has an avatar and then extract the data from it. if (hasAvatar) newData->avatar.assignRaw(rawData.data(), rawData.size()); // Get the contact capabilities. contact->HasCapability(Contact::CAPABILITY_TEXT, newData->canIM); newData->canCall = (newData->status != Offline); newData->canFT = (newData->status != Offline && type == Contact::SKYPE); return newData; }
SEStringList SEStringList::split(const SEString& str, char sep, char esc) { SEStringList ret; size_t from = 0; size_t cur = 0; const size_t len = str.length(); if (len == 0) return ret; // skip leading separators // .bwc. Repeated code, but easier to understand this way I think. // The compiler may optimize this away. while (str[cur] == sep) { cur++; } // .bwc. At this point, cur is not pointing at a separator; // we will not end up in the code block that appends below // until we have incremented at least once. from = cur; bool in_escape=false; bool in_quotes=false; while (cur < len) { if (str[cur] == sep) { if (!in_escape && !in_quotes) { ret.append(str.substr(from, cur - 1)); while (str[cur] == sep) cur++; // Not pointing at a separator; will not append // again until we have incremented at least // once. from = cur; continue; } } else if (esc && str[cur] == '\"' && !in_escape) { // !bwc! We check esc because that is what we've always // done. Once I hear back from the guys that // implemented this about whether this is the intended // behavior, this component might be removed. in_quotes = !in_quotes; } in_escape = esc && str[cur] == esc && !in_escape; cur++; } // .bwc. cur == from can happen when we have a trailing separator. // (both are pointing at the null terminator in this case) if(cur != from) { ret.append(str.substr(from, cur)); } return ret; }