UNPKG

glance-dom

Version:
110 lines (83 loc) 2.6 kB
'use strict'; Object.defineProperty(exports, "__esModule", { value: true }); var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; var _log = require('../../utils/log'); var _log2 = _interopRequireDefault(_log); var _filter2 = require('@arr/filter'); var _filter3 = _interopRequireDefault(_filter2); var _map = require('@arr/map'); var _map2 = _interopRequireDefault(_map); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } function sqr(x) { return x * x; } function distance(base, item) { return sqr(base.x - item.x) + sqr(base.y - item.y); } function distToSegment(base, item1, item2) { var l = distance(item1, item2); if (l === 0) return distance(base, item1); var t = ((base.x - item1.x) * (item2.x - item1.x) + (base.y - item1.y) * (item2.y - item1.y)) / l; if (t < 0) return distance(base, item1); if (t > 1) return distance(base, item2); return distance(base, { x: item1.x + t * (item2.x - item1.x), y: item1.y + t * (item2.y - item1.y) }); } function getSizeAndLocation(element) { var rect = element.getBoundingClientRect(); return _extends({ element: element }, rect, { x: rect.left, y: rect.top }); } function shortestDistance(a, t) { var p1 = t; var p2 = { x: t.x + t.width, y: t.y }; var p3 = { x: t.x + t.width, y: t.y + t.height }; var p4 = { x: t.x, y: t.y + t.height }; return Math.min(distToSegment(a, p1, p2), distToSegment(a, p2, p3), distToSegment(a, p4, p3), distToSegment(a, p1, p4)); } exports.default = { options: { 'closest': { filter: function filter(_ref) { var elements = _ref.elements, scopeElements = _ref.scopeElements; _log2.default.debug('Filtering for closest element to scope'); return (0, _map2.default)(scopeElements, function (scope) { var base = getSizeAndLocation(scope); var baseID = base.element; var a = base; a.x = a.x + base.width / 2; a.y = a.y + base.height / 2; var targets = (0, _map2.default)(elements, function (e) { return getSizeAndLocation(e); }); var sorted = (0, _filter3.default)(targets, function (t) { return t.element !== baseID; }).sort(function (x, y) { var l = shortestDistance(a, x); var r = shortestDistance(a, y); return l < r ? -1 : l > r ? 1 : 0; }); return sorted[0].element; }); } } } };