Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(20)

Side by Side Diff: ui/gfx/icc_profile.cc

Issue 2755953005: color: Use SkColorSpaceXform instead of QCMS for LUTs (Closed)
Patch Set: Rebase Created 3 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « ui/gfx/color_transform.cc ('k') | ui/gfx/icc_profile_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "ui/gfx/icc_profile.h" 5 #include "ui/gfx/icc_profile.h"
6 6
7 #include <list> 7 #include <list>
8 8
9 #include "base/containers/mru_cache.h" 9 #include "base/containers/mru_cache.h"
10 #include "base/lazy_instance.h" 10 #include "base/lazy_instance.h"
11 #include "base/synchronization/lock.h" 11 #include "base/synchronization/lock.h"
12 #include "third_party/skia/include/core/SkColorSpaceXform.h"
12 #include "third_party/skia/include/core/SkICC.h" 13 #include "third_party/skia/include/core/SkICC.h"
13 #include "ui/gfx/color_transform.h" 14 #include "ui/gfx/color_transform.h"
14 #include "ui/gfx/skia_color_space_util.h" 15 #include "ui/gfx/skia_color_space_util.h"
15 16
16 namespace gfx { 17 namespace gfx {
17 18
18 const uint64_t ICCProfile::test_id_adobe_rgb_ = 1; 19 const uint64_t ICCProfile::test_id_adobe_rgb_ = 1;
19 const uint64_t ICCProfile::test_id_color_spin_ = 2; 20 const uint64_t ICCProfile::test_id_color_spin_ = 2;
20 const uint64_t ICCProfile::test_id_generic_rgb_ = 3; 21 const uint64_t ICCProfile::test_id_generic_rgb_ = 3;
21 const uint64_t ICCProfile::test_id_srgb_ = 4; 22 const uint64_t ICCProfile::test_id_srgb_ = 4;
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
64 65
65 // static 66 // static
66 ICCProfile ICCProfile::FromData(const void* data, size_t size) { 67 ICCProfile ICCProfile::FromData(const void* data, size_t size) {
67 return FromDataWithId(data, size, 0); 68 return FromDataWithId(data, size, 0);
68 } 69 }
69 70
70 // static 71 // static
71 ICCProfile ICCProfile::FromDataWithId(const void* data, 72 ICCProfile ICCProfile::FromDataWithId(const void* data,
72 size_t size, 73 size_t size,
73 uint64_t new_profile_id) { 74 uint64_t new_profile_id) {
74 if (!size) { 75 if (!size)
75 DLOG(ERROR) << "Invalid empty ICC profile.";
76 return ICCProfile(); 76 return ICCProfile();
77 }
78 77
79 const char* data_as_char = reinterpret_cast<const char*>(data); 78 const char* data_as_char = reinterpret_cast<const char*>(data);
80 { 79 {
81 // Linearly search the cached ICC profiles to find one with the same data. 80 // Linearly search the cached ICC profiles to find one with the same data.
82 // If it exists, re-use its id and touch it in the cache. 81 // If it exists, re-use its id and touch it in the cache.
83 Cache& cache = g_cache.Get(); 82 Cache& cache = g_cache.Get();
84 base::AutoLock lock(cache.lock); 83 base::AutoLock lock(cache.lock);
85 for (auto iter = cache.id_to_icc_profile_mru.begin(); 84 for (auto iter = cache.id_to_icc_profile_mru.begin();
86 iter != cache.id_to_icc_profile_mru.end(); ++iter) { 85 iter != cache.id_to_icc_profile_mru.end(); ++iter) {
87 const std::vector<char>& iter_data = iter->second.data_; 86 const std::vector<char>& iter_data = iter->second.data_;
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after
169 auto found = cache.id_to_icc_profile_mru.Get(id_); 168 auto found = cache.id_to_icc_profile_mru.Get(id_);
170 if (found != cache.id_to_icc_profile_mru.end()) { 169 if (found != cache.id_to_icc_profile_mru.end()) {
171 color_space_ = found->second.color_space_; 170 color_space_ = found->second.color_space_;
172 parametric_color_space_ = found->second.parametric_color_space_; 171 parametric_color_space_ = found->second.parametric_color_space_;
173 successfully_parsed_by_sk_icc_ = 172 successfully_parsed_by_sk_icc_ =
174 found->second.successfully_parsed_by_sk_icc_; 173 found->second.successfully_parsed_by_sk_icc_;
175 return; 174 return;
176 } 175 }
177 } 176 }
178 177
178 // Parse the profile and attempt to create a SkColorSpaceXform out of it.
179 sk_sp<SkColorSpace> sk_srgb_color_space = SkColorSpace::MakeSRGB();
179 sk_sp<SkICC> sk_icc = SkICC::Make(data_.data(), data_.size()); 180 sk_sp<SkICC> sk_icc = SkICC::Make(data_.data(), data_.size());
180 if (sk_icc) { 181 sk_sp<SkColorSpace> sk_icc_color_space;
182 std::unique_ptr<SkColorSpaceXform> sk_color_space_xform;
183 if (sk_icc)
184 sk_icc_color_space = SkColorSpace::MakeICC(data_.data(), data_.size());
185 if (sk_icc_color_space) {
186 sk_color_space_xform = SkColorSpaceXform::New(sk_srgb_color_space.get(),
187 sk_icc_color_space.get());
188 }
189
190 // Attempt to extract a parametric represetation for this space.
191 if (sk_color_space_xform) {
181 bool parametric_color_space_is_accurate = false; 192 bool parametric_color_space_is_accurate = false;
182 successfully_parsed_by_sk_icc_ = true; 193 successfully_parsed_by_sk_icc_ = true;
183 194
184 // Populate |parametric_color_space_| as a primary matrix and analytic 195 // Populate |parametric_color_space_| as a primary matrix and analytic
185 // transfer function, if possible. 196 // transfer function, if possible.
186 SkMatrix44 to_XYZD50_matrix; 197 SkMatrix44 to_XYZD50_matrix;
187 if (sk_icc->toXYZD50(&to_XYZD50_matrix)) { 198 if (sk_icc->toXYZD50(&to_XYZD50_matrix)) {
188 SkColorSpaceTransferFn fn; 199 SkColorSpaceTransferFn fn;
189 // First try to get a numerical transfer function from the profile. 200 // First try to get a numerical transfer function from the profile.
190 if (sk_icc->isNumericalTransferFn(&fn)) { 201 if (sk_icc->isNumericalTransferFn(&fn)) {
(...skipping 28 matching lines...) Expand all
219 // If the approximation is accurate, then set |parametric_color_space_| and 230 // If the approximation is accurate, then set |parametric_color_space_| and
220 // |color_space_| to the same value, and link them to |this|. Otherwise, set 231 // |color_space_| to the same value, and link them to |this|. Otherwise, set
221 // them separately, and do not link |parametric_color_space_| to |this|. 232 // them separately, and do not link |parametric_color_space_| to |this|.
222 if (parametric_color_space_is_accurate) { 233 if (parametric_color_space_is_accurate) {
223 parametric_color_space_.icc_profile_id_ = id_; 234 parametric_color_space_.icc_profile_id_ = id_;
224 color_space_ = parametric_color_space_; 235 color_space_ = parametric_color_space_;
225 } else { 236 } else {
226 color_space_ = ColorSpace(ColorSpace::PrimaryID::ICC_BASED, 237 color_space_ = ColorSpace(ColorSpace::PrimaryID::ICC_BASED,
227 ColorSpace::TransferID::ICC_BASED); 238 ColorSpace::TransferID::ICC_BASED);
228 color_space_.icc_profile_id_ = id_; 239 color_space_.icc_profile_id_ = id_;
229 color_space_.icc_profile_sk_color_space_ = 240 color_space_.icc_profile_sk_color_space_ = sk_icc_color_space;
230 SkColorSpace::MakeICC(data_.data(), data_.size());
231 } 241 }
242 } else if (sk_icc_color_space) {
243 DLOG(ERROR) << "Parsed ICCProfile, but unable to create an "
244 "SkColorSpaceXform from it.";
245 successfully_parsed_by_sk_icc_ = false;
232 } else { 246 } else {
233 DLOG(ERROR) << "Unable parse ICCProfile."; 247 DLOG(ERROR) << "Unable to parse ICCProfile.";
234 successfully_parsed_by_sk_icc_ = false; 248 successfully_parsed_by_sk_icc_ = false;
235 } 249 }
236 250
237 // Add to the cache. 251 // Add to the cache.
238 { 252 {
239 Cache& cache = g_cache.Get(); 253 Cache& cache = g_cache.Get();
240 base::AutoLock lock(cache.lock); 254 base::AutoLock lock(cache.lock);
241 cache.id_to_icc_profile_mru.Put(id_, *this); 255 cache.id_to_icc_profile_mru.Put(id_, *this);
242 } 256 }
243 } 257 }
244 258
245 } // namespace gfx 259 } // namespace gfx
OLDNEW
« no previous file with comments | « ui/gfx/color_transform.cc ('k') | ui/gfx/icc_profile_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698