-
Notifications
You must be signed in to change notification settings - Fork 10
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(libs): fontsource api, font selector
- Loading branch information
1 parent
acb0c71
commit f3c12df
Showing
15 changed files
with
449 additions
and
435 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
{ | ||
"name": "@twir/fontsource", | ||
"type": "module", | ||
"types": "./src/index.ts", | ||
"exports": { | ||
".": "./src/index.ts" | ||
}, | ||
"dependencies": { | ||
"naive-ui": "2.35.0", | ||
"vue": "3.3.12" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
<script setup lang="ts"> | ||
import type { SelectOption } from 'naive-ui'; | ||
import { NSelect } from 'naive-ui'; | ||
import { ref, computed, watch, h } from 'vue'; | ||
import { useFontSource } from '../composable/use-fontsource.js'; | ||
const props = defineProps<{ | ||
initialFontFamily: string | ||
}>(); | ||
const emits = defineEmits<{ | ||
'update-font-family': [fontFamily: string] | ||
}>(); | ||
const fontSource = useFontSource(); | ||
const selectedFont = ref(props.initialFontFamily); | ||
watch(() => selectedFont.value, async (font) => { | ||
if (!font || fontSource.loading.value) return; | ||
await fontSource.loadFont(font); | ||
emits('update-font-family', font); | ||
}); | ||
const options = computed((): SelectOption[] => { | ||
return fontSource.fonts.value.map((font) => ({ | ||
label: font.family, | ||
value: font.id, | ||
})); | ||
}); | ||
function renderLabel(option: SelectOption) { | ||
if (!fontSource.loading.value) { | ||
fontSource.loadFont(option.value as string); | ||
} | ||
return h( | ||
'div', | ||
{ style: { 'font-family': `"${option.value}"` } }, | ||
{ default: () => option.label }, | ||
); | ||
} | ||
</script> | ||
|
||
<template> | ||
<n-select | ||
v-model:value="selectedFont" | ||
:default-value="props.initialFontFamily" | ||
:render-label="renderLabel" | ||
filterable | ||
:options="options" | ||
:loading="fontSource.loading.value" | ||
:disabled="fontSource.loading.value" | ||
check-strategy="child" | ||
/> | ||
</template> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
import { ref, onMounted } from 'vue'; | ||
|
||
import { loadFontItems, loadFont as loadFontById } from '../helpers.js'; | ||
import type { FontItem } from '../types.js'; | ||
|
||
export function useFontSource() { | ||
const loading = ref(true); | ||
const fonts = ref<FontItem[]>([]); | ||
|
||
onMounted(async () => { | ||
try { | ||
fonts.value = await loadFontItems(); | ||
} catch (err) { | ||
console.error(err); | ||
} finally { | ||
loading.value = false; | ||
} | ||
}); | ||
|
||
async function loadFont(fontId: string, fontWeight = 400) { | ||
for (const fontFace of document.fonts.values()) { | ||
if (fontFace.family === fontId) return; | ||
} | ||
|
||
try { | ||
await loadFontById(fontId, fontWeight); | ||
} catch (err) { | ||
console.error(err); | ||
} | ||
} | ||
|
||
return { | ||
loading, | ||
fonts, | ||
loadFont, | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
export const FONTSOURCE_API_URL = 'https://api.fontsource.org/v1'; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
import { FONTSOURCE_API_URL } from './constants.js'; | ||
import type { Font, FontItem } from './types.js'; | ||
|
||
export async function loadFontItems() { | ||
const response = await fetch(`${FONTSOURCE_API_URL}/fonts`); | ||
const fonts = await response.json() as FontItem[]; | ||
return fonts; | ||
} | ||
|
||
export async function loadFont(fontId: string, fontWeight = 400) { | ||
const response = await fetch(`${FONTSOURCE_API_URL}/fonts/${fontId}`); | ||
const font = await response.json() as Font; | ||
|
||
// eslint-disable-next-line @typescript-eslint/ban-ts-comment | ||
// @ts-ignore | ||
const fontSource = `url(${font.variants[fontWeight].normal.latin.url.woff2})`; | ||
const fontFace = new FontFace(font.id, fontSource); | ||
await fontFace.load(); | ||
document.fonts.add(fontFace); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
import FontSelector from './components/font-selector.vue'; | ||
import { useFontSource } from './composable/use-fontsource.js'; | ||
|
||
export { | ||
FontSelector, | ||
useFontSource, | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
export type FontVariants = | ||
| '100' | ||
| '200' | ||
| '300' | ||
| '400' | ||
| '500' | ||
| '600' | ||
| '700' | ||
| '800' | ||
| '900' | ||
|
||
export type FontStyle = 'normal' | 'italic' | ||
export type FontSubset = 'latin' | 'cyrillic' | ||
export type FontType = 'woff2' | ||
|
||
export interface FontItem { | ||
category: string | ||
defSubset: string | ||
family: string | ||
id: string | ||
lastModified: string | ||
styles: FontStyle[] | ||
subsets: FontSubset[] | ||
type: string | ||
variable: boolean | ||
version: string | ||
weights: number[] | ||
} | ||
|
||
export type FontVariant = { | ||
[key in FontVariants]: { | ||
[key in FontStyle]: { | ||
[key in FontSubset]: { | ||
url: { | ||
[key in FontType]: string | ||
} | ||
} | ||
} | ||
} | ||
} | ||
|
||
export interface Font { | ||
id: string | ||
family: string | ||
subsets: FontSubset | ||
weights: number[] | ||
styles: string[] | ||
unicodeRange: { | ||
[key in FontSubset]: string | ||
} | ||
defSubset: string | ||
variable: boolean | ||
category: string | ||
version: string | ||
type: string | ||
variants: FontVariant | ||
} |
Oops, something went wrong.