Skip to content
Snippets Groups Projects
Select Git revision
  • 3e81f2cf1500a3589d8236bd04e6ad52534e7f60
  • master default protected
  • 0.5.9
  • 0.5.8
  • 0.5.7
  • 0.5.6
  • 0.5.5
  • 0.5.4
  • 0.5.3
  • 0.5.2
  • 0.5.1
  • 0.5.0
  • 0.4.17
  • 0.4.16
  • 0.4.15
  • 0.4.14
  • 0.4.13
  • 0.4.12
  • 0.4.11
  • 0.4.10
  • 0.4.9
  • 0.4.8
22 results

path.go

Blame
  • dimension.mjs 2.97 KiB
    /**
     * Copyright schukai GmbH and contributors 2023. All Rights Reserved.
     * Node module: @schukai/monster
     * This file is licensed under the AGPLv3 License.
     * License text available at https://www.gnu.org/licenses/agpl-3.0.en.html
     */
    
    import { getWindow } from "./util.mjs";
    import { validateString } from "../types/validate.mjs";
    
    export { convertToPixels, getDeviceDPI };
    
    /**
     * Stores the DPI of the device.
     *
     * @private
     * @returns {number}
     * @since 3.34.0
     * @type {number|function}
     */
    let CURRENT_DEVICE_DPI = function () {
    	let i = 0;
    	for (i = 56; i < 2000; i++) {
    		if (getWindow().matchMedia(`(max-resolution: ${i}dpi)`).matches === true) {
    			return i;
    		}
    	}
    	return i;
    };
    
    /**
     * Returns the DPI of the device.
     *
     * @since 3.34.0
     * @memberOf Monster.DOM
     * @returns {number}
     */
    function getDeviceDPI() {
    	// only call the function once
    	if (typeof CURRENT_DEVICE_DPI === "function") {
    		CURRENT_DEVICE_DPI = CURRENT_DEVICE_DPI();
    	}
    
    	return getWindow().devicePixelRatio * CURRENT_DEVICE_DPI;
    }
    
    /**
     * Converts a CSS value to pixels.
     *
     * As Example:
     *
     * ```js
     * convertToPixels('1em') // returns the current font size in pixels
     * convertToPixels('1rem') // returns the current root font size in pixels
     * convertToPixels('1px') // returns 1
     * convertToPixels('100%') // returns the current width of the parent element in pixels
     * ```
     *
     * Following units are supported:
     * - px
     * - em
     * - rem
     * - %
     *
     * @param {string} value
     * @param {HTMLElement} [parentElement=document.documentElement]
     * @param {HTMLElement} [fontSizeElement=document.documentElement]
     * @returns {number}
     * @license AGPLv3
     * @since 3.34.0
     * @copyright schukai GmbH
     * @throws {Error} Unsupported unit
     * @memberOf Monster.DOM
     * @throws {Error} Invalid value format
     */
    
    function convertToPixels(
    	value,
    	parentElement = document.documentElement,
    	fontSizeElement = document.documentElement,
    ) {
    	validateString(value);
    
    	const regex = /^(-?[\d.]+)(.*)$/;
    	const matchResult = value.match(regex);
    
    	if (!matchResult) {
    		throw new Error(`Invalid value format: ${value}`);
    	}
    
    	const [, num, unit] = matchResult;
    	const number = parseFloat(num);
    	const dpi = getDeviceDPI();
    
    	if (unit === "px") {
    		return number;
    	} else if (unit === "em") {
    		const fontSize = parseFloat(
    			window.getComputedStyle(fontSizeElement).fontSize,
    		);
    		return number * fontSize;
    	} else if (unit === "rem") {
    		const rootFontSize = parseFloat(
    			window.getComputedStyle(parentElement).fontSize,
    		);
    		return number * rootFontSize;
    	} else if (unit === "%") {
    		const parentWidth = parseFloat(
    			window.getComputedStyle(parentElement).width,
    		);
    		return (number * parentWidth) / 100;
    	} else if (unit === "in") {
    		return number * dpi;
    	} else if (unit === "cm") {
    		return (number * dpi) / 2.54;
    	} else if (unit === "mm") {
    		return (number * dpi) / 25.4;
    	} else if (unit === "pt") {
    		return (number * dpi) / 72;
    	} else if (unit === "pc") {
    		return (number * dpi) / 6;
    	} else {
    		throw new Error(`Unsupported unit: ${unit}`);
    	}
    }