Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/use proxy #30

Merged
merged 26 commits into from
Aug 16, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
fb23eac
chore: update node
davidenke May 28, 2024
635c3c3
chore: update deps
davidenke May 28, 2024
4f0a61a
chore: remove orphaned deps
davidenke May 28, 2024
01da44d
build: clean output folders
davidenke May 28, 2024
7fd393c
chore: update eslint
davidenke May 28, 2024
55bbdfa
feat: separate polyfill imports from check
davidenke May 28, 2024
9359ee7
chore: align to linter
davidenke May 28, 2024
ac0280f
build: disable unnecessary code splitting
davidenke May 28, 2024
0ad483b
build: move preview sse into html file
davidenke May 28, 2024
ac5cb5c
feat: poc for proxy usage
davidenke May 28, 2024
c9a6b7b
build: clean scripts
davidenke May 28, 2024
2dd996b
test: finally run tests in correct environment
davidenke May 28, 2024
88e21d0
ci: add dependency required for gh action
davidenke May 30, 2024
31fb6ef
ci: report passed tests
davidenke May 30, 2024
7982fc8
refactor: self contained filters
davidenke Aug 12, 2024
6ce40b0
refactor: remove unused stuff
davidenke Aug 12, 2024
b44c924
refactor: use proxy to draw individually
davidenke Aug 14, 2024
0d7a2b1
feat: define options declaratively
davidenke Aug 15, 2024
7993a84
chore: overhaul example
davidenke Aug 15, 2024
e7ded36
build: update dependencies
davidenke Aug 15, 2024
37a64bc
build: preview polyfill and native
davidenke Aug 15, 2024
18e0fc2
fix: reset transformations
davidenke Aug 15, 2024
dd5bef7
refactor: history based incremental drawing
davidenke Aug 16, 2024
30161a0
chore: cleanup
davidenke Aug 16, 2024
4923ccf
docs: align readme
davidenke Aug 16, 2024
113e791
chore: align linter config
davidenke Aug 16, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 0 additions & 14 deletions .eslintrc.cjs

This file was deleted.

12 changes: 7 additions & 5 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
name: Build and release
name: test and build
on:
push:
branches: [main]
Expand All @@ -23,19 +23,21 @@ jobs:
- uses: actions/checkout@v3
- uses: actions/setup-node@v3
with:
node-version: 18.13.0
node-version: 20.16.0
- uses: actions/cache@v3
with:
path: ~/.npm
key: v1-npm-deps-${{ hashFiles('**/package-lock.json') }}
restore-keys: v1-npm-deps-
- run: npm ci
- run: npx --package @rollup/rollup-linux-x64-gnu --package playwright playwright install --with-deps webkit
- run: npm install
- run: npm run lint
- run: npm run test:ci
- uses: mikepenz/action-junit-report@v4
if: success() || failure()
with:
check_name: "report"
include_passed: true
report_paths: "**/reports/junit.xml"

build:
Expand All @@ -45,7 +47,7 @@ jobs:
- uses: actions/checkout@v3
- uses: actions/setup-node@v3
with:
node-version: 18.13.0
node-version: 20.16.0
- uses: actions/cache@v3
with:
path: ~/.npm
Expand Down Expand Up @@ -95,7 +97,7 @@ jobs:
- uses: actions/checkout@v3
- uses: actions/setup-node@v3
with:
node-version: 18.13.0
node-version: 20.16.0
registry-url: https://registry.npmjs.org/
- uses: actions/download-artifact@v3
with:
Expand Down
2 changes: 1 addition & 1 deletion .nvmrc
Original file line number Diff line number Diff line change
@@ -1 +1 @@
18.13.0
20.16.0
4 changes: 1 addition & 3 deletions .prettierrc
Original file line number Diff line number Diff line change
@@ -1,9 +1,7 @@
{
"singleQuote": true,
"jsxSingleQuote": false,
"trailingComma": "all",
"endOfLine": "auto",
"arrowParens": "avoid",
"tabWidth": 2,
"printWidth": 100
"tabWidth": 2
}
47 changes: 20 additions & 27 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,17 +1,14 @@
# context-filter-polyfill

