Compare commits

..

No commits in common. "master" and "add-license-1" have entirely different histories.

35 changed files with 8792 additions and 2738 deletions

5
demo/.gitignore vendored Normal file
View file

@ -0,0 +1,5 @@
dist
node_modules
app/*.js
app/*.js.map

17
demo/app/index.tsx Normal file
View file

@ -0,0 +1,17 @@
import * as React from "react";
import * as ReactDOM from "react-dom";
import {classList, spriteUrl, TestIcons, spriteEntries} from "svg-sprites/test";
console.log("Mein Hello World: AddFolder: %s, Path: %s", TestIcons.AddFolder, spriteUrl);
console.log("All entries: %O", spriteEntries);
const container = document.createElement("div");
container.style.fontSize = "100px";
document.body.append(container);
ReactDOM.render(<>
{classList.map(icon => {
return <React.Fragment key={icon}><div className={"icon_em " + icon} /><br /></React.Fragment>;
})}
</>, container);

41
demo/app/test.d.ts vendored Normal file
View file

@ -0,0 +1,41 @@
declare module "svg-sprites/test" {
export type TestIconClasses = "client-about" | "client-activate_microphone" | "client-add" | "client-add_foe" | "client-add_folder" | "client-add_friend" | "client-addon-collection" | "client-addon" | "client-apply" | "client-arrow_down" | "client-arrow_left" | "client-arrow_right" | "client-arrow_up" | "client-away" | "client-ban_client" | "client-ban_list" | "client-bookmark_add" | "client-bookmark_add_folder" | "client-bookmark_duplicate" | "client-w2g";
export enum TestIcons {
About = "client-about",
ActivateMicrophone = "client-activate_microphone",
Add = "client-add",
AddFoe = "client-add_foe",
AddFolder = "client-add_folder",
AddFriend = "client-add_friend",
AddonCollection = "client-addon-collection",
Addon = "client-addon",
Apply = "client-apply",
ArrowDown = "client-arrow_down",
ArrowLeft = "client-arrow_left",
ArrowRight = "client-arrow_right",
ArrowUp = "client-arrow_up",
Away = "client-away",
BanClient = "client-ban_client",
BanList = "client-ban_list",
BookmarkAdd = "client-bookmark_add",
BookmarkAddFolder = "client-bookmark_add_folder",
BookmarkDuplicate = "client-bookmark_duplicate",
W2g = "client-w2g",
}
export const spriteEntries: {
id: string;
className: string;
width: number;
height: number;
xOffset: number;
yOffset: number;
}[];
export const spriteUrl: string;
export const classList: string[];
export const spriteWidth: number;
export const spriteHeight: number;
}

4476
demo/package-lock.json generated Normal file

File diff suppressed because it is too large Load diff

27
demo/package.json Normal file
View file

@ -0,0 +1,27 @@
{
"name": "svg-sprite-demo",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"build": "webpack"
},
"keywords": [],
"author": "",
"license": "ISC",
"devDependencies": {
"@types/react": "^16.9.45",
"@types/react-dom": "^16.9.8",
"ts-loader": "^8.0.2",
"typescript": "^3.9.7",
"webpack": "^4.44.1",
"webpack-cli": "^3.3.12"
},
"dependencies": {
"fs": "0.0.1-security",
"fs-extra": "^9.0.1",
"html-webpack-plugin": "^4.3.0",
"react": "^16.13.1",
"react-dom": "^16.13.1"
}
}

6
demo/sprites/about.svg Normal file
View file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-about" width="16"
height="16" viewBox="0 0 16 16" x="96" y="0">
<path fill="#7289da"
d="M3 1.125c-1.036 0-1.875 0.839-1.875 1.875v10c0 1.036 0.84 1.875 1.875 1.875h10c1.036 0 1.875-0.839 1.875-1.875v-10c0-1.036-0.839-1.875-1.875-1.875h-10zM7.206 2.653h1.588c0.198 0 0.365 0.069 0.501 0.209s0.205 0.31 0.205 0.514v1.552c0 0.204-0.069 0.376-0.205 0.514-0.136 0.141-0.303 0.211-0.501 0.211h-1.588c-0.198 0-0.366-0.072-0.501-0.215s-0.204-0.312-0.204-0.51v-1.552c0-0.204 0.068-0.374 0.204-0.514s0.304-0.209 0.501-0.209zM7.206 7.063h1.588c0.198 0 0.365 0.067 0.501 0.203 0.136 0.135 0.205 0.3 0.205 0.498v5.098c0 0.197-0.069 0.364-0.205 0.497-0.136 0.136-0.303 0.204-0.501 0.204h-1.588c-0.198 0-0.366-0.070-0.501-0.208-0.136-0.139-0.204-0.303-0.204-0.493v-5.098c0-0.197 0.068-0.363 0.204-0.498 0.136-0.136 0.304-0.203 0.501-0.203z"></path>
</svg>

After

Width:  |  Height:  |  Size: 992 B

View file

@ -0,0 +1,12 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-activate_microphone"
width="16" height="16" viewBox="0 0 16 16" x="128" y="0">
<path fill="#a9aaac"
d="M1.706 14.29c0.774 0.775 2.029 0.775 2.805 0.002l-2.807-2.807c-0.773 0.775-0.773 2.030 0.002 2.805z"></path>
<path fill="#a9aaac"
d="M4.688 10.624l0.835-0.835c0.316-0.316 0.721-0.482 1.171-0.482s0.854 0.167 1.172 0.483l0.563 0.563 0.931-0.929c-0.614-0.242-1.188-0.608-1.684-1.104-0.499-0.499-0.868-1.079-1.109-1.698l-4.103 4.103 2.095 2.095c-0.231-0.291-0.354-0.641-0.354-1.025 0-0.45 0.167-0.855 0.483-1.172z"></path>
<path fill="#7289da"
d="M13.459 6.018c0.396 0 0.758 0.13 1.054 0.376 0.647-1.369 0.406-3.057-0.724-4.187-1.438-1.438-3.777-1.438-5.215 0s-1.438 3.777 0 5.215c0.513 0.513 1.14 0.841 1.801 0.989l1.912-1.909c0.312-0.312 0.728-0.484 1.172-0.484z"></path>
<path fill="#1ca037"
d="M14.705 8.919l-5.8 5.791c-0.112 0.112-0.278 0.165-0.497 0.159-0.2-0.006-0.353-0.059-0.459-0.159l-2.502-2.502c-0.112-0.112-0.168-0.25-0.168-0.412s0.056-0.3 0.168-0.412l0.834-0.834c0.112-0.112 0.25-0.169 0.412-0.169s0.3 0.056 0.412 0.169l1.321 1.321 4.62-4.61c0.112-0.112 0.25-0.169 0.412-0.169s0.3 0.056 0.412 0.169l0.834 0.824c0.112 0.119 0.169 0.258 0.169 0.417s-0.056 0.298-0.169 0.417z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

6
demo/sprites/add.svg Normal file
View file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-add" width="16"
height="16" viewBox="0 0 16 16" x="160" y="0">
<path fill="#1ca037"
d="M14.715 6.985c-0.182-0.184-0.413-0.279-0.684-0.279h-4.737v-4.737c0-0.269-0.093-0.5-0.277-0.688-0.189-0.187-0.421-0.281-0.691-0.281h-0.648c-0.271 0-0.503 0.094-0.691 0.28-0.186 0.189-0.279 0.421-0.279 0.689v4.737h-4.735c-0.262 0-0.491 0.094-0.683 0.279s-0.288 0.418-0.288 0.691v0.648c0 0.277 0.096 0.509 0.285 0.691 0.181 0.184 0.413 0.278 0.685 0.278h4.736v4.736c0 0.259 0.093 0.489 0.276 0.682 0.193 0.193 0.425 0.289 0.694 0.289h0.648c0.268 0 0.501-0.095 0.69-0.283 0.185-0.189 0.279-0.42 0.279-0.688v-4.736h4.737c0.271 0 0.502-0.094 0.686-0.28 0.187-0.18 0.283-0.413 0.283-0.689v-0.648c0-0.276-0.096-0.509-0.285-0.691z"></path>
</svg>

After

Width:  |  Height:  |  Size: 876 B

10
demo/sprites/add_foe.svg Normal file
View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-add_foe" width="16"
height="16" viewBox="0 0 16 16" x="192" y="0">
<path fill="#7289da"
d="M6.396 11.359c0-1.375 0.586-2.615 1.52-3.485-0.117-0.106-0.201-0.202-0.2-0.256 0.002-0.009 0.006-0.018 0.013-0.026 0.498-0.54 0.719-0.708 0.978-1.346l0.083-0.203 0.185-0.095c0.153-0.079 0.356-0.381 0.466-0.882 0.063-0.285 0.076-0.573 0.036-0.79-0.029-0.156-0.077-0.237-0.111-0.261l-0.216-0.151-0.032-0.278c-0.167-1.458-1.002-2.461-2.492-2.461-0 0-0 0-0 0s-0 0-0 0c-1.491 0-2.325 1.003-2.492 2.461l-0.032 0.278-0.216 0.151c-0.035 0.024-0.082 0.106-0.111 0.261-0.040 0.217-0.027 0.505 0.036 0.79 0.111 0.5 0.314 0.803 0.467 0.882l0.185 0.095 0.083 0.203c0.259 0.638 0.481 0.806 0.978 1.346 0.007 0.008 0.010 0.017 0.013 0.026 0.003 0.134-0.512 0.525-0.77 0.681-0.030 0.018-0.058 0.033-0.080 0.044-0.171 0.086-0.345 0.134-0.527 0.186-0.509 0.142-1.085 0.305-1.786 1.371-0.526 0.803-0.768 3.558-0.798 4.974h6.376c-0.953-0.872-1.552-2.125-1.552-3.516z"></path>
<path fill="#c90709"
d="M11.36 7.844c-1.942 0-3.516 1.574-3.516 3.515s1.574 3.516 3.516 3.516c1.941 0 3.515-1.574 3.515-3.516s-1.574-3.515-3.515-3.515z"></path>
<path fill="#fff"
d="M13.547 11.661c0 0.076-0.025 0.14-0.079 0.191-0.051 0.052-0.115 0.077-0.19 0.077h-1.348v1.348c0 0.075-0.026 0.139-0.077 0.191-0.053 0.052-0.116 0.079-0.192 0.079h-0.604c-0.076 0-0.139-0.027-0.192-0.080-0.051-0.054-0.077-0.117-0.077-0.19v-1.348h-1.348c-0.075 0-0.14-0.026-0.191-0.077-0.053-0.051-0.079-0.116-0.079-0.191v-0.604c0-0.076 0.027-0.14 0.080-0.191s0.116-0.078 0.19-0.078h1.348v-1.348c0-0.075 0.026-0.139 0.077-0.191 0.053-0.052 0.116-0.078 0.192-0.078h0.604c0.076 0 0.139 0.025 0.192 0.078 0.051 0.052 0.077 0.116 0.077 0.191v1.348h1.348c0.075 0 0.139 0.026 0.19 0.078 0.053 0.051 0.079 0.115 0.079 0.191v0.604z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

View file

@ -0,0 +1,8 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-add_folder" width="16"
height="16" viewBox="0 0 16 16" x="224" y="0">
<path fill="#7289da"
d="M13.801 3.864h-5.693v-0.752c0-0.593-0.481-1.074-1.074-1.074h-4.834c-0.593 0-1.074 0.481-1.074 1.074v9.775c0 0.593 0.481 1.074 1.074 1.074h11.602c0.593 0 1.074-0.481 1.074-1.074v-7.949c-0-0.593-0.481-1.074-1.074-1.074z"></path>
<path fill="#f2f2f2"
d="M10.734 9.782h-1.953v1.953c0 0.109-0.038 0.203-0.113 0.278s-0.167 0.113-0.277 0.113h-0.781c-0.11 0-0.203-0.039-0.278-0.116s-0.113-0.168-0.113-0.275v-1.953h-1.953c-0.11 0-0.203-0.040-0.278-0.116s-0.113-0.167-0.113-0.274v-0.781c0-0.11 0.038-0.203 0.113-0.278s0.168-0.113 0.278-0.113h1.953v-1.953c0-0.11 0.038-0.203 0.113-0.278s0.168-0.113 0.278-0.113h0.781c0.11 0 0.202 0.038 0.277 0.113s0.113 0.168 0.113 0.278v1.953h1.953c0.109 0 0.203 0.039 0.278 0.113s0.113 0.168 0.113 0.278v0.781c0 0.107-0.038 0.198-0.113 0.274s-0.169 0.116-0.278 0.116z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1 KiB

View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-add_friend" width="16"
height="16" viewBox="0 0 16 16" x="256" y="0">
<path fill="#7289da"
d="M6.396 11.359c0-1.375 0.586-2.615 1.52-3.485-0.117-0.106-0.201-0.202-0.2-0.256 0.002-0.009 0.006-0.018 0.013-0.026 0.498-0.54 0.719-0.708 0.978-1.346l0.083-0.203 0.185-0.095c0.153-0.079 0.356-0.381 0.466-0.882 0.063-0.285 0.076-0.573 0.036-0.79-0.029-0.156-0.077-0.237-0.111-0.261l-0.216-0.151-0.032-0.278c-0.167-1.458-1.002-2.461-2.492-2.461-0 0-0 0-0 0s-0 0-0 0c-1.491 0-2.325 1.003-2.492 2.461l-0.032 0.278-0.216 0.151c-0.035 0.024-0.082 0.106-0.111 0.261-0.040 0.217-0.027 0.505 0.036 0.79 0.111 0.5 0.314 0.803 0.467 0.882l0.185 0.095 0.083 0.203c0.259 0.638 0.481 0.806 0.978 1.346 0.007 0.008 0.010 0.017 0.013 0.026 0.003 0.134-0.512 0.525-0.77 0.681-0.030 0.018-0.058 0.033-0.080 0.044-0.171 0.086-0.345 0.134-0.527 0.186-0.509 0.142-1.085 0.305-1.786 1.371-0.526 0.803-0.768 3.558-0.798 4.974h6.376c-0.953-0.872-1.552-2.125-1.552-3.516z"></path>
<path fill="#1ca037"
d="M11.36 7.844c-1.942 0-3.516 1.574-3.516 3.516s1.574 3.516 3.516 3.516c1.941 0 3.515-1.574 3.515-3.516s-1.574-3.515-3.515-3.515z"></path>
<path fill="#fff"
d="M13.547 11.661c0 0.076-0.025 0.14-0.079 0.191-0.051 0.052-0.115 0.077-0.19 0.077h-1.348v1.348c0 0.075-0.026 0.139-0.077 0.191-0.053 0.052-0.116 0.079-0.192 0.079h-0.604c-0.076 0-0.139-0.027-0.192-0.080-0.051-0.054-0.077-0.117-0.077-0.19v-1.348h-1.348c-0.075 0-0.14-0.026-0.191-0.077-0.053-0.051-0.079-0.116-0.079-0.191v-0.604c0-0.076 0.027-0.14 0.080-0.191s0.116-0.078 0.19-0.078h1.348v-1.348c0-0.075 0.026-0.139 0.077-0.191 0.053-0.052 0.116-0.078 0.192-0.078h0.604c0.076 0 0.139 0.025 0.192 0.078 0.051 0.052 0.077 0.116 0.077 0.191v1.348h1.348c0.075 0 0.139 0.026 0.19 0.078 0.053 0.051 0.079 0.115 0.079 0.191v0.604z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

View file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-addon-collection"
width="16" height="16" viewBox="0 0 16 16" x="320" y="0">
<path fill="#1ca037"
d="M15.918 6.892c-0.088-0.666-0.264-1.317-0.526-1.936-0.451-1.097-1.11-2.054-1.993-2.845-1.985-1.774-4.306-2.447-6.914-1.956-2.367 0.446-4.174 1.758-5.4 3.837-0.874 1.481-1.213 3.091-1.040 4.805 0.006 0.054 0.013 0.108 0.020 0.161 0.145 1.261 0.545 2.435 1.276 3.473 1.86 2.644 4.413 3.857 7.628 3.509 2.352-0.254 4.212-1.424 5.583-3.357 0.321-0.462 0.595-0.956 0.817-1.473 0.325-0.736 0.481-1.518 0.582-2.313 0.091-0.637 0.046-1.273-0.032-1.905zM12.256 8.796c-0.103 0.121-0.234 0.161-0.392 0.161-0.912-0.003-1.823 0-2.734-0.005-0.143 0-0.193 0.028-0.191 0.184 0.007 0.907 0.003 1.814 0.002 2.721 0 0.348-0.124 0.471-0.476 0.471-0.327 0-0.655 0-0.982 0-0.293 0-0.429-0.138-0.43-0.434-0.002-0.923-0.005-1.847 0-2.77 0-0.134-0.032-0.173-0.17-0.172-0.917 0.007-1.833 0-2.75 0.007-0.166 0.002-0.292-0.043-0.396-0.164-0.039-0.102-0.058-0.21-0.055-0.32 0.003-0.339 0.006-0.678-0.002-1.016-0.005-0.226 0.11-0.397 0.384-0.395 0.295 0.002 0.59 0 0.884 0 0.633 0 1.266-0.005 1.901 0.003 0.158 0.002 0.212-0.028 0.21-0.203-0.011-0.902-0.006-1.803-0.006-2.705-0.002-0.054 0.001-0.109 0.008-0.163 0.032-0.201 0.1-0.288 0.302-0.3 0.414-0.028 0.829-0.027 1.242 0.002 0.23 0.017 0.336 0.171 0.336 0.421 0 0.913 0.003 1.825-0.005 2.738-0.002 0.158 0.027 0.213 0.202 0.211 0.9-0.010 1.801-0.005 2.702-0.005 0.345 0 0.471 0.129 0.471 0.476 0 0.306-0.002 0.613 0 0.918 0 0.114-0.019 0.228-0.056 0.336v0z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.6 KiB

6
demo/sprites/addon.svg Normal file
View file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-addon" width="16"
height="16" viewBox="0 0 16 16" x="288" y="0">
<path fill="#7289da"
d="M11.98 12.488c0 0.133-0.073 0.11-0.149 0.11-1.006 0-2.011 0.002-3.017-0.003-0.148 0-0.205 0.037-0.195 0.193 0.008 0.125 0.012 0.25 0.031 0.375 0.029 0.21 0.102 0.378 0.291 0.521 0.59 0.444 0.594 1.188 0.015 1.646-0.538 0.428-1.154 0.512-1.803 0.323-0.276-0.081-0.537-0.203-0.743-0.427-0.438-0.475-0.411-1.107 0.087-1.516 0.176-0.145 0.372-0.274 0.444-0.5 0.055-0.171 0.090-0.35 0.058-0.534-0.018-0.106-0.094-0.076-0.156-0.076-0.88 0-1.76-0.004-2.64 0.002-0.141 0-0.181-0.033-0.179-0.178 0.007-0.958 0.006-1.917 0.002-2.875-0.006-0.098 0.040-0.193 0.121-0.25 0.436-0.341 1.099-0.236 1.408 0.227 0.227 0.341 0.539 0.551 0.952 0.488 0.493-0.076 0.819-0.396 1.005-0.851 0.138-0.333 0.189-0.696 0.149-1.055-0.063-0.365-0.19-0.703-0.439-0.986-0.373-0.422-0.981-0.493-1.409-0.201-0.137 0.094-0.235 0.236-0.322 0.38-0.037 0.063-0.097 0.109-0.168 0.128-0.307 0.094-0.617 0.143-0.922 0.016-0.237-0.099-0.385-0.202-0.379-0.536 0.018-0.994 0.012-1.989 0.003-2.984-0.002-0.167 0.049-0.193 0.2-0.192 0.9 0.007 1.801 0 2.701 0.007 0.138 0 0.212-0.050 0.267-0.164 0.166-0.344 0.13-0.691 0.037-1.041-0.018-0.069-0.086-0.087-0.136-0.122-0.261-0.181-0.476-0.397-0.547-0.719-0.087-0.397 0.063-0.719 0.347-0.987 0.642-0.605 1.877-0.607 2.527-0.009 0.557 0.513 0.497 1.231-0.142 1.681-0.386 0.277-0.509 0.803-0.287 1.224 0.054 0.099 0.119 0.138 0.235 0.137 0.869-0.005 1.738 0 2.607-0.004 0.1 0 0.147 0.012 0.147 0.132-0.004 1.393 0 2.785 0 4.178-0.001 0.021-0.003 0.042-0.006 0.063-0.001 1.459-0 2.921 0.007 4.381z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.7 KiB

6
demo/sprites/apply.svg Normal file
View file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-apply" width="16"
height="16" viewBox="0 0 16 16" x="352" y="0">
<path fill="#1ca037"
d="M2.539 8.041c0.169-0.168 0.369-0.255 0.6-0.25 0.228-0.002 0.427 0.082 0.595 0.25l1.924 1.924 6.608-6.608c0.168-0.168 0.366-0.251 0.595-0.253 0.233 0.001 0.432 0.083 0.601 0.251l0.458 0.458c0.169 0.169 0.25 0.37 0.25 0.604-0.006 0.232-0.089 0.431-0.251 0.592 0 0-7.421 7.421-7.534 7.534s-0.352 0.351-0.726 0.351c-0.374 0-0.622-0.247-0.726-0.351s-2.851-2.851-2.851-2.851c-0.168-0.168-0.251-0.367-0.25-0.595-0.004-0.231 0.082-0.431 0.25-0.599l0.458-0.458z"></path>
</svg>

After

Width:  |  Height:  |  Size: 709 B

View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-arrow_down" width="16"
height="16" viewBox="0 0 16 16" x="384" y="0">
<path fill="#7289da"
d="M8.001 0.178c-4.337 0-7.853 3.516-7.853 7.853s3.516 7.853 7.853 7.853c4.336 0 7.852-3.516 7.852-7.853s-3.516-7.853-7.852-7.853z"></path>
<path fill="#0f0"
d="M7.122 14.647c-0.007 0-0.014-0.001-0.022-0.001-0.006 0-0.011 0.001-0.017 0-0.191-0.002-0.357-0.074-0.499-0.216l-3.895-3.895c-0.136-0.136-0.207-0.301-0.213-0.496-0.006-0.194 0.060-0.36 0.198-0.498l1.242-1.242c0.137-0.137 0.301-0.204 0.495-0.201 0.19 0.002 0.357 0.073 0.5 0.216l1.52 1.52v-7.112c0-0.193 0.067-0.359 0.2-0.501s0.297-0.212 0.492-0.212h1.756c0.194 0 0.357 0.069 0.492 0.208 0.133 0.136 0.201 0.305 0.201 0.506l0 6.254v4.959c0 0.2-0.068 0.368-0.201 0.505-0.135 0.138-0.298 0.206-0.492 0.206z"></path>
<path fill="#fff"
d="M7.122 14.647c-0.007 0-0.014-0.001-0.022-0.001-0.006 0-0.011 0.001-0.017 0-0.191-0.002-0.357-0.074-0.499-0.216l-3.895-3.895c-0.136-0.136-0.207-0.301-0.213-0.496-0.006-0.194 0.060-0.36 0.198-0.498l1.242-1.242c0.137-0.137 0.301-0.204 0.495-0.201 0.19 0.002 0.357 0.073 0.5 0.216l1.52 1.519v-0.857l0-6.254c0-0.024 0.001-0.048 0.003-0.071 0.014-0.17 0.081-0.315 0.198-0.435 0.097-0.099 0.208-0.162 0.334-0.19 0.028-0.006 0.056-0.011 0.085-0.014 0.020-0.002 0.041-0.003 0.062-0.003 0.003-0 0.007-0.001 0.010-0.001 0 0 0 0 0.001 0h1.755c0.004 0 0.007 0.001 0.011 0.001 0.021 0 0.041 0.001 0.062 0.003 0.023 0.002 0.045 0.005 0.067 0.010 0.006 0.001 0.012 0.003 0.018 0.004 0.126 0.028 0.238 0.091 0.334 0.19 0.117 0.12 0.183 0.265 0.198 0.435 0.002 0.023 0.003 0.047 0.003 0.071l0 6.254v0.857l1.52-1.519c0.142-0.142 0.31-0.213 0.5-0.216 0.193-0.002 0.357 0.064 0.495 0.201l1.242 1.242c0.138 0.138 0.203 0.304 0.198 0.498-0.006 0.195-0.077 0.36-0.213 0.496l-3.895 3.895c-0.141 0.141-0.308 0.213-0.499 0.216-0.006 0-0.011-0-0.017-0-0.007 0-0.014 0.001-0.022 0.001h-0z"></path>
</svg>

After

Width:  |  Height:  |  Size: 2 KiB

View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-arrow_left" width="16"
height="16" viewBox="0 0 16 16" x="416" y="0">
<path fill="#7289da"
d="M8.001 0.178c-4.337 0-7.853 3.516-7.853 7.853s3.516 7.853 7.853 7.853c4.336 0 7.852-3.516 7.852-7.853s-3.516-7.853-7.852-7.853z"></path>
<path fill="#0f0"
d="M1.681 7.45c0-0.007 0.001-0.014 0.001-0.022-0-0.006-0.001-0.011-0-0.017 0.002-0.191 0.074-0.357 0.216-0.499l3.895-3.895c0.136-0.136 0.301-0.207 0.496-0.213 0.194-0.006 0.36 0.060 0.498 0.198l1.242 1.242c0.137 0.137 0.204 0.301 0.201 0.495-0.002 0.19-0.073 0.357-0.216 0.5l-1.52 1.52h7.112c0.193 0 0.359 0.067 0.501 0.2s0.212 0.297 0.212 0.492v1.756c0 0.194-0.069 0.357-0.208 0.492-0.136 0.133-0.305 0.201-0.506 0.201l-11.214 0c-0.2 0-0.368-0.068-0.505-0.201-0.138-0.135-0.206-0.298-0.206-0.492z"></path>
<path fill="#fff"
d="M1.681 7.45c0-0.007 0.001-0.014 0.001-0.022-0-0.006-0.001-0.011-0-0.017 0.002-0.191 0.074-0.357 0.216-0.499l3.895-3.895c0.136-0.136 0.301-0.207 0.496-0.213 0.194-0.006 0.36 0.060 0.498 0.198l1.242 1.242c0.137 0.137 0.204 0.301 0.201 0.495-0.002 0.19-0.073 0.357-0.216 0.5l-1.519 1.52 7.112 0c0.024 0 0.048 0.001 0.071 0.003 0.17 0.014 0.315 0.081 0.435 0.198 0.099 0.097 0.162 0.208 0.19 0.334 0.006 0.028 0.011 0.056 0.014 0.085 0.002 0.020 0.003 0.041 0.003 0.062 0 0.003 0.001 0.007 0.001 0.010 0 0 0 0 0 0.001v1.755c0 0.004-0.001 0.007-0.001 0.011-0 0.021-0.001 0.041-0.003 0.062-0.002 0.023-0.005 0.045-0.010 0.067-0.001 0.006-0.003 0.012-0.004 0.018-0.028 0.126-0.091 0.238-0.19 0.334-0.12 0.117-0.265 0.183-0.435 0.198-0.023 0.002-0.047 0.003-0.071 0.003l-7.112 0 1.519 1.52c0.142 0.142 0.213 0.31 0.216 0.5 0.002 0.193-0.064 0.357-0.201 0.495l-1.242 1.242c-0.138 0.138-0.304 0.203-0.498 0.198-0.195-0.006-0.36-0.077-0.496-0.213l-3.895-3.895c-0.141-0.141-0.213-0.308-0.216-0.499-0-0.006 0-0.011 0-0.017-0-0.007-0.001-0.014-0.001-0.022v-0z"></path>
</svg>

After

Width:  |  Height:  |  Size: 2 KiB

View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-arrow_right" width="16"
height="16" viewBox="0 0 16 16" x="448" y="0">
<path fill="#7289da"
d="M8.001 0.178c-4.337 0-7.853 3.516-7.853 7.853s3.516 7.853 7.853 7.853c4.336 0 7.852-3.516 7.852-7.853s-3.516-7.853-7.852-7.853z"></path>
<path fill="#0f0"
d="M14.319 9.207c0 0.007-0.001 0.014-0.001 0.022 0 0.006 0.001 0.011 0 0.017-0.002 0.191-0.074 0.357-0.216 0.499l-3.895 3.895c-0.136 0.136-0.301 0.207-0.496 0.213-0.194 0.006-0.36-0.060-0.498-0.198l-1.242-1.242c-0.137-0.137-0.204-0.301-0.201-0.495 0.002-0.19 0.073-0.357 0.216-0.5l1.52-1.52h-7.112c-0.193 0-0.359-0.067-0.501-0.2s-0.212-0.297-0.212-0.492v-1.756c0-0.194 0.069-0.357 0.208-0.492 0.136-0.133 0.305-0.201 0.506-0.201l11.214-0c0.2 0 0.368 0.068 0.505 0.201 0.138 0.135 0.206 0.298 0.206 0.492z"></path>
<path fill="#fff"
d="M14.319 9.207c0 0.007-0.001 0.014-0.001 0.022 0 0.006 0.001 0.011 0 0.017-0.002 0.191-0.074 0.357-0.216 0.499l-3.895 3.895c-0.136 0.136-0.301 0.207-0.496 0.213-0.194 0.006-0.36-0.060-0.498-0.198l-1.242-1.242c-0.137-0.137-0.204-0.301-0.201-0.495 0.002-0.19 0.073-0.357 0.216-0.5l1.519-1.52-7.112-0c-0.024 0-0.048-0.001-0.071-0.003-0.17-0.014-0.315-0.081-0.435-0.198-0.099-0.097-0.162-0.208-0.19-0.334-0.006-0.028-0.011-0.056-0.014-0.085-0.002-0.020-0.003-0.041-0.003-0.062-0-0.003-0-0.007-0-0.010 0-0 0-0 0-0.001v-1.755c0-0.004 0-0.007 0-0.011 0-0.021 0.001-0.041 0.003-0.062 0.002-0.023 0.005-0.045 0.010-0.067 0.001-0.006 0.003-0.012 0.004-0.018 0.028-0.126 0.091-0.238 0.19-0.334 0.12-0.117 0.265-0.183 0.435-0.198 0.023-0.002 0.047-0.003 0.071-0.003l7.112-0-1.519-1.52c-0.142-0.142-0.213-0.31-0.216-0.5-0.002-0.193 0.064-0.357 0.201-0.495l1.242-1.242c0.138-0.138 0.304-0.203 0.498-0.198 0.195 0.006 0.36 0.077 0.496 0.213l3.895 3.895c0.141 0.141 0.213 0.308 0.216 0.499 0 0.006-0 0.011-0 0.017 0 0.007 0.001 0.014 0.001 0.022v0z"></path>
</svg>

After

Width:  |  Height:  |  Size: 2 KiB

10
demo/sprites/arrow_up.svg Normal file
View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-arrow_up" width="16"
height="16" viewBox="0 0 16 16" x="480" y="0">
<path fill="#7289da"
d="M8.001 0.178c-4.337 0-7.853 3.516-7.853 7.853s3.516 7.853 7.853 7.853c4.336 0 7.852-3.516 7.852-7.853s-3.516-7.853-7.852-7.853z"></path>
<path fill="#0f0"
d="M7.122 2.010c-0.007 0-0.014 0.001-0.022 0.001-0.006-0-0.011-0.001-0.017-0-0.191 0.002-0.357 0.074-0.499 0.216l-3.895 3.895c-0.136 0.136-0.207 0.301-0.213 0.496-0.006 0.194 0.060 0.36 0.198 0.498l1.242 1.242c0.137 0.137 0.301 0.204 0.495 0.201 0.19-0.002 0.357-0.073 0.5-0.216l1.52-1.52v7.112c0 0.193 0.067 0.359 0.2 0.501s0.297 0.212 0.492 0.212h1.756c0.194 0 0.357-0.069 0.492-0.208 0.133-0.136 0.201-0.305 0.201-0.506l0-6.254v-4.959c0-0.2-0.068-0.368-0.201-0.505-0.135-0.138-0.298-0.206-0.492-0.206h-1.756z"></path>
<path fill="#fff"
d="M7.122 2.010c-0.007 0-0.014 0.001-0.022 0.001-0.006-0-0.011-0.001-0.017-0-0.191 0.002-0.357 0.074-0.499 0.216l-3.895 3.895c-0.136 0.136-0.207 0.301-0.213 0.496-0.006 0.194 0.060 0.36 0.198 0.498l1.242 1.242c0.137 0.137 0.301 0.204 0.495 0.201 0.19-0.002 0.357-0.073 0.5-0.216l1.52-1.519v0.857l0 6.254c0 0.024 0.001 0.048 0.003 0.071 0.014 0.17 0.081 0.315 0.198 0.435 0.097 0.099 0.208 0.162 0.334 0.19 0.028 0.006 0.056 0.011 0.085 0.014 0.020 0.002 0.041 0.003 0.062 0.003 0.003 0 0.007 0 0.010 0 0 0 0 0 0.001 0h1.755c0.004 0 0.007-0 0.011-0 0.021-0 0.041-0.001 0.062-0.003 0.023-0.002 0.045-0.005 0.067-0.010 0.006-0.001 0.012-0.003 0.018-0.004 0.126-0.028 0.238-0.091 0.334-0.19 0.117-0.12 0.183-0.265 0.198-0.435 0.002-0.023 0.003-0.047 0.003-0.071l0-6.254v-0.857l1.52 1.519c0.142 0.142 0.31 0.213 0.5 0.216 0.193 0.002 0.357-0.064 0.495-0.201l1.242-1.242c0.138-0.138 0.203-0.304 0.198-0.498-0.006-0.195-0.077-0.36-0.213-0.496l-3.895-3.895c-0.141-0.141-0.308-0.213-0.499-0.216-0.006-0-0.011 0-0.017 0-0.007-0-0.014-0.001-0.022-0.001h-1.757z"></path>
</svg>

After

Width:  |  Height:  |  Size: 2 KiB

9
demo/sprites/away.svg Normal file
View file

@ -0,0 +1,9 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-away" width="16"
height="16" viewBox="0 0 16 16" x="0" y="32">
<path fill="#7289da"
d="M14.875 13.808c0 0.593-0.481 1.074-1.074 1.074h-11.601c-0.593 0-1.074-0.481-1.074-1.074v-6.016c0-0.593 0.481-1.074 1.074-1.074h11.602c0.593 0 1.074 0.481 1.074 1.074v6.016h-0z"></path>
<path fill="#fff"
d="M8.991 10.623l1.589 1.595c0.070 0.070 0.105 0.153 0.105 0.249s-0.035 0.178-0.105 0.244l-0.493 0.493c-0.066 0.070-0.149 0.105-0.247 0.105s-0.18-0.035-0.247-0.105l-1.595-1.589-1.595 1.589c-0.066 0.070-0.149 0.105-0.247 0.105s-0.18-0.035-0.247-0.105l-0.493-0.493c-0.070-0.066-0.105-0.148-0.105-0.244s0.035-0.179 0.105-0.249l1.589-1.595-1.589-1.589c-0.070-0.070-0.105-0.153-0.105-0.249s0.035-0.179 0.105-0.249l0.493-0.493c0.066-0.066 0.149-0.1 0.247-0.1s0.18 0.033 0.247 0.1l1.595 1.595 1.594-1.595c0.066-0.066 0.149-0.1 0.247-0.1s0.18 0.033 0.247 0.1l0.493 0.493c0.070 0.070 0.105 0.153 0.105 0.249s-0.035 0.179-0.105 0.249l-1.589 1.589z"></path>
<path fill="#a9aaac" d="M8 2.93l2.146 2.515h1.787l-3.933-4.609-3.933 4.609h1.787l2.146-2.515z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.2 KiB

View file

@ -0,0 +1,9 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-ban_client" width="16"
height="16" viewBox="0 0 16 16" x="32" y="32">
<path fill="#7289da"
d="M6.235 11.359c0-1.375 0.586-2.615 1.52-3.485-0.117-0.106-0.201-0.202-0.2-0.256 0.002-0.009 0.006-0.018 0.013-0.026 0.498-0.54 0.719-0.708 0.978-1.346l0.083-0.203 0.185-0.095c0.153-0.079 0.356-0.381 0.466-0.882 0.063-0.285 0.076-0.573 0.036-0.79-0.029-0.156-0.077-0.237-0.111-0.261l-0.216-0.151-0.032-0.278c-0.167-1.458-1.002-2.461-2.492-2.461-0 0-0 0-0 0s-0 0-0 0c-1.491 0-2.325 1.003-2.493 2.461l-0.032 0.278-0.216 0.151c-0.035 0.024-0.082 0.106-0.111 0.261-0.040 0.217-0.027 0.505 0.036 0.79 0.111 0.5 0.314 0.803 0.467 0.882l0.185 0.095 0.083 0.203c0.259 0.638 0.481 0.806 0.978 1.346 0.007 0.008 0.010 0.017 0.013 0.026 0.003 0.134-0.512 0.525-0.77 0.681-0.030 0.018-0.058 0.033-0.080 0.044-0.171 0.086-0.345 0.134-0.527 0.186-0.509 0.142-1.085 0.305-1.786 1.371-0.526 0.803-0.768 3.558-0.798 4.975h6.376c-0.953-0.872-1.552-2.125-1.552-3.516z"></path>
<path fill="#c90709"
d="M11.089 8.834c1.401 0 2.54 1.14 2.54 2.541s-1.139 2.54-2.54 2.54c-1.401 0-2.54-1.139-2.54-2.54s1.14-2.541 2.54-2.541zM11.089 7.875c-1.933 0-3.5 1.568-3.5 3.5s1.567 3.5 3.5 3.5c1.933 0 3.5-1.567 3.5-3.5s-1.567-3.5-3.5-3.5z"></path>
<path fill="#c90709" d="M9.091 14.070l-0.708-0.709 4.692-4.692 0.709 0.708-4.693 4.693z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.4 KiB

15
demo/sprites/ban_list.svg Normal file
View file

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-ban_list" width="16"
height="16" viewBox="0 0 16 16" x="64" y="32">
<path fill="#c90709"
d="M10.884 7.714c1.748 0 3.169 1.422 3.169 3.17s-1.422 3.17-3.169 3.17c-1.748 0-3.17-1.422-3.17-3.169s1.422-3.17 3.17-3.17zM10.884 6.518c-2.411 0-4.366 1.955-4.366 4.366s1.955 4.366 4.366 4.366c2.411 0 4.366-1.955 4.366-4.366s-1.955-4.366-4.366-4.366z"></path>
<path fill="#c90709" d="M13.361 7.508l0.884 0.884-5.853 5.853-0.884-0.884 5.853-5.853z"></path>
<path fill="#a9aaac"
d="M6.279 14.001h-3.654c-0.345 0-0.625-0.28-0.625-0.625v-10.751c0-0.345 0.28-0.625 0.625-0.625h9.059c0.345 0 0.625 0.28 0.625 0.625 0 0 0 1.933 0 2.883 0.44 0.117 0.859 0.286 1.25 0.502v-3.384c0-1.034-0.841-1.875-1.875-1.875h-9.059c-1.034 0-1.875 0.841-1.875 1.875v10.751c0 1.034 0.841 1.875 1.875 1.875h4.819c-0.449-0.354-0.843-0.776-1.165-1.25z"></path>
<path fill="#a9aaac"
d="M10.862 4.125c-0.113-0.115-0.271-0.187-0.445-0.187h-6.896c-0.345 0-0.625 0.28-0.625 0.625 0 0.17 0.068 0.323 0.178 0.436l-0.002 0.002c0.113 0.115 0.271 0.187 0.445 0.187h6.896c0.345 0 0.625-0.28 0.625-0.625 0-0.17-0.068-0.323-0.178-0.436l0.002-0.002z"></path>
<path fill="#a9aaac"
d="M2.895 8.001c0 0.345 0.28 0.625 0.625 0.625h2.282c0.201-0.451 0.46-0.871 0.769-1.25h-3.051c-0.345 0-0.625 0.28-0.625 0.625z"></path>
<path fill="#a9aaac"
d="M2.895 11.438c0 0.345 0.28 0.625 0.625 0.625h1.928c-0.082-0.38-0.127-0.775-0.127-1.179 0-0.024 0.002-0.047 0.002-0.071h-1.803c-0.345 0-0.625 0.28-0.625 0.625z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.6 KiB

View file

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-bookmark_add" width="16"
height="16" viewBox="0 0 16 16" x="96" y="32">
<path fill="#7289da" d="M4.885 14.875l-1.88-1.858-1.88 1.858v-13.75h3.76v13.75z"></path>
<path fill="#ccc"
d="M12.755 6.57v1.566h1.566c0.191 0 0.378 0.031 0.554 0.089v-7.101h-3.76v3.695c0.427 0.027 0.824 0.203 1.128 0.507 0.33 0.33 0.512 0.772 0.512 1.243z"></path>
<path fill="#b3b3b3"
d="M8.137 8.136v-1.566c0-0.471 0.182-0.913 0.513-1.245 0.327-0.327 0.764-0.507 1.23-0.511v-3.69h-3.76v7.071c0.145-0.038 0.296-0.059 0.45-0.059l1.566 0z"></path>
<path fill="#1ca037"
d="M14.321 11.553h-2.768v2.768c0 0.155-0.053 0.287-0.16 0.393s-0.238 0.16-0.393 0.16h-1.107c-0.156 0-0.287-0.055-0.394-0.164s-0.16-0.24-0.16-0.389v-2.768h-2.768c-0.156 0-0.287-0.055-0.394-0.165s-0.16-0.239-0.16-0.389v-1.107c0-0.156 0.053-0.287 0.16-0.394s0.238-0.16 0.394-0.16h2.768v-2.768c0-0.156 0.053-0.287 0.16-0.394s0.238-0.16 0.394-0.16h1.107c0.156 0 0.287 0.053 0.393 0.16s0.16 0.238 0.16 0.394v2.768h2.768c0.155 0 0.287 0.054 0.393 0.16s0.16 0.238 0.16 0.394v1.107c0 0.15-0.053 0.279-0.16 0.389s-0.238 0.165-0.393 0.165z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.2 KiB

View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-bookmark_add_folder"
width="16" height="16" viewBox="0 0 16 16" x="128" y="32">
<path fill="#7289da"
d="M9.865 3.408h-1.758v-0.752c0-0.593-0.481-1.074-1.074-1.074h-4.834c-0.593 0-1.074 0.481-1.074 1.074v9.775c0 0.593 0.481 1.074 1.074 1.074h7.666v-10.097z"></path>
<path fill="#ccc"
d="M13.801 3.408h-2.686v11.011l1.88-1.858 1.88 1.858v-9.936c0-0.593-0.481-1.074-1.074-1.074z"></path>
<path fill="#e6e6e6"
d="M7.961 9.193h-1.758v1.758c0 0.098-0.034 0.183-0.102 0.25s-0.151 0.102-0.25 0.102h-0.703c-0.099 0-0.183-0.036-0.25-0.104s-0.102-0.152-0.102-0.247v-1.758h-1.758c-0.099 0-0.183-0.036-0.25-0.105s-0.102-0.151-0.102-0.247v-0.703c0-0.099 0.034-0.183 0.102-0.25s0.151-0.102 0.25-0.102h1.758v-1.758c0-0.099 0.034-0.183 0.102-0.25s0.151-0.102 0.25-0.102h0.703c0.099 0 0.182 0.034 0.25 0.102s0.102 0.151 0.102 0.25v1.758h1.758c0.098 0 0.183 0.035 0.25 0.102s0.102 0.151 0.102 0.25v0.703c0 0.096-0.034 0.178-0.102 0.247s-0.152 0.105-0.25 0.105z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.1 KiB

View file

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="client-bookmark_duplicate"
width="16" height="16" viewBox="0 0 16 16" x="160" y="32">
<path fill="#7289da"
d="M5.814 11.281v-1.094h-1.093c-0.467 0-0.904-0.184-1.228-0.516-0.317-0.324-0.491-0.752-0.491-1.203v-0.937c0-0.461 0.178-0.893 0.502-1.218 0.324-0.323 0.756-0.501 1.217-0.501h1.093v-1.093c0-0.461 0.178-0.894 0.503-1.218 0.286-0.285 0.656-0.457 1.057-0.493v-1.883h-6.25v13.75l3.125-2.233 3.125 2.233v-1.883c-0.405-0.037-0.78-0.213-1.066-0.506-0.318-0.324-0.493-0.752-0.493-1.205z"></path>
<path fill="#a9aaac"
d="M8.626 1.125v1.883c0.402 0.035 0.774 0.207 1.061 0.494 0.323 0.324 0.502 0.756 0.502 1.217v1.093h1.094c0.461 0 0.893 0.178 1.217 0.502s0.501 0.756 0.501 1.217v0.937c0 0.452-0.175 0.879-0.49 1.201-0.325 0.334-0.761 0.518-1.229 0.518h-1.094v1.094c0 0.461-0.178 0.893-0.502 1.217-0.287 0.287-0.659 0.459-1.061 0.494v1.883l3.125-2.233 3.125 2.233v-13.75h-6.25z"></path>
<path fill="#1ca037"
d="M11.283 8.938h-2.344v2.344c0 0.131-0.045 0.243-0.136 0.333s-0.201 0.136-0.333 0.136h-0.937c-0.132 0-0.243-0.047-0.333-0.139s-0.136-0.203-0.136-0.33v-2.344h-2.344c-0.132 0-0.243-0.047-0.333-0.139s-0.136-0.202-0.136-0.329v-0.937c0-0.132 0.045-0.243 0.135-0.333s0.202-0.136 0.333-0.136h2.344v-2.343c0-0.132 0.045-0.243 0.136-0.333s0.202-0.136 0.334-0.136h0.937c0.132 0 0.243 0.045 0.333 0.135s0.136 0.202 0.136 0.333v2.343h2.344c0.131 0 0.243 0.046 0.333 0.136s0.136 0.202 0.136 0.334v0.937c0 0.128-0.045 0.237-0.136 0.329s-0.202 0.139-0.333 0.139z"></path>
</svg>

After

Width:  |  Height:  |  Size: 1.6 KiB

4
demo/sprites/w2g.svg Normal file
View file

@ -0,0 +1,4 @@
<svg xmlns="http://www.w3.org/2000/svg" height="100%" version="1.1" viewBox="0 0 68 48" width="100%">
<path d="M66.52,7.74c-0.78-2.93-2.49-5.41-5.42-6.19C55.79,.13,34,0,34,0S12.21,.13,6.9,1.55 C3.97,2.33,2.27,4.81,1.48,7.74C0.06,13.05,0,24,0,24s0.06,10.95,1.48,16.26c0.78,2.93,2.49,5.41,5.42,6.19 C12.21,47.87,34,48,34,48s21.79-0.13,27.1-1.55c2.93-0.78,4.64-3.26,5.42-6.19C67.94,34.95,68,24,68,24S67.94,13.05,66.52,7.74z" fill="#f00"></path>
<path d="M 45,24 27,14 27,34" fill="#fff"></path>
</svg>

After

Width:  |  Height:  |  Size: 506 B

12
demo/tsconfig.json Normal file
View file

@ -0,0 +1,12 @@
{
"compilerOptions": {
"module": "commonjs",
"target": "es6",
"sourceMap": true,
"baseUrl": ".",
"jsx": "react"
},
"include": [
"app"
]
}

63
demo/webpack.config.ts Normal file
View file

@ -0,0 +1,63 @@
import * as path from "path";
import {Configuration} from "webpack";
import * as SpriteGenerator from "../plugin";
import * as HtmlWebpackPlugin from "html-webpack-plugin";
export = {
entry: path.join(__dirname, "app", "index.tsx"),
target: "web",
plugins: [
new SpriteGenerator.Plugin({
dtsOutputFolder: path.join(__dirname, "app"),
configurations: {
test: {
folder: path.join(__dirname, "sprites"),
cssClassPrefix: "client-",
dtsOptions: {
module: true,
enumName: "TestIcons",
classUnionName: "TestIconClasses",
cssClassPrefix: "client-",
},
cssOptions: [
{
scale: 1,
selector: ".icon",
unit: "px"
},
{
scale: 2,
selector: ".icon_x2",
unit: "px"
},
{
scale: 1,
selector: ".icon_em",
unit: "em"
}
]
}
}
}),
new HtmlWebpackPlugin()
],
module: {
rules: [
{
test: /\.tsx?$/,
loader: [
"ts-loader"
]
}
]
},
mode: process.env.NODE_ENV === "development" ? "development" : "production",
resolve: {
extensions: [".ts", ".tsx", ".css", ".js"]
},
output: {
filename: "[name].[contenthash].js",
}
} as Configuration;

6394
package-lock.json generated

File diff suppressed because it is too large Load diff

View file

@ -1,6 +1,6 @@
{
"name": "webpack-svg-sprite-generator",
"version": "5.0.7",
"version": "1.0.11",
"description": "",
"main": "plugin.js",
"types": "ts/index.d.ts",
@ -8,35 +8,24 @@
"build": "webpack"
},
"keywords": [],
"author": "WolverinDEV",
"license": "GPL-3.0",
"bugs": {
"url": "https://git.kle.li/TeaSpeak/webpack-svg-sprites/issues"
},
"repository": {
"url": "https://git.kle.li/TeaSpeak/webpack-svg-sprites.git",
"type": "git"
},
"author": "",
"license": "ISC",
"devDependencies": {
"@types/fs-extra": "^11.0.4",
"@types/tapable": "^2.2.7",
"@types/webpack": "^5.28.5",
"change-case": "^4.1.2",
"clean-webpack-plugin": "^4.0.0",
"copy-webpack-plugin": "^11.0.0",
"html-webpack-plugin": "^5.5.3",
"potpack": "^2.0.0",
"@types/tapable": "^1.0.6",
"@types/webpack": "^4.41.21",
"change-case": "^4.1.1",
"clean-webpack-plugin": "^3.0.0",
"copy-webpack-plugin": "^6.0.3",
"sha1": "^1.1.1",
"ts-loader": "^9.5.1",
"ts-node": "^10.9.1",
"typescript": "^5.2.2",
"webpack": "^5.89.0",
"webpack-cli": "^5.1.4",
"ts-loader": "^8.0.2",
"typescript": "^3.9.7",
"webpack-cli": "^3.3.12",
"xml-parser": "^1.2.1"
},
"peerDependencies": {
"fs-extra": "^11.1.1",
"dependencies": {
"path": "^0.12.7",
"webpack": "^5.x"
"webpack": "^4.44.1",
"fs-extra": "^9.0.1",
"potpack": "^1.0.1"
}
}
}

View file

@ -1,9 +1,11 @@
import * as fs from "fs-extra";
import * as path from "path";
import * as XMLParser from "xml-parser";
import { pascalCase } from "change-case";
import XMLParser from "xml-parser";
import potpack from "potpack";
let potpack = require("potpack");
if(typeof potpack !== "function" && potpack.default)
potpack = potpack.default;
function generateAttributes(attributes: XMLParser.Attributes) {
const keys = Object.keys(attributes);
@ -19,8 +21,8 @@ function jsNode2xml(indent: string, data: XMLParser.Node) {
const tagOpen = `<${data.name}${generateAttributes(data.attributes)}>`;
const tagClose = `</${data.name}>`;
let content = data.children.length ? data.children.map(e => jsNode2xml(indent + " ", e)).join("\n") : data.content || "";
if(content.length !== 0)
let content = data.children.length ? data.children.map(e => jsNode2xml(indent + " ", e)).join("\n") : data.content;
if(content?.length !== 0)
content = "\n" + content + "\n" + indent;
return (
@ -48,7 +50,7 @@ export async function generateSpriteSvg(sprite: GeneratedSprite) {
let result = "";
result += `<?xml version="1.0" encoding="utf-8"?>\n`;
result += `<!-- ${sprite.entries.length} icons packed -->\n`;
result += `<svg xmlns="http://www.w3.org/2000/svg" width="${sprite.width}" height="${sprite.height}" viewBox="0 0 ${sprite.width} ${sprite.height}">\n`;
result += `<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="${sprite.width}" height="${sprite.height}" viewBox="0 0 ${sprite.width} ${sprite.height}">\n`;
for(const file of sprite.entries) {
const root = file.data.root;
@ -91,14 +93,21 @@ export async function generateSpriteCss(options: SpriteCssOptions, classPrefix:
let result = "";
result += `${options.selector}{`;
result += `display:inline-block;`;
/* doing a relative path here as well since WebPack may messes around here since the public path may start with / and if it's a file path / means the root... */
result += `background-image:url(".${publicUrl}"),url("${publicUrl}");`;
result += `background-repeat:no-repeat;`;
result += `background:url("${publicUrl}") no-repeat;`;
result += `background-size:${sprite.width * scaleX}${options.unit} ${sprite.height * scaleY}${options.unit};`;
result += `height:${defaultHeight * scaleY}${options.unit};`;
result += `width:${defaultWidth * scaleX}${options.unit}`;
result += `}`;
/*
const unit = (value: number) => {
let valStr = value.toString();
if(valStr.length < 5)
valStr = " ".substr(valStr.length - 5) + valStr;
return value === 0 ? `${valStr} ` : `${valStr}${options.unit}`;
};
*/
const unit = (value: number) => {
let valStr = value.toString();
return value === 0 ? `${valStr}` : `${valStr}${options.unit}`;
@ -141,25 +150,15 @@ function generateEnumMembers(options: SpriteDtsOptions, sprite: GeneratedSprite,
return result;
}
export async function generateSpriteDts(options: SpriteDtsOptions, moduleName: string, sprite: GeneratedSprite, cssClassPrefix: string, modulePrefix: string, sourceDirectory: string) {
const headerLines = [];
export async function generateSpriteDts(options: SpriteDtsOptions, moduleName: string, sprite: GeneratedSprite, cssClassPrefix: string, modulePrefix: string) {
const lines = [];
headerLines.push(`/*`);
headerLines.push(` * DO NOT MODIFY THIS FILE!`);
headerLines.push(` *`);
headerLines.push(` * This file has been auto generated by the svg-sprite generator.`);
headerLines.push(` * Sprite source directory: ${sourceDirectory}`);
headerLines.push(` * Sprite count: ${sprite.entries.length}`);
headerLines.push(` */`);
headerLines.push(``);
{
let union = "";
for(const file of sprite.entries)
union += ` | "${cssClassPrefix}${file.name}"`;
lines.push(`export type ${options.classUnionName} = ${union.substring(3)};`);
lines.push(`export type ${options.classUnionName} = ${union.substr(3)};`);
}
lines.push(``);
@ -195,13 +194,12 @@ export async function generateSpriteDts(options: SpriteDtsOptions, moduleName: s
if(options.module) {
let result = "";
result += headerLines.join("\n");
result += `declare module "${modulePrefix}${moduleName}" {\n`;
result += lines.map(e => " " + e).join("\n");
result += `\n}`;
return result;
} else {
return headerLines.join("\n") + lines.join("\n");
return lines.join("\n");
}
}
@ -215,22 +213,24 @@ export async function generateSpriteJs(options: SpriteDtsOptions, sprite: Genera
lines.push(`EnumClassList[EnumClassList["${key}"] = "${members[key]}"] = "${key}";`);
}
lines.push(``);
lines.push(`let SpriteEntries = [`);
for(const entry of sprite.entries) {
lines.push(` Object.freeze({`);
lines.push(` id: "${entry.name}",`);
lines.push(` className: "${cssClassPrefix}${entry.name}",`);
{
lines.push(``);
lines.push(`let SpriteEntries = [`);
for(const entry of sprite.entries) {
lines.push(` Object.freeze({`);
lines.push(` id: "${entry.name}",`);
lines.push(` className: "${cssClassPrefix}${entry.name}",`);
lines.push(` width: ${entry.bounds.w},`);
lines.push(` height: ${entry.bounds.h},`);
lines.push(` width: ${entry.bounds.w},`);
lines.push(` height: ${entry.bounds.h},`);
lines.push(` xOffset: ${entry.bounds.x},`);
lines.push(` yOffset: ${entry.bounds.y},`);
lines.push(` xOffset: ${entry.bounds.x},`);
lines.push(` yOffset: ${entry.bounds.y},`);
lines.push(` }),`);
lines.push(` }),`);
}
lines.push(`];`);
}
lines.push(`];`);
lines.push(``);
lines.push(`let SpriteUrl = decodeURIComponent("${encodeURIComponent(publicUrl)}");`);
@ -239,13 +239,13 @@ export async function generateSpriteJs(options: SpriteDtsOptions, sprite: Genera
lines.push(`let ClassList = [${sprite.entries.map(e => `"${cssClassPrefix}${e.name}", `)}];`);
lines.push(``);
lines.push(`Object.defineProperty(module.exports, "__esModule", { value: true });`);
lines.push(`module.exports.${options.enumName} = Object.freeze(EnumClassList);`);
lines.push(`module.exports.spriteUrl = SpriteUrl;`);
lines.push(`module.exports.classList = Object.freeze(ClassList);`);
lines.push(`module.exports.spriteEntries = Object.freeze(SpriteEntries);`);
lines.push(`module.exports.spriteWidth = ${sprite.width};`);
lines.push(`module.exports.spriteHeight = ${sprite.height};`);
lines.push(`Object.defineProperty(exports, "__esModule", { value: true });`);
lines.push(`exports.${options.enumName} = Object.freeze(EnumClassList);`);
lines.push(`exports.spriteUrl = SpriteUrl;`);
lines.push(`exports.classList = Object.freeze(ClassList);`);
lines.push(`exports.spriteEntries = Object.freeze(SpriteEntries);`);
lines.push(`exports.spriteWidth = ${sprite.width};`);
lines.push(`exports.spriteHeight = ${sprite.height};`);
return lines.join("\n");
}
@ -267,25 +267,17 @@ export async function generateSprite(files: string[]) : Promise<GeneratedSprite>
svg.data = XMLParser((await fs.readFile(file)).toString());
svg.name = path.basename(file, path.extname(file));
if(!svg.data.root) {
console.warn("Missing svg root element for %s. Skipping file.", file);
continue;
}
if(svg.data.root.name !== "svg") {
console.warn("invalid svg root attribute for " + file + " (" + svg.data.root.name + ")");
continue;
}
const rootAttributes = svg.data.root.attributes;
const [ /* xOff */, /* yOff */, width, height ] = rootAttributes["viewBox"].split(" ").map(parseFloat);
const [ xOff, yOff, width, height ] = rootAttributes["viewBox"].split(" ").map(parseFloat);
if(isNaN(width) || isNaN(height)) {
console.warn("Skipping SVG %s because of invalid bounds (Parsed: %d x %d, Values: %o).", file, width, height, rootAttributes["viewBox"].split(" "));
continue;
} else if(Math.floor(width) !== width || Math.floor(height) !== height) {
console.warn("Skipping SVG %s because of an non interger height/width (%fx%f)", file, width, height);
continue;
}
svg.bounds = {
@ -299,8 +291,13 @@ export async function generateSprite(files: string[]) : Promise<GeneratedSprite>
result.entries.push(svg);
}
/* take the element height/with divided by two since that's a good number to work with */
//const svgSpaceWidth = result.elementWidth / 2;
//const svgSpaceHeight = result.elementHeight / 2;
//result.entries.forEach(e => { e.bounds.w += svgSpaceWidth; e.bounds.h += svgSpaceHeight });
const spriteDim = potpack(result.entries.map(e => e.bounds));
//result.entries.forEach(e => { e.bounds.w -= svgSpaceWidth; e.bounds.h -= svgSpaceHeight });
result.width = spriteDim.w;
result.height = spriteDim.h;

View file

@ -1,5 +1,5 @@
import * as Generator from "./generator";
import { SpriteGenerator, Options as PluginOptions } from "./plugin";
import * as Generator from "./Generator";
import { SpriteGenerator, Options as PluginOptions } from "./Plugin";
export type Sprite = Generator.GeneratedSprite;
export type DtsOptions = Generator.SpriteDtsOptions;

View file

@ -1,7 +1,7 @@
import * as webpack from "webpack";
import * as path from "path";
import * as SystemFs from "fs-extra";
import sha1 from "sha1";
import webpack, {Compiler, Module, RuntimeGlobals} from "webpack";
import * as fs from "fs-extra";
import * as sha1 from "sha1";
import {
GeneratedSprite,
@ -11,19 +11,17 @@ import {
SpriteCssOptions,
SpriteDtsOptions
} from "./generator";
import Compilation = webpack.Compilation;
const { RawSource } = require("webpack-sources");
export interface Options {
modulePrefix?: string, /* defaults to svg-sprites/ */
dtsOutputFolder: string,
configurations: {
[key: string] : SvgSpriteConfiguration
},
publicPath?: string,
}
}
const Module = require("webpack/lib/Module");
const { RawSource } = require("webpack-sources");
interface SvgSpriteConfiguration {
folder: string;
@ -33,120 +31,78 @@ interface SvgSpriteConfiguration {
cssOptions: SpriteCssOptions[];
}
const TYPES = new Set(["javascript"]);
const RUNTIME_REQUIREMENTS = new Set([
RuntimeGlobals.module
]);
class SvgSpriteModule extends Module {
private readonly pluginConfig: Options;
private readonly configName: string;
private readonly config: SvgSpriteConfiguration;
private sprite: GeneratedSprite;
private spriteSvg: string;
private spriteCss: string;
private spriteJs: string;
private spriteAssetName: string;
private spriteAssetUrl: string;
constructor(context: string, pluginConfig: Options, configName: string, config: SvgSpriteConfiguration) {
super("javascript/dynamic", null);
this.context = context;
super("javascript/dynamic", context);
this.pluginConfig = pluginConfig;
this.configName = configName;
this.config = config;
this.buildInfo = {};
this.clearDependenciesAndBlocks();
}
getSourceTypes() {
return TYPES;
}
identifier() {
return this.pluginConfig.modulePrefix + this.configName;
}
readableIdentifier() {
return `SVG sprite ` + this.configName;
}
libIdent() {
return this.pluginConfig.modulePrefix + this.configName;
readableIdentifier(requestShortener) {
return `SVG sprite ` + this.configName;
}
needBuild(context, callback) {
context.fileSystemInfo.getContextHash(this.config.folder, (error, hash) => {
if(error) {
callback(error);
return;
}
const needBuild = this.buildMeta?.directoryHash !== hash;
callback(null, needBuild);
})
needRebuild() {
return false;
}
build(options, compilation: Compilation, resolver, fs, callback) {
this.buildAsync(options, compilation).then(() => {
callback();
}).catch(error => {
callback(error);
});
}
build(options, compilation, resolver, fs_, callback) {
console.info("Building SVG sprite for configuration %s", this.configName);
private async buildAsync(options_, compilation: Compilation) {
this.built = true;
this.buildMeta = {
async: false,
exportsType: undefined
};
this.buildInfo = {
cacheable: true,
assets: {},
};
this.buildInfo = {};
if(this.spriteAssetName) {
delete compilation.assets[this.spriteAssetName];
}
this.buildMeta.directoryHash = await new Promise((resolve, reject) => {
compilation.fileSystemInfo.getContextHash(this.config.folder, (err, hash) => {
if(err) {
reject(err);
} else {
resolve(hash);
}
});
(async () => {
const files = (await fs.readdir(this.config.folder)).map(e => path.join(this.config.folder, e));
this.sprite = await generateSprite(files);
this.spriteSvg = await generateSpriteSvg(this.sprite);
this.spriteAssetName = "sprite-" + sha1(this.spriteSvg).substr(-20) + ".svg";
this.spriteAssetUrl = (compilation.options.output.publicPath || "") + this.spriteAssetName;
compilation.assets[this.spriteAssetName] = new RawSource(this.spriteSvg);
this.spriteCss = "";
for(const cssOption of this.config.cssOptions) {
this.spriteCss += await generateSpriteCss(cssOption, this.config.cssClassPrefix, this.sprite, this.spriteAssetUrl);
}
this.spriteJs = await generateSpriteJs(this.config.dtsOptions, this.sprite, this.spriteAssetUrl, this.config.cssClassPrefix);
const dtsContent = await generateSpriteDts(this.config.dtsOptions, this.configName, this.sprite, this.config.cssClassPrefix, this.pluginConfig.modulePrefix);
await fs.writeFile(path.join(this.pluginConfig.dtsOutputFolder, this.configName + ".d.ts"), dtsContent);
})().then(() => {
callback();
}).catch(error => {
console.error(error);
callback("failed to generate sprite");
});
compilation.logger.info("Building SVG sprite for configuration %s (Hash: %s).", this.configName, this.buildMeta.directoryHash);
const files = await SystemFs.readdir(this.config.folder);
this.sprite = await generateSprite(files.map(file => path.join(this.config.folder, file)));
this.spriteSvg = await generateSpriteSvg(this.sprite);
this.spriteAssetName = "sprite-" + sha1(this.spriteSvg).substr(-20) + ".svg";
this.spriteAssetUrl = (this.pluginConfig.publicPath || "") + this.spriteAssetName;
this.buildInfo.assets[this.spriteAssetName] = new RawSource(this.spriteSvg);
this.spriteCss = "";
for(const cssOption of this.config.cssOptions) {
this.spriteCss += await generateSpriteCss(cssOption, this.config.cssClassPrefix, this.sprite, this.spriteAssetUrl);
}
this.spriteJs = await generateSpriteJs(this.config.dtsOptions, this.sprite, this.spriteAssetUrl, this.config.cssClassPrefix);
const dtsContent = await generateSpriteDts(this.config.dtsOptions, this.configName, this.sprite, this.config.cssClassPrefix, this.pluginConfig.modulePrefix, this.config.folder);
await SystemFs.writeFile(path.join(this.pluginConfig.dtsOutputFolder, this.configName + ".d.ts"), dtsContent);
compilation.logger.info("SVG sprite configuration %s contains %d/%d sprites", this.configName, this.sprite.entries.length, files.length);
}
codeGeneration(context) {
const sources = new Map();
source() {
const encodedCss = this.spriteCss
.replace(/%/g, "%25")
.replace(/"/g, "%22")
@ -160,9 +116,7 @@ class SvgSpriteModule extends Module {
lines.push(``);
lines.push(`/* initialize typescript objects */`);
lines.push(...this.spriteJs.split("\n"));
sources.set("javascript", new RawSource(lines.join("\n")));
return { sources: sources, runtimeRequirements: RUNTIME_REQUIREMENTS };
return new RawSource(lines.join("\n"));
}
size() {
@ -176,20 +130,8 @@ class SvgSpriteModule extends Module {
hash.update(this.spriteSvg || "none");
super.updateHash(hash, chunkGraph);
}
addReason(_requestModule, _dependency) { }
addCacheDependencies(
fileDependencies,
contextDependencies,
missingDependencies,
buildDependencies
) {
contextDependencies.add(this.config.folder);
}
}
export class SpriteGenerator {
readonly options: Options;
constructor(options: Options) {
@ -198,19 +140,20 @@ export class SpriteGenerator {
this.options.modulePrefix = this.options.modulePrefix || "svg-sprites/";
}
apply(compiler: Compiler) {
compiler.hooks.normalModuleFactory.tap("SpriteGenerator", normalModuleFactory => {
normalModuleFactory.hooks.resolve.tap("SpriteGenerator", resolveData => {
if(!resolveData.request.startsWith(this.options.modulePrefix)) {
apply(compiler: webpack.Compiler) {
compiler.hooks.thisCompilation.tap("SpriteGenerator", (compilation, { normalModuleFactory }) => {
normalModuleFactory.hooks.factory.tap("SpriteGenerator", factory => (data, callback) => {
if(data.request.startsWith(this.options.modulePrefix)) {
const configName = data.request.substr(this.options.modulePrefix.length);
if(this.options.configurations[configName] === undefined) {
callback("Missing SVG configuration " + configName);
return;
}
callback(null, new SvgSpriteModule(data.request, this.options, configName, this.options.configurations[configName]));
return;
}
const configName = resolveData.request.substring(this.options.modulePrefix.length);
if(!this.options.configurations[configName]) {
return;
}
return new SvgSpriteModule(resolveData.request, this.options, configName, this.options.configurations[configName]);
factory(data, callback);
});
});
}

View file

@ -1,2 +1 @@
## SVG Sprite generator for webpack with typescript support
An example usage could be found in the [demo](https://github.com/WolverinDEV/webpack-svg-sprites/tree/master/demo) folder.
# SVG Sprite generator for webpack with typescript support

View file

@ -5,8 +5,7 @@
"sourceMap": false,
"declarationDir": "dist/ts",
"declarationMap": false,
"declaration": true,
"esModuleInterop": true
"declaration": true
},
"include": [
"plugin"

View file

@ -1,9 +1,9 @@
import * as path from "path";
import {Configuration} from "webpack";
import {CleanWebpackPlugin} from "clean-webpack-plugin";
import CopyWebpackPlugin from "copy-webpack-plugin";
import * as CopyWebpackPlugin from "copy-webpack-plugin";
export default {
export = {
entry: "./plugin/index.ts",
module: {
rules: [
@ -51,7 +51,7 @@ export default {
target: "node",
output: {
path: process.env.OUTPUT_PATH || path.resolve(__dirname, "dist"),
path: path.resolve(__dirname, "dist"),
filename: "plugin.js",
libraryTarget: "umd",