What if rendering a Trello card was as simple as adding a paragraph <p>
or a
link <a>
? With the card component, its as simple as <trello-card>
!
Although we have the awesome card embed that lets you embed a Trello card into your project, it relies on a Trello user being logged in and isn't as flexible as some developers want it to be. If you are looking for a way to render native Trello cards in your project in a more flexible and controllable way, this card component is for you.
Below is a live example of the card component:
And the code for the above βοΈis below π β copy and paste it into an html file and give it a try!
1 2<script> const container = document.getElementById("card-component-example"); container.innerText = "Loading..."; const scriptSrc = window.customElements ? "/card.min.js" : "/card-polyfilled.min.js"; const cardJs = document.createElement("script"); cardJs.crossOrigin = "anonymous"; cardJs.src = "https://p.trellocdn.com" + scriptSrc; cardJs.onload = function () { fetch( "https://api.trello.com/1/card/MA6fxIg3?fields=name,closed,url,badges,idAttachmentCover,labels&attachments=cover&customFields=true&customFieldItems=true&members=true&stickers=true" ) .then(function (resp) { return resp.json(); }) .then(function (card) { const cardEl = document.createElement("trello-card"); cardEl.card = card; container.innerHTML = ""; container.appendChild(cardEl); }); }; document.head.appendChild(cardJs); </script> <div style="width:272px;background-color:#dfe1e6;padding:8px;"> <div id="card-component-example"> <!-- Card Component Will Be Inserted Here --> </div> </div>
The main component script you should include can be found here:
https://trellocdn.com/card.min.js
However, if you want to support Edge, we recommend loading the polyfill that we
have hosted at https://trellocdn.com/card-polyfilled.min.js
. Below is an
example of how to load the polyfill to support Edge:
1 2<!DOCTYPE html> <html> <head> <!-- Your head content --> <script> const scriptSrc = window.customElements ? "/card.min.js" : "/card-polyfilled.min.js"; window.cardComponentLoaded = new Promise(function (resolve) { const cardJs = document.createElement("script"); cardJs.crossOrigin = "anonymous"; cardJs.src = "https://p.trellocdn.com" + scriptSrc; cardJs.onload = resolve; document.head.appendChild(cardJs); }); </script> </head> <body> <!-- ... --> </body> </html>
This unusual script loading fork is a result of the Microsoft Edge browser not currently having built-in support for custom elements. We don't want to punish the other browsers which do have support so we only load the full polyfilled bundle when we detect that the browser needs it.
If your browser support matrix is limited to browsers that have native support for custom elements (see: https://caniuse.com/#feat=custom-elementsv1) you could simplify this to a single script tag:
1 2<!-- If you don't support browsers like Edge --> <script src="https://p.trellocdn.com/card.min.js" crossorigin="anonymous" ></script>
As with all of the scripts Trello hosts, when we announce updates on the changelog we will push changes to the staging versions of the component scripts first:
You can render a card by passing in an object that contains the card's field data to an element returned from the component. The only required field for a card is a name. For example, here is the minimal code required to render a card:
1 2const cardEl = document.createElement("trello-card"); cardEl.card = { name: "Name of card", // required url: "https://trello.com/c/something", // required }; document.body.appendChild(cardEl);
But that isn't very exciting! We support all of the fields from a card required to render a full-fledged card front. Below is an example making use of all of the supported fields:
1 2const cardEl = document.createElement("trello-card"); // Determines whether colorblind labels should be used or not. Default is true. cardEl.colorblind = false; // Determines whether to show text on labels. Default is true. cardEl.labeltext = true; cardEl.card = { id: "5b907e0e39cccd595f1c8bfa", name: "Name of card", // Required url: "https://trello.com/c/something", // Required closed: false, idAttachmentCover: null, badges: { attachmentsByType: { trello: { board: 1, card: 0 }, }, location: false, votes: 0, viewingMemberVoted: false, subscribed: true, checkItems: 5, checkItemsChecked: 4, comments: 3, attachments: 7, description: true, due: null, dueComplete: false, }, labels: [ { id: "5b8fd55d451e437262fe7aff", idBoard: "599dbf8d693c9eeaed69ca09", name: "bug", color: "red", }, ], stickers: [], attachments: [], // Only need attachment for idAttachmentCover members: [ { id: "556c8537a1928ba745504dd8", avatarHash: "0b48c7057767cca8f339109b27a064d7", fullName: "Matt Cowan", username: "mattcowan", initials: "MC", }, ], customFields: [], customFieldItems: [], }; // There is a custom event that is fired when a user clicks on the labels that // you can listen and respond to. cardEl.addEventListener("labelTextChanged", (e) => { console.log("labeltext property is now", e.detail.labeltext); }); document.body.appendChild(cardEl);
React 16.x still has some quirks when it comes to handling native custom elements so we recommend you follow our example below; in this example, we fetch a card from the Trello REST API, take the data returned, and turn it into a custom card rendered as a React component:
1 2import React from "react"; // ... const API_ROOT = "https://api.trello.com/1/card/"; const CARD_QUERY = `?fields=name,closed,url,badges,idAttachmentCover,labels&attachments=cover&customFields=true&customFieldItems=true&members=true&stickers=true&key=${API_KEY}&token=${API_TOKEN}`; let card; fetch(`${API_ROOT}${idCard}${CARD_QUERY}`) // Fetch card data from Trello API .then((resp) => resp.json()) .then((cardData) => (card = cardData)); // ... class TrelloCardWrapper extends React.Component { constructor(props) { super(props); this.setRef = this.setRef.bind(this); this.onClick = this.onClick.bind(this); this.onLabelTextChanged = this.onLabelTextChanged.bind(this); } componentDidMount() { if (!this.el) { return; } this.el.card = this.props.card; this.el.addEventListener("click", this.onClick); this.el.addEventListener("labelTextChanged", this.onLabelTextChanged); } componentDidUpdate() { if (!this.el) { return; } this.el.card = this.props.card; } onClick(e) { if (typeof this.props.onClick === "function") { e.preventDefault(); this.props.onClick(); } } onLabelTextChanged(e) { if (typeof this.props.onLabelTextChanged === "function") { this.props.onLabelTextChanged(e.detail.labeltext); } } setRef(el) { this.el = el; } render() { return ( <trello-card ref={this.setRef} colorblind={this.props.colorblind} labeltext={this.props.labelText} /> ); } } // ...
In general, framework support for custom elements is quite good. That said, there may be some quirks to how to use a custom element in your framework of choice. We suggest taking a look at https://custom-elements-everywhere.com/ to see if there is anything special you would need to do in your framework to use the Trello card component.
The component is made such that it works if you pass it a full response from
t.card('all')
or, as the example above demonstrates, a JSON response from the
1/cards/{idCard}
endpoint from
Trello's REST API.
The following properties are specific to the component and can be explicitly set to control the display of the card:
Name | Value | Details |
---|---|---|
colorblind | Boolean Default: false | Determines whether to render the labels with colorblind-friendly patterns. |
labeltext | Boolean Default: true | Determines whether to render the name field for labels. |
There is a custom event, labelTextChanged , that fires when the visibility
of label text is toggled by clicking on a label on the card.
event.detail.labeltext
will have the new value of the labeltext
property.
In addition to any custom events above, normal DOM events can be used as well. For example, if you wanted to add your own handler for a click on the card, and not have it open a new tab with the card URL you would use:
1 2cardElement.addEventListener("click", (e) => { e.preventDefault(); // ... });
Rate this page: