Pen Settings

HTML

CSS

CSS Base

Vendor Prefixing

Add External Stylesheets/Pens

Any URL's added here will be added as <link>s in order, and before the CSS in the editor. If you link to another Pen, it will include the CSS from that Pen. If the preprocessor matches, it will attempt to combine them before processing.

+ add another resource

JavaScript

Babel is required to process package imports. If you need a different preprocessor remove all packages first.

Add External Scripts/Pens

Any URL's added here will be added as <script>s in order, and run before the JavaScript in the editor. You can use the URL of any other Pen and it will include the JavaScript from that Pen.

+ add another resource

Behavior

Save Automatically?

If active, Pens will autosave every 30 seconds after being saved once.

Auto-Updating Preview

If enabled, the preview panel updates automatically as you code. If disabled, use the "Run" button to update.

Format on Save

If enabled, your code will be formatted when you actively save your Pen. Note: your code becomes un-folded during formatting.

Editor Settings

Code Indentation

Want to change your Syntax Highlighting theme, Fonts and more?

Visit your global Editor Settings.

HTML

              
                <script src="https://s.picdn.net/editor/image/assets/integration.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.15.10/highlight.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.15.10/languages/javascript.min.js"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/9.15.10/styles/a11y-light.min.css" />
  
<main>
  <h2>License Shutterstock assets while using Editor</h2>
  <p>This page demonstrates how to license Shutterstock images for end-users inside of Shutterstock Editor with the use of the Shutterstock API.</p>

  <p>
    See <a target="_blank" href="https://developers.shutterstock.com/documentation/editor-integration">documentation</a> for more help.
  </p>
  <hr />
  <code><span style="color: #777">Status: </span><span id="status">Loading...</span></code>
  
  <br />
  <p>Click
    <button id="show">show</button> to display Editor. (Or <button id="hide">hide</button> to hide it.)</p>
  <hr />
  <div id="info">
    <p>By using the <code>getShutterstockAssetIds</code> method, you can retrieve the IDs of assets in a design. Using the Shutterstock API, you can retrieve URLs to licensed versions of those images. Finally, the <a href="https://developers.shutterstock.com/documentation/editor-integration#gatekeeperurls">gatekeeperUrls</a> section of the documentation covers how to pass unwatermarked URLs to Editor when retrieving image data. These steps together allow you to license images in a design without any user intervention.</p>
    <p>Below is a code example that demonstrates that.</p>
    
    <div>Code example:</div>
    <pre>
<code class="javascript">

function yourLicensingLogic(imageIds) {
  // Logic that receives an array of image ids,
  // determines whether to license them,
  // and retrieves/returns an array of
  // unwatermarked id/url pairs, like so:
  return Promise.resolve([
    {
      id: 123,
      url: 'valid_url'
    }
  ]);
}

function renderImage() {
  editor.getShutterstockAssetIds().then(assetIds => {
    return yourLicensingLogic(assetIds);
  })
  .then(gatekeeperUrls => {
    return editor.getBase64({ gatekeeperUrls });
  }).then(renderedImage => {
    document.querySelector('#output-image').setAttribute('src', imageData);
  })
}

editor.on('primaryaction', renderImage);
</code>
</pre>
    <br />
    <p><i>Click on the save button in the Editor SDK to initiate a render. The image of the design will be replaced with a placeholder image.</i></p>
    <img id="output-image" />
    
    <div id="target"></div>

</div>

</main>
              
            
!

CSS

              
                body {
  font-family: sans-serif;
}

main {
  max-width: 800px;
  margin: auto;
  margin-top: 40px;
}


#info {
  margin-top: 30px;
}

hr {
  margin: 30px 0;
}

#target iframe {
  height: 500px;
  border: none;
  margin-top: 30px;
}
              
            
!

