Skip to content

Commit

Permalink
Added MediaQueryList mocks
Browse files Browse the repository at this point in the history
  • Loading branch information
ascartabelli committed Aug 6, 2024
1 parent 7181d37 commit 2d5e5d9
Show file tree
Hide file tree
Showing 18 changed files with 195 additions and 128 deletions.
2 changes: 1 addition & 1 deletion explorer/src/lib/components/__tests__/BlocksCard.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,10 @@ describe("Blocks Card", () => {
const data = getTenBlocks(gqlBlocks.blocks);

const baseProps = {
appStore: appStore,
blocks: null,
error: null,
loading: false,
appStore: appStore
};
const baseOptions = {
props: baseProps,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,10 @@ describe("Transactions Card", () => {
const data = getTenTransactions(gqlTransactions.transactions);

const baseProps = {
appStore: appStore,
error: null,
loading: false,
txns: null,
appStore: appStore
};
const baseOptions = {
props: baseProps,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -745,36 +745,5 @@ exports[`Blocks Card > should render the \`BlocksCard\` component 1`] = `
</div>
`;

exports[`Blocks Card > should render the \`BlocksCard\` component with the mobile layout 1`] = `
<div
class="dusk-card data-card"
>
<header
class="data-card__header"
slot="header"
>
<h1
class="data-card__header-title"
>
Blocks — 0 Displayed Items
</h1>
<button
class="dusk-button dusk-button--type--button dusk-button--variant--tertiary dusk-button--size--normal"
type="button"
>
<span
class="dusk-button__text"
>
Show More
</span>
</button>
</header>
</div>
`;
8 changes: 3 additions & 5 deletions explorer/src/lib/components/blocks-card/BlocksCard.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
$: displayedBlocks = blocks ? blocks.slice(0, itemsToDisplay) : [];
$: isLoadMoreDisabled =
(blocks && itemsToDisplay >= blocks.length) || (loading && blocks === null);
$: ({ isSmallScreen } = $appStore);
const loadMoreItems = () => {
if (blocks && itemsToDisplay < blocks.length) {
Expand All @@ -47,16 +48,13 @@
label: "Show More",
}}
>
{#if $appStore.isSmallScreen}
{#if isSmallScreen}
<div class="blocks-card__list">
{#each displayedBlocks as block (block)}
<BlocksList data={block} />
{/each}
</div>
{:else}
<BlocksTable
data={displayedBlocks}
className="blocks-card__table"
/>
<BlocksTable data={displayedBlocks} className="blocks-card__table" />
{/if}
</DataCard>
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
/** @type {Boolean} */
export let loading;
/** @type {AppStore} */
export let appStore;
/** @type {boolean} */
export let isSmallScreen;
$: classes = makeClassName(["latest-blocks-card", className]);
</script>
Expand All @@ -36,11 +36,11 @@
label: "All Blocks",
}}
>
{#if $appStore.isSmallScreen}
{#if isSmallScreen}
{#each blocks as block (block)}
<BlocksList data={block} />
{/each}
{:else}
<BlocksTable data={blocks}/>
<BlocksTable data={blocks} />
{/if}
</DataCard>
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,8 @@
/** @type {Boolean} */
export let displayTooltips = false;
/** @type {AppStore} */
export let appStore;
/** @type {boolean} */
export let isSmallScreen;
$: classes = makeClassName(["latest-transactions-card", className]);
</script>
Expand All @@ -48,7 +48,7 @@
}
: undefined}
>
{#if $appStore.isSmallScreen}
{#if isSmallScreen}
{#each txns as txn (txn)}
<TransactionsList
data={txn}
Expand All @@ -57,9 +57,6 @@
/>
{/each}
{:else}
<TransactionsTable
data={txns}
mode={isOnHomeScreen ? "compact" : "full"}
/>
<TransactionsTable data={txns} mode={isOnHomeScreen ? "compact" : "full"} />
{/if}
</DataCard>
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@
$: displayedTxns = txns ? txns.slice(0, itemsToDisplay) : [];
$: isLoadMoreDisabled =
(txns && itemsToDisplay >= txns.length) || (loading && txns === null);
$: ({ isSmallScreen } = $appStore);
const loadMoreItems = () => {
if (txns && itemsToDisplay < txns.length) {
Expand All @@ -51,7 +52,7 @@
label: "Show More",
}}
>
{#if $appStore.isSmallScreen}
{#if isSmallScreen}
<div class="transactions-card__list">
{#each displayedTxns as txn (txn)}
<TransactionsList data={txn} mode="full" />
Expand Down
104 changes: 67 additions & 37 deletions explorer/src/lib/dusk/mocks/MediaQueryList.js
Original file line number Diff line number Diff line change
@@ -1,38 +1,68 @@
export default class MediaQueryList {
/**
* @param {String} query
*/
constructor(query) {
this.matches = false;
this.media = query;
this.listeners = [];
import { afterAll } from "vitest";

const controllers = new Set();

afterAll(() => {
controllers.forEach((controller) => {
controller.abort();
controllers.delete(controller);
});
});

/**
* Mocks the `MediaQueryList` object and listens to the
* "DuskMediaQueryMatchesChange" custom event.
* Fire one manually or with the `changeMediaQueryMatches`
* helper function to simulate media query changes.
*/
export default class MediaQueryList extends EventTarget {
#matches;

#media;

/**
* @param {string} mediaQuery
* @param {boolean} initialMatches
*/
constructor(mediaQuery, initialMatches) {
super();

this.#matches = initialMatches;
this.#media = mediaQuery;

const abortController = new AbortController();

controllers.add(abortController);

global.addEventListener("DuskMediaQueryMatchesChange", this, {
signal: abortController.signal,
});
}

get matches() {
return this.#matches;
}

get media() {
return this.#media;
}

/** @param {CustomEvent<{ media: string, matches: boolean }>} evt */
handleEvent(evt) {
const { detail, type } = evt;

if (
type === "DuskMediaQueryMatchesChange" &&
detail.media === this.#media
) {
this.#matches = detail.matches;

this.dispatchEvent(
new MediaQueryListEvent("change", {
matches: this.#matches,
media: this.#media,
})
);
}

/**
* @param {String} event
* @param {Function} callback
*/
addEventListener(event, callback) {
if (event === 'change') {
this.listeners.push(callback);
}
}

/**
* @param {String} event
* @param {Function} callback
*/
removeEventListener(event, callback) {
if (event === 'change') {
this.listeners = this.listeners.filter(listener => listener !== callback);
}
}

/**
* @param {Boolean} matches
*/
change(matches) {
this.matches = matches;
this.listeners.forEach(listener => listener({ matches }));
}
}
}
}
26 changes: 26 additions & 0 deletions explorer/src/lib/dusk/mocks/MediaQueryListEvent.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
import { pickIn } from "lamb";

export default class MediaQueryListEvent extends Event {
#matches;

#media;

/**
* @param {string} type
* @param {MediaQueryListEventInit} options
*/
constructor(type, options) {
super(type, pickIn(options, ["bubbles", "cancelable", "composed"]));

this.#matches = options.matches;
this.#media = options.media;
}

get matches() {
return this.#matches;
}

get media() {
return this.#media;
}
}
1 change: 1 addition & 0 deletions explorer/src/lib/dusk/mocks/index.js
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
export { default as IntersectionObserver } from "./IntersectionObserver";
export { default as MediaQueryList } from "./MediaQueryList";
export { default as MediaQueryListEvent } from "./MediaQueryListEvent";
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { describe, expect, it } from "vitest";

import { changeMediaQueryMatches } from "..";

describe("changeMediaQueryMatches", () => {
it('should dispatch "DuskMediaQueryMatchesChange" custom events', () => {
const media = "(max-width: 1024px)";
const matches = true;

/** @param {Event} evt */
const handler = (evt) => {
expect(evt).toBeInstanceOf(CustomEvent);
expect(evt.type).toBe("DuskMediaQueryMatchesChange");

// @ts-ignore see https://github.com/Microsoft/TypeScript/issues/28357
expect(evt.detail).toStrictEqual({ matches, media });
};

global.addEventListener("DuskMediaQueryMatchesChange", handler);

changeMediaQueryMatches(media, matches);

global.removeEventListener("DuskMediaQueryMatchesChange", handler);

expect.assertions(3);
});
});
14 changes: 14 additions & 0 deletions explorer/src/lib/dusk/test-helpers/changeMediaQueryMatches.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
/**
* Helper to fire "DuskMediaQueryMatchesChange" custom
* events that are listened by our `MediaQueryList` mock.
*
* @param {string} media
* @param {boolean} matches
*/
export default function changeMediaQueryMatches(media, matches) {
dispatchEvent(
new CustomEvent("DuskMediaQueryMatchesChange", {
detail: { matches, media },
})
);
}
1 change: 1 addition & 0 deletions explorer/src/lib/dusk/test-helpers/index.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
export { default as changeMediaQueryMatches } from "./changeMediaQueryMatches";
export { default as mockReadableStore } from "./mockReadableStore";
export { default as renderWithSimpleContent } from "./renderWithSimpleContent";
export { default as renderWithSlots } from "./renderWithSlots";
Expand Down
Loading

0 comments on commit 2d5e5d9

Please sign in to comment.