1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef CONTENT_COMMON_MAC_ATTRIBUTED_STRING_CODER_H_
6 #define CONTENT_COMMON_MAC_ATTRIBUTED_STRING_CODER_H_
7 
8 #include <set>
9 
10 #include "base/strings/string16.h"
11 #include "content/common/content_export.h"
12 #include "ipc/ipc_message_utils.h"
13 #include "ui/gfx/range/range.h"
14 
15 #if __OBJC__
16 @class NSAttributedString;
17 @class NSDictionary;
18 #else
19 class NSAttributedString;
20 class NSDictionary;
21 #endif
22 
23 namespace base {
24 class Pickle;
25 class PickleIterator;
26 }
27 
28 namespace mac {
29 
30 // This class will serialize the font information of an NSAttributedString so
31 // that it can be sent over IPC. This class only stores the information of the
32 // NSFontAttributeName. The motive is that of security: using NSArchiver and
33 // friends to send objects from the renderer to the browser could lead to
34 // deserialization of arbitrary objects. This class restricts serialization to
35 // a specific object class and specific attributes of that object.
36 class CONTENT_EXPORT AttributedStringCoder {
37  public:
38   // A C++ IPC-friendly representation of the NSFontAttributeName attribute
39   // set.
40   class FontAttribute {
41    public:
42     FontAttribute(NSDictionary* ns_attributes, gfx::Range effective_range);
43     FontAttribute(const base::string16& font_name,
44                   float font_point_size,
45                   const gfx::Range& range);
46     FontAttribute();
47     ~FontAttribute();
48 
49     // Creates an autoreleased NSDictionary that can be attached to an
50     // NSAttributedString.
51     NSDictionary* ToAttributesDictionary() const;
52 
53     // Whether or not the attribute should be placed in the EncodedString. This
54     // can return false, e.g. if the Cocoa-based constructor can't find any
55     // information to encode.
56     bool ShouldEncode() const;
57 
58     // Accessors:
font_name()59     const base::string16& font_name() const { return font_name_; }
font_point_size()60     float font_point_size() const { return font_point_size_; }
effective_range()61     const gfx::Range& effective_range() const { return effective_range_; }
62 
63    private:
64     base::string16 font_name_;
65     float font_point_size_;
66     gfx::Range effective_range_;
67   };
68 
69   // A class that contains the pertinent information from an NSAttributedString,
70   // which can be serialized over IPC.
71   class EncodedString {
72    public:
73     explicit EncodedString(base::string16 string);
74     EncodedString();
75     EncodedString(const EncodedString& other);
76     EncodedString& operator=(const EncodedString& other);
77     ~EncodedString();
78 
79     // Accessors:
string()80     base::string16 string() const { return string_; }
attributes()81     const std::vector<FontAttribute>& attributes() const {
82       return attributes_;
83     }
attributes()84     std::vector<FontAttribute>* attributes() { return &attributes_; }
85 
86    private:
87     // The plain-text string.
88     base::string16 string_;
89     // The set of attributes that style |string_|.
90     std::vector<FontAttribute> attributes_;
91   };
92 
93   // Takes an NSAttributedString, extracts the pertinent attributes, and returns
94   // an object that represents it. Caller owns the result.
95   static const EncodedString* Encode(NSAttributedString* str);
96 
97   // Returns an autoreleased NSAttributedString from an encoded representation.
98   static NSAttributedString* Decode(const EncodedString* str);
99 
100  private:
101   AttributedStringCoder();
102 };
103 
104 }  // namespace mac
105 
106 // IPC ParamTraits specialization //////////////////////////////////////////////
107 
108 namespace IPC {
109 
110 template <>
111 struct ParamTraits<mac::AttributedStringCoder::EncodedString> {
112   typedef mac::AttributedStringCoder::EncodedString param_type;
113   static void Write(base::Pickle* m, const param_type& p);
114   static bool Read(const base::Pickle* m,
115                    base::PickleIterator* iter,
116                    param_type* r);
117   static void Log(const param_type& p, std::string* l);
118 };
119 
120 template <>
121 struct ParamTraits<mac::AttributedStringCoder::FontAttribute> {
122   typedef mac::AttributedStringCoder::FontAttribute param_type;
123   static void Write(base::Pickle* m, const param_type& p);
124   static bool Read(const base::Pickle* m,
125                    base::PickleIterator* iter,
126                    param_type* r);
127   static void Log(const param_type& p, std::string* l);
128 };
129 
130 }  // namespace IPC
131 
132 #endif  // CONTENT_COMMON_MAC_ATTRIBUTED_STRING_CODER_H_
133