mbed-os/TEST_APPS/device/nfcapp/SmartPoster.cpp

248 lines
6.0 KiB
C++

/* Copyright (c) 2018 ARM Limited. All rights reserved.
* SPDX-License-Identifier: Apache-2.0
* Licensed under the Apache License, Version 2.0 (the License); you may
* not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an AS IS BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "SmartPoster.h"
#include "nfc/ndef/common/Text.h"
#include "nfc/ndef/common/URI.h"
#include "nfc/ndef/common/Mime.h"
#include "nfc/ndef/MessageBuilder.h"
#include "nfc/ndef/common/util.h"
using mbed::Span;
using mbed::nfc::ndef::MessageBuilder;
using mbed::nfc::ndef::RecordType;
using mbed::nfc::ndef::Record;
using mbed::nfc::ndef::RecordID;
using mbed::nfc::ndef::RecordPayload;
using mbed::nfc::ndef::common::span_from_cstr;
using mbed::nfc::ndef::common::Mime;
using mbed::nfc::ndef::common::Text;
using mbed::nfc::ndef::common::URI;
// todo: this class probably needs to be in the nfc module itself
namespace {
static RecordType smart_poster_record_type()
{
return RecordType(RecordType::well_known_type, span_from_cstr("Sp"));
}
static RecordType action_record_type()
{
return RecordType(RecordType::well_known_type, span_from_cstr("act"));
}
static RecordType size_record_type()
{
return RecordType(RecordType::well_known_type, span_from_cstr("s"));
}
static RecordType type_record_type()
{
return RecordType(RecordType::well_known_type, span_from_cstr("T"));
}
static size_t compute_record_size(const RecordType &type,
const RecordPayload &payload)
{
return MessageBuilder::compute_record_size(
Record(type, payload, RecordID(), false, false));
}
} // end of anonymous namespace
SmartPoster::SmartPoster(const URI &uri) :
_uri(uri), _action(), _resource_size(0), _action_set(false), _resource_size_set(
false)
{
}
void SmartPoster::set_title(const Text &text)
{
_title = text;
}
void SmartPoster::set_icon(const Mime &icon)
{
_icon = icon;
}
void SmartPoster::set_action(action_t action)
{
_action = action;
_action_set = true;
}
void SmartPoster::set_resource_size(uint32_t size)
{
_resource_size = size;
_resource_size_set = true;
}
void SmartPoster::set_resource_type(Span<const uint8_t> &type)
{
_type.set_text(Text::UTF8, Span<const uint8_t>(), type);
}
bool SmartPoster::append_record(MessageBuilder &ndef_builder,
bool is_last_record) const
{
if (_uri.get_uri_field().empty()) {
return false;
}
struct PayloadBuilder: MessageBuilder::PayloadBuilder {
PayloadBuilder(const SmartPoster &sp) :
sp(sp)
{
}
virtual size_t size() const
{
return sp.get_uri_record_size() + sp.get_title_record_size()
+ sp.get_icon_record_size() + sp.get_action_record_size()
+ sp.get_resource_size_record_size()
+ sp.get_type_record_size();
}
virtual void build(const Span<uint8_t> &buffer) const
{
MessageBuilder smart_poster_builder(buffer);
sp.append_title(smart_poster_builder);
sp.append_icon(smart_poster_builder);
sp.append_resource_size(smart_poster_builder);
sp.append_type(smart_poster_builder);
sp.append_action(smart_poster_builder);
sp.append_uri(smart_poster_builder);
}
const SmartPoster &sp;
};
bool result = ndef_builder.append_record(smart_poster_record_type(),
PayloadBuilder(*this), is_last_record);
return result;
}
void SmartPoster::append_uri(MessageBuilder &builder) const
{
_uri.append_as_record(builder, true);
}
size_t SmartPoster::get_uri_record_size() const
{
return _uri.get_record_size();
}
void SmartPoster::append_title(MessageBuilder &builder) const
{
if (_title.get_text().empty()) {
return;
}
_title.append_as_record(builder);
}
size_t SmartPoster::get_title_record_size() const
{
if (_title.get_text().empty()) {
return 0;
}
return _title.get_record_size();
}
void SmartPoster::append_icon(MessageBuilder &builder) const
{
if (_icon.get_mime_content().empty()) {
return;
}
_icon.append_as_record(builder);
}
size_t SmartPoster::get_icon_record_size() const
{
if (_icon.get_mime_content().empty()) {
return 0;
}
return _icon.get_record_size();
}
void SmartPoster::append_action(MessageBuilder &builder) const
{
if (!_action_set) {
return;
}
const uint8_t action_value[1] = { _action };
builder.append_record(action_record_type(), action_value);
}
size_t SmartPoster::get_action_record_size() const
{
if (!_action_set) {
return 0;
}
const uint8_t action_value[1] = { _action };
return compute_record_size(action_record_type(), action_value);
}
void SmartPoster::append_resource_size(MessageBuilder &builder) const
{
if (!_resource_size_set) {
return;
}
uint8_t value[4];
std::reverse_copy(&_resource_size, &_resource_size + 4, value);
builder.append_record(size_record_type(), value);
}
size_t SmartPoster::get_resource_size_record_size() const
{
if (!_resource_size_set) {
return 0;
}
uint8_t value[4];
return compute_record_size(size_record_type(), value);
}
void SmartPoster::append_type(MessageBuilder &builder) const
{
if (_type.get_text().empty()) {
return;
}
builder.append_record(type_record_type(), _type.get_text());
}
size_t SmartPoster::get_type_record_size() const
{
if (_type.get_text().empty()) {
return 0;
}
return compute_record_size(type_record_type(), _type.get_text());
}