• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2017 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef SKSL_STRING
9 #define SKSL_STRING
10 
11 #include <cstring>
12 
13 #define SKSL_USE_STD_STRING
14 
15 #include <stdarg.h>
16 
17 #ifdef SKSL_USE_STD_STRING
18     #define SKSL_STRING_BASE std::string
19     #include <string>
20 #else
21     #define SKSL_STRING_BASE SkString
22     #include "SkString.h"
23 #endif
24 
25 namespace SkSL {
26 
27 // Represents a (not necessarily null-terminated) slice of a string.
28 struct StringFragment {
StringFragmentStringFragment29     StringFragment()
30     : fChars("")
31     , fLength(0) {}
32 
StringFragmentStringFragment33     StringFragment(const char* chars)
34     : fChars(chars)
35     , fLength(strlen(chars)) {}
36 
StringFragmentStringFragment37     StringFragment(const char* chars, size_t length)
38     : fChars(chars)
39     , fLength(length) {}
40 
41     char operator[](size_t idx) const {
42         return fChars[idx];
43     }
44 
45     bool operator==(const char* s) const;
46     bool operator!=(const char* s) const;
47     bool operator==(StringFragment s) const;
48     bool operator!=(StringFragment s) const;
49     bool operator<(StringFragment s) const;
50 
51     const char* fChars;
52     size_t fLength;
53 };
54 
55 bool operator==(const char* s1, StringFragment s2);
56 
57 bool operator!=(const char* s1, StringFragment s2);
58 
59 class String : public SKSL_STRING_BASE {
60 public:
61     String() = default;
62     String(const String&) = default;
63     String(String&&) = default;
64     String& operator=(const String&) = default;
65     String& operator=(String&&) = default;
66 
67 #ifndef SKSL_USE_STD_STRING
String(const SkString & s)68     String(const SkString& s)
69     : INHERITED(s) {}
70 #endif
71 
String(const char * s)72     String(const char* s)
73     : INHERITED(s) {}
74 
String(const char * s,size_t size)75     String(const char* s, size_t size)
76     : INHERITED(s, size) {}
77 
String(StringFragment s)78     String(StringFragment s)
79     : INHERITED(s.fChars, s.fLength) {}
80 
81     static String printf(const char* fmt, ...);
82 
83 #ifdef SKSL_USE_STD_STRING
84     void appendf(const char* fmt, ...);
85     // For API compatibility with SkString's reset (vs. std:string's clear)
86     void reset();
87     // For API compatibility with SkString's findLastOf(vs. find_last_of -> size_t)
88     int findLastOf(const char c) const;
89 #endif
90     void vappendf(const char* fmt, va_list va);
91 
92     bool startsWith(const char* s) const;
93     bool endsWith(const char* s) const;
94 
95     int find(const char* substring, int fromPos = 0) const;
96     int find(const String& substring, int fromPos = 0) const;
97 
98     String operator+(const char* s) const;
99     String operator+(const String& s) const;
100     String operator+(StringFragment s) const;
101     String& operator+=(char c);
102     String& operator+=(const char* s);
103     String& operator+=(const String& s);
104     String& operator+=(StringFragment s);
105     bool operator==(const char* s) const;
106     bool operator!=(const char* s) const;
107     bool operator==(const String& s) const;
108     bool operator!=(const String& s) const;
109     friend String operator+(const char* s1, const String& s2);
110     friend bool operator==(const char* s1, const String& s2);
111     friend bool operator!=(const char* s1, const String& s2);
112 
113 private:
114     typedef SKSL_STRING_BASE INHERITED;
115 };
116 
117 String operator+(const char* s1, const String& s2);
118 bool operator!=(const char* s1, const String& s2);
119 
120 String to_string(double value);
121 
122 String to_string(int32_t value);
123 
124 String to_string(uint32_t value);
125 
126 String to_string(int64_t value);
127 
128 String to_string(uint64_t value);
129 
130 int stoi(const String& s);
131 
132 double stod(const String& s);
133 
134 long stol(const String& s);
135 
136 } // namespace
137 
138 namespace std {
139     template<> struct hash<SkSL::StringFragment> {
140         size_t operator()(const SkSL::StringFragment& s) const {
141             size_t result = 0;
142             for (size_t i = 0; i < s.fLength; ++i) {
143                 result = result * 101 + s.fChars[i];
144             }
145             return result;
146         }
147     };
148 } // namespace
149 
150 #ifdef SKSL_USE_STD_STRING
151 namespace std {
152     template<> struct hash<SkSL::String> {
153         size_t operator()(const SkSL::String& s) const {
154             return hash<std::string>{}(s);
155         }
156     };
157 } // namespace
158 #else
159 #include "SkOpts.h"
160 namespace std {
161     template<> struct hash<SkSL::String> {
162         size_t operator()(const SkSL::String& s) const {
163             return SkOpts::hash_fn(s.c_str(), s.size(), 0);
164         }
165     };
166 } // namespace
167 #endif // SKIA_STANDALONE
168 
169 #endif
170