16373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman/*
26373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman * Copyright 2016 Google Inc.
36373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman *
46373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman * Use of this source code is governed by a BSD-style license that can be
56373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman * found in the LICENSE file.
66373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman */
76373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman
86373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#include "SkStream.h"
96373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman
106373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#if defined(SK_BUILD_FOR_MAC)
116373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#include <ApplicationServices/ApplicationServices.h>
126373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#elif defined(SK_BUILD_FOR_WIN)
136373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#include <windows.h>
146373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#endif
156373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman
166373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosmanint main(int argc, char** argv) {
176373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#if defined(SK_BUILD_FOR_MAC)
186373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    CGColorSpaceRef cs = CGDisplayCopyColorSpace(CGMainDisplayID());
196373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    CFDataRef dataRef = CGColorSpaceCopyICCProfile(cs);
206373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    const uint8_t* data = CFDataGetBytePtr(dataRef);
216373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    size_t size = CFDataGetLength(dataRef);
2263fd760a37905c45d26fc3d49cac261fad1b4808Ben Wagner
236373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    SkFILEWStream file("monitor_0.icc");
246373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    file.write(data, size);
2563fd760a37905c45d26fc3d49cac261fad1b4808Ben Wagner
266373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    CFRelease(cs);
276373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    CFRelease(dataRef);
286373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    return 0;
296373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#elif defined(SK_BUILD_FOR_WIN)
306373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    DISPLAY_DEVICE dd = { sizeof(DISPLAY_DEVICE) };
316373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    SkString outputFilename;
326373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman
336373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    // Chrome's code for this currently just gets the primary monitor's profile. This code iterates
346373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    // over all attached monitors, so it's "better" in that sense. Making intelligent use of this
356373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    // information (via things like MonitorFromWindow or MonitorFromRect to pick the correct
366373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    // profile for a particular window or region of a window), is an exercise left to the reader.
376373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    for (int i = 0; EnumDisplayDevices(NULL, i, &dd, 0); ++i) {
386373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman        if (dd.StateFlags & DISPLAY_DEVICE_ATTACHED_TO_DESKTOP) {
396373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman            // There are other helpful things in dd at this point:
406373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman            // dd.DeviceString has a longer name for the adapter
416373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman            // dd.StateFlags indicates primary display, mirroring, etc...
426373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman            HDC dc = CreateDC(NULL, dd.DeviceName, NULL, NULL);
436373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman            if (dc) {
446373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                char icmPath[MAX_PATH + 1];
456373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                DWORD pathLength = MAX_PATH;
466373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                if (GetICMProfile(dc, &pathLength, icmPath)) {
476373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                    // GetICMProfile just returns the path to the installed profile (not the data)
486373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                    outputFilename = SkStringPrintf("monitor_%d.icc", i);
496373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                    CopyFile(icmPath, outputFilename.c_str(), FALSE);
506373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                }
516373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman                DeleteDC(dc);
526373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman            }
536373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman        }
546373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    }
556373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman
566373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    return 0;
576373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#else
586373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    SkDebugf("ERROR: Unsupported platform\n");
596373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman    return 1;
606373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman#endif
616373c955541f6ebbb075ee6b2a58daa22ea9cecfbrianosman}
62