JS

              
                const originalDesign = {
  "state": {
    "pages": [
      {
        "id": 1,
        "width": 200,
        "height": 200,
        "active": true,
        "selected": false,
        "presetId": -1,
        "assetId": "224856823"
      }
    ],
    "doc": {
      "fabric": {
        "pages": [
          {
            "backgroundImageId": "ryytqLrLH-3",
            "data": {
              "objects": [
                {
                  "type": "editorImage",
                  "originX": "center",
                  "originY": "center",
                  "left": 100,
                  "top": 100,
                  "width": 1500,
                  "height": 1500,
                  "fill": "rgb(0,0,0)",
                  "stroke": "rgba(0, 0, 0, 1)",
                  "strokeWidth": 1,
                  "strokeDashArray": null,
                  "strokeLineCap": "butt",
                  "strokeLineJoin": "miter",
                  "strokeMiterLimit": 4,
                  "scaleX": 0.13333333,
                  "scaleY": 0.13333333,
                  "angle": 0,
                  "flipX": false,
                  "flipY": false,
                  "opacity": 1,
                  "shadow": {
                    "color": "rgba(0, 0, 0, 0.2)",
                    "blur": 10,
                    "offsetX": 3,
                    "offsetY": 3,
                    "affectStroke": false,
                    "enabled": false
                  },
                  "visible": true,
                  "fillRule": "nonzero",
                  "paintFirst": "fill",
                  "skewX": 0,
                  "skewY": 0,
                  "isLocked": false,
                  "perspective": null,
                  "id": "ryytqLrLH-3",
                  "strokeNofill": true,
                  "strokeUniform": true,
                  "isPlaceholder": false,
                  "crossOrigin": "anonymous",
                  "cropX": 0,
                  "cropY": 0,
                  "imageId": "224856823",
                  "signatureBarHeight": 0,
                  "isInPerspectiveMode": false,
                  "isCropping": false,
                  "vignetteStrength": 0,
                  "src": "https://image.shutterstock.com/z/photo-slug-224856823.jpg",
                  "filters": [],
                  "fileTitle": "224856823",
                  "clipPathObject": null,
                  "aspectRatio": 1
                }
              ],
              "backgroundImage": {
                "type": "editorArtboard",
                "originX": "center",
                "originY": "center",
                "left": 100,
                "top": 100,
                "width": 200,
                "height": 200,
                "fill": "#ccc",
                "opacity": 1
              }
            },
            "id": 1
          }
        ],
        "textSelectionStart": null,
        "textSelectionEnd": null
      },
      "printResolution": {
        "dotsPerUnit": 300,
        "units": "PIXELS"
      }
    }
  }
};

function init() {
  const editor = window.Editor({
    apiKey: 'k4m3J9SvPBs4clbaPI6ebOUi',
    container: document.querySelector('#target'),
    initialPanel: 'none',
  });
  
  window.editor = editor;
  
  editor.launch();

  editor.on("error", errorHandler);
  editor.on("open", readyHandler);
  editor.on('close', closeHandler);
  
  function yourLicensingLogic(imageIds) {
    return new Promise(function(resolve, reject) {
      setTimeout(() => {
        setStatus('External "licensing" step complete.');
        resolve(imageIds.map(id => {
          return { id, url: 'https://www.shutterstock.com/editor/image/corsimage.jpg'};
        }))
      }, 1000);
    })
  }
  editor.on('primaryaction', function() {
    editor.getShutterstockAssetIds().then(imageIds => {
      console.log({ imageIds });
      setStatus(`Retrieved imageIds: ${JSON.stringify(imageIds)}`);
      return yourLicensingLogic(imageIds);
    }).then(gatekeeperUrls => {
      return editor.getBase64({ gatekeeperUrls});
    }).then(imageData => {
      document.querySelector('#output-image').setAttribute('src', imageData);
      setStatus('Image rendered.');
      editor.hide();
    })
  });
}

function closeHandler() {
    editor.hide();
  }

function setStatus(m) {
  document.querySelector("#status").innerText = m;
}

function errorHandler(e) {
  if (e.type === 401) {
    setStatus("Error: invalid SDK key");
  }
}

function showHandler() {
  editor.show();
}
document.querySelector('#show').addEventListener('click', showHandler);

function hideHandler() {
  editor.hide();
}
document.querySelector('#hide').addEventListener('click', hideHandler);

function readyHandler() {
  setStatus('Ready.');
  editor.setDesign(originalDesign);
}

init();


hljs.initHighlightingOnLoad();</script>
              
            
!
999px

Console