- From: Domenic Denicola <notifications@github.com>
- Date: Mon, 13 Dec 2021 09:22:59 -0800
- To: w3c/clipboard-apis <clipboard-apis@noreply.github.com>
- Cc: Subscribed <subscribed@noreply.github.com>
- Message-ID: <w3c/clipboard-apis/pull/158/review/830520504@github.com>
@domenic commented on this pull request. > - Promise<Blob> getType(DOMString type); - }; + <dt><code><var>clipboardItem</var>.<var>types</var></code> + <dd><p>Returns the list of <var>types</var> contained in the <var>clipboardItem</var> object. + + </dl> + + <h4 id="clipboard-item">Clipboard Item</h4> + + A [=clipboard item=] is conceptually data that the user has expressed a desire to make shareable by invoking a "cut" or "copy" command. This should be a definition, i.e. `A <dfn>clipboard item</dfn> is...`. You can either formally make it a `[=struct=]` with `[=struct/items=]`, as @mbrodesser suggests, or just say what it's associated values are (i.e. its list of representations and presentation style) like you do now. > + <dt><code><var>clipboardItem</var>.<var>types</var></code> + <dd><p>Returns the list of <var>types</var> contained in the <var>clipboardItem</var> object. + + </dl> + + <h4 id="clipboard-item">Clipboard Item</h4> + + A [=clipboard item=] is conceptually data that the user has expressed a desire to make shareable by invoking a "cut" or "copy" command. + + <p class=note> + For example, if a user copies a range of cells from a spreadsheet of a native application, it will result in one [=clipboard item=]. If a user copies a set of files from their desktop, that list of files will be represented by multiple [=clipboard item=]s. + </p> + + Some platforms may support having more than one [=clipboard item=] at a time on the [=Clipboard=], while other platforms replace the previous [=clipboard item=] with the new one. + + A [=clipboard item=] has a <dfn>list of representations</dfn>, each <dfn>representation</dfn> with an associated [=mime type=] and <dfn>data</dfn>. ```suggestion A [=clipboard item=] has a <dfn>list of representations</dfn>, each <dfn>representation</dfn> with an associated <dfn for="representation">mime type</dfn> (a [=MIME type=]) and <dfn for="representation">data</dfn> (a {{ClipboardItemData}}). ``` > + <p class=note> + Making the range of cells available as an image will allow the user to paste the cells into a photo editing app, while the text/plain format can be used by text editor apps. + </p> + + A [=clipboard item=] can also optionally have a <dfn>presentation style</dfn> that helps distinguish whether apps "pasting" a [=clipboard item=] should insert the contents of an appropriate [=representation=] inline at the point of paste or if it should be treated as an attachment. + + Apps that support pasting only a single [=clipboard item=] should use the first [=clipboard item=]. + Apps that support pasting more than one [=clipboard item=] could, for example, provide a user interface that previews the contents of each [=clipboard item=] and allow the user to choose which one to paste. + Further, apps are expected to enumerate the [=mime type=]s of the [=clipboard item=] they are pasting and select the one best-suited for the app according to some app-specific algorithm. + Alternatively, an app can present the user with options on how to paste a [=clipboard item=], e.g. "paste as image" or "paste formatted text", etc. + + A {{ClipboardItem}} object has an associated <dfn for="ClipboardItem">clipboard item</dfn>, which is a [=clipboard item=]. + + A {{ClipboardItem}} object has an associated <dfn for="ClipboardItem">types array</dfn>, which is a {{FrozenArray}}. + + To <dfn>create a {{ClipboardItem}} object</dfn>, given a [=clipboard item=] |clipboardItem|'s [=relevant realm=] |realm|, run these steps: ```suggestion To <dfn>create a {{ClipboardItem}} object</dfn>, given a [=clipboard item=] |clipboardItem| and a [=Realm=] |realm|: ``` > + + Apps that support pasting only a single [=clipboard item=] should use the first [=clipboard item=]. + Apps that support pasting more than one [=clipboard item=] could, for example, provide a user interface that previews the contents of each [=clipboard item=] and allow the user to choose which one to paste. + Further, apps are expected to enumerate the [=mime type=]s of the [=clipboard item=] they are pasting and select the one best-suited for the app according to some app-specific algorithm. + Alternatively, an app can present the user with options on how to paste a [=clipboard item=], e.g. "paste as image" or "paste formatted text", etc. + + A {{ClipboardItem}} object has an associated <dfn for="ClipboardItem">clipboard item</dfn>, which is a [=clipboard item=]. + + A {{ClipboardItem}} object has an associated <dfn for="ClipboardItem">types array</dfn>, which is a {{FrozenArray}}. + + To <dfn>create a {{ClipboardItem}} object</dfn>, given a [=clipboard item=] |clipboardItem|'s [=relevant realm=] |realm|, run these steps: + 1. Let |clipboardItemObject| be a [=new=] {{ClipboardItem}} with |realm|. + + 1. Set |clipboardItemObject|'s [=clipboard item=] to |clipboardItem|. + + The <a constructor lt="ClipboardItem()">constructor</a> steps for <code>new ClipboardItem(<var>items</var>, <var>options</var>)</code> are: ```suggestion The <dfn constructor for="ClipboardItem" lt="ClipboardItem(items, options)"><code>new ClipboardItem(<var>items</var>, <var>options</var>)</code></dfn> constructor steps are: ``` > + The <a constructor lt="ClipboardItem()">constructor</a> steps for <code>new ClipboardItem(<var>items</var>, <var>options</var>)</code> are: + 1. Set [=this=]'s [=ClipboardItem/clipboard item=] to a new [=clipboard item=]. + + 1. Set [=this=]'s [=ClipboardItem/clipboard item=]'s [=presentation style=] to |options|["{{ClipboardItemOptions/presentationStyle}}"]. + + 1. Let |types| be a list of {{DOMString}}. + + 1. For each (|key|, |value|) in |items|: + + 1. Let |mimeType| be the result of [=parse a mime type=] given |key|. + + 1. If |mimeType| is failure, then throw a {{TypeError}}. + + 1. Let |representation| be a new [=representation=]. + + 1. Set |representation|'s [=mime type=] to |key|. ```suggestion 1. Set |representation|'s [=representation/MIME type=] to |key|. ``` > + + 1. Set [=this=]'s [=ClipboardItem/clipboard item=]'s [=presentation style=] to |options|["{{ClipboardItemOptions/presentationStyle}}"]. + + 1. Let |types| be a list of {{DOMString}}. + + 1. For each (|key|, |value|) in |items|: + + 1. Let |mimeType| be the result of [=parse a mime type=] given |key|. + + 1. If |mimeType| is failure, then throw a {{TypeError}}. + + 1. Let |representation| be a new [=representation=]. + + 1. Set |representation|'s [=mime type=] to |key|. + + 1. Set |representation|'s [=data=] to |value|. ```suggestion 1. Set |representation|'s [=representation/data=] to |value|. ``` > + + 1. For each (|key|, |value|) in |items|: + + 1. Let |mimeType| be the result of [=parse a mime type=] given |key|. + + 1. If |mimeType| is failure, then throw a {{TypeError}}. + + 1. Let |representation| be a new [=representation=]. + + 1. Set |representation|'s [=mime type=] to |key|. + + 1. Set |representation|'s [=data=] to |value|. + + 1. Append |representation| to [=this=]'s [=ClipboardItem/clipboard item=]'s [=list of representations=]. + + 1. Let |mimeTypeString| be the result of [=serialize a mime type=] with |mimeType|. ```suggestion 1. Let |mimeTypeString| be the result of [=serializing a MIME type=] with |mimeType|. ``` > + + To <dfn>create a {{ClipboardItem}} object</dfn>, given a [=clipboard item=] |clipboardItem|'s [=relevant realm=] |realm|, run these steps: + 1. Let |clipboardItemObject| be a [=new=] {{ClipboardItem}} with |realm|. + + 1. Set |clipboardItemObject|'s [=clipboard item=] to |clipboardItem|. + + The <a constructor lt="ClipboardItem()">constructor</a> steps for <code>new ClipboardItem(<var>items</var>, <var>options</var>)</code> are: + 1. Set [=this=]'s [=ClipboardItem/clipboard item=] to a new [=clipboard item=]. + + 1. Set [=this=]'s [=ClipboardItem/clipboard item=]'s [=presentation style=] to |options|["{{ClipboardItemOptions/presentationStyle}}"]. + + 1. Let |types| be a list of {{DOMString}}. + + 1. For each (|key|, |value|) in |items|: + + 1. Let |mimeType| be the result of [=parse a mime type=] given |key|. ```suggestion 1. Let |mimeType| be the result of [=parsing a MIME type=] given |key|. ``` > + 1. Append |representation| to [=this=]'s [=ClipboardItem/clipboard item=]'s [=list of representations=]. + + 1. Let |mimeTypeString| be the result of [=serialize a mime type=] with |mimeType|. + + 1. Add |mimeTypeString| to |types|. + + 1. Set [=this=]'s [=ClipboardItem/types array=] to the result of running [=create a frozen array=] from |types|. + + <h4 attribute for=ClipboardItem lt=presentationStyle>presentationStyle</h4> + <p> + The {{ClipboardItem/presentationStyle}} getter steps are to return [=this=]'s [=ClipboardItem/clipboard item=]'s [=presentation style=]. + </p> + + <h4 attribute for=ClipboardItem lt=types>types</h4> + <p> + {{ClipboardItem/types}} getter steps are to return [=this=]'s [=ClipboardItem/types array=]. ```suggestion The {{ClipboardItem/types}} getter steps are to return [=this=]'s [=ClipboardItem/types array=]. ``` > + + <h4 attribute for=ClipboardItem lt=presentationStyle>presentationStyle</h4> + <p> + The {{ClipboardItem/presentationStyle}} getter steps are to return [=this=]'s [=ClipboardItem/clipboard item=]'s [=presentation style=]. + </p> + + <h4 attribute for=ClipboardItem lt=types>types</h4> + <p> + {{ClipboardItem/types}} getter steps are to return [=this=]'s [=ClipboardItem/types array=]. + </p> + + <h4 method for=ClipboardItem lt=getType(type)>getType(type)</a> must run the below steps:</h4> + + 1. Let |realm| be [=this=]'s [=relevant realm=]. + + 1. Let |mimeType| be the result of [=parse a mime type=] given |type|. ```suggestion 1. Let |mimeType| be the result of [=parsing a MIME type=] given |type|. ``` > + + <h4 method for=ClipboardItem lt=getType(type)>getType(type)</a> must run the below steps:</h4> + + 1. Let |realm| be [=this=]'s [=relevant realm=]. + + 1. Let |mimeType| be the result of [=parse a mime type=] given |type|. + + 1. If |mimeType| is failure, then throw a {{TypeError}}. + + 1. Let |itemTypeList| be [=this=]'s [=ClipboardItem/clipboard item=]'s [=list of representations=]. + + 1. For each |representation| in |itemTypeList|: + + 1. If |representation|'s [=mime type=] is |mimeType|, then: + + 1. Let |blobData| be a [=Blob=] created using |representation|'s [=data=] and with its {{Blob/type}} set to |mimeType|, [=serialize a MIME type|serialized=]. representation's data is a `ClipboardItemData`, i.e. a `Promise<(DOMString or Blob)>`. You cannot create a blob from a promise. I think you need to use https://webidl.spec.whatwg.org/#dfn-perform-steps-once-promise-is-settled . - In your fulfillment steps, you will get either a `DOMString` or a `Blob`. - If it is a `DOMString`, probably you want to [encode](https://encoding.spec.whatwg.org/#utf-8-encode) the result into bytes, and then create a `Blob` from that. - If it is a `Blob`... do you want to create a new `Blob`? Or do you want to return the existing one? This is an observable choice. - In your rejection steps, you want to reject |p|. (Where |p| is a promise you create before the for each loop.) > 1. Run the following steps [=in parallel=]: - 1. Let |r| be the result of running [=check clipboard read permission=] [=in parallel=] + 1. Let |r| be the result of running [=check clipboard read permission=]. + + Note: Clipboard permission is not supported on Safari. However, the read() method must be called inside + a user gesture event and the user must select the paste option from the native context menu that pops up + when read() is called from JS, otherwise, the promise will be rejected. + + 1. If |r| is not "granted", then [=Queue a global task=] on the [=permission task source=], given |realm|'s [=Realm/global object=], to perform the below step: "check clipboard read permission" returns true or false, not "granted". > - 1. If |r| is not "granted", then reject |p| with a "NotAllowedError" DOMException + 1. Abort all steps. This is confusing, since you can't queue a task to abort steps happening in parallel. I think the phrasing you want is something like: > 1. If r is not granted, then: > 1. Queue a global task ... to reject p with ... > 1. Abort these steps. > - 1. Let |data| be a copy of the [=system clipboard data=] represented as - a sequence of {{ClipboardItem}}s. + 1. Let |data| be a copy of the [=system clipboard data=] represented as [=clipboard items=]. For the MIME types defined in the [=mandatory data types=] list, |data| contains the sanitized copy of text/html format, but image/png format has unsanitized payload to preserve meta data. + + Note: Currently in Chromium, only one [=clipboard item=] object is supported for reading and writing via the [=clipboard=] object. I don't really understand this note. However, notes on what specific implementations do don't have a place in the standard, so this is best deleted. > Note: As further described in [[#image-transcode]] this explicitly does not transcode images. Rather the original unmodified image data should be exposed to the website. - 1. Resolve |p| with |data|. + 1. [=Queue a global task=] on the [=clipboard task source=], given |realm|'s [=Realm/global object=], to perform the below steps: + + 1. Let |items| be a [=sequence=]<{{ClipboardItem}}>. + + 1. For each [=clipboard item=] |underlyingItem| of |data|: + + 1. Let |item| be the result of running the steps of [=create a ClipboardItem object=] given |underlyingItem|. + + 1. Append |item| to |items|. + + 1. Resolve |p| with |items|. I don't think you want to resolve this each time you loop. It should probably be dedented. > <pre class="idl" data-highlight="webidl"> - typedef sequence<ClipboardItem> ClipboardItems; + typedef (DOMString or Blob) ClipboardItemDataType; Since this typedef is only used once, I think it is best not to have a typedef at all, and just inline it into the next line. -- You are receiving this because you are subscribed to this thread. Reply to this email directly or view it on GitHub: https://github.com/w3c/clipboard-apis/pull/158#pullrequestreview-830520504
Received on Monday, 13 December 2021 17:23:14 UTC