[![Build Status](https://github.com/davidenke/context-filter-polyfill/actions/workflows/main.yml/badge.svg?branch=main)](https://github.com/davidenke/context-filter-polyfill)
[![NPM Version][npm-version-image]][npm-url]
[![NPM Install Size][npm-install-size-image]][npm-install-size-url]

https://davidenke.github.io/context-filter-polyfill/
Examples: https://davidenke.github.io/context-filter-polyfill/

Polyfills [`CanvasRenderingContext2d.filter`](https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/filter) capability of adopting CSS3 filters to canvas contexts at least partially.

Successfully tested on

- macOS Safari
- iOS Safari
- Windows 10 IE11
- Windows 10 Edge 16-18
Right now ~~only WebKit [misses an implementation (Bugzilla #198416)](https://bugs.webkit.org/show_bug.cgi?id=198416)~~ all engines support it natively, despite Safari not having shipped it yet in the stable release channel.

## Installation

Expand All @@ -35,6 +32,15 @@ npm install context-filter-polyfill
import 'context-filter-polyfill';
```

## Changes in 0.4

Since version 0.4.0 the method of how the polyfill is applied has been reworked.
It now polyfills the filter on each drawing function call instead of applying it once on the context in the end.

This results in more accurate behavior compared to the native implementation.

The [polyfilled and native results](https://davidenke.github.io/context-filter-polyfill/) can be compared with a non-WebKit browser like Firefox or Chrome.

## Supported filters

- [`url`](<https://developer.mozilla.org/en-US/docs/Web/CSS/filter#url()>) ✗
Expand All @@ -52,26 +58,13 @@ import 'context-filter-polyfill';

## See it in action

Just open the [integration demo](https://davidenke.github.io/context-filter-polyfill/) on Safari / iOS or IE11.

## Strategy

The polyfill is applied by the following steps:

1. monkey patching all properties of the `CanvasRenderingContext2d`
1. monkey patching all getters and setters of the `CanvasRenderingContext2d`
1. monkey patching all methods of the `CanvasRenderingContext2d`
Just open the [integration demo](https://davidenke.github.io/context-filter-polyfill/) on Safari / iOS.

These patches are proxying all changes to a **offscreen canvas** which applies the appropriate filter polyfills everytime a _drawing
function_ is called:
## License

- `clearRect`
- `drawImage`
- `fill`
- `fillRect`
- `fillText`
- `stroke`
- `strokeRect`
- `strokeText`
[MIT](LICENSE)

The contents of the **offscreen canvas** are applied back to the original canvas and is then resetted.
[npm-install-size-image]: https://badgen.net/packagephobia/install/context-filter-polyfill
[npm-install-size-url]: https://packagephobia.com/result?p=context-filter-polyfill
[npm-url]: https://npmjs.org/package/context-filter-polyfill
[npm-version-image]: https://badgen.net/npm/v/context-filter-polyfill
28 changes: 17 additions & 11 deletions esbuild.config.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { parseArgs } from 'node:util';
import { type BuildOptions, build, context } from 'esbuild';
import { dtsPlugin } from 'esbuild-plugin-d.ts';

import { build, type BuildOptions, context } from 'esbuild';
import copyStaticFiles from 'esbuild-copy-static-files';

const { values } = parseArgs({
options: {
Expand All @@ -11,26 +12,31 @@ const { values } = parseArgs({
const { port, serve } = values;

const options: BuildOptions = {
entryPoints: ['src/index.ts', 'src/index.html', 'src/mocks/mock-1.jpg', 'src/mocks/mock-2.png'],
entryPoints: [
'src/index.ts',
'src/polyfill.ts',

'src/example.ts',
'src/example.css',
'src/example.jpg',
],
outdir: 'dist',
format: 'esm',
bundle: true,
sourcemap: true,
minify: true,
splitting: false,
target: ['es6'],
loader: { '.html': 'copy', '.jpg': 'copy', '.png': 'copy' },
plugins: [dtsPlugin()],
loader: { '.jpg': 'copy' },
plugins: [
copyStaticFiles({ src: 'src/module.d.ts', dest: 'dist/index.d.ts' }),
copyStaticFiles({ src: 'src/example.html', dest: 'dist/index.html' }),
],
};

try {
if (serve) {
const ctx = await context({
...options,
banner: {
js: `new EventSource('/esbuild').addEventListener('change', () => location.reload())`,
},
});
const ctx = await context(options);
await ctx.watch();
await ctx.serve({ servedir: 'dist', port: Number(port) });
console.log(`> Serving on http://localhost:${port}`);
Expand Down
37 changes: 37 additions & 0 deletions eslint.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
// @ts-check

import eslintJs from '@eslint/js';
import eslintPluginPrettierRecommended from 'eslint-plugin-prettier/recommended';
import eslintSimpleImportSort from 'eslint-plugin-simple-import-sort';
import eslintPluginUnusedImports from 'eslint-plugin-unused-imports';
import eslintTs from 'typescript-eslint';

export default eslintTs.config(
eslintJs.configs.recommended,
...eslintTs.configs.recommended,
eslintPluginPrettierRecommended,
{
ignores: [
'**/node_modules/',
'**/generated/',
'**/dist/',
'**/coverage/',
'**/reports/',
],
},
{
plugins: {
'simple-import-sort': eslintSimpleImportSort,
'unused-imports': eslintPluginUnusedImports,
},
rules: {
'linebreak-style': ['error', 'unix'],
quotes: ['error', 'single'],
semi: ['error', 'always'],
'simple-import-sort/imports': 'error',
'simple-import-sort/exports': 'error',
'prettier/prettier': ['error'],
'unused-imports/no-unused-imports': 'error',
},
},
);
Loading
Loading