mirror of
https://github.com/zoriya/react-native-svg.git
synced 2025-12-20 14:05:09 +00:00
Transverse Box Alignment, specifies how an inline-level box is aligned within the line, and by how much the box is shifted up from its alignment point. https://drafts.csswg.org/css-inline/#propdef-vertical-align https://www.w3.org/TR/css-inline-3/#propdef-baseline-shift https://www.w3.org/TR/css-inline-3/#transverse-alignment
146 lines
3.7 KiB
JavaScript
146 lines
3.7 KiB
JavaScript
import _ from 'lodash';
|
|
//noinspection JSUnresolvedVariable
|
|
import React, {Children} from 'react';
|
|
import TSpan from '../../elements/TSpan';
|
|
import extractLengthList from './extractLengthList';
|
|
|
|
const fontRegExp = /^\s*((?:(?:normal|bold|italic)\s+)*)(?:(\d+(?:\.\d+)?[ptexm%])*(?:\s*\/.*?)?\s+)?\s*"?([^"]*)/i;
|
|
const fontFamilyPrefix = /^[\s"']*/;
|
|
const fontFamilySuffix = /[\s"']*$/;
|
|
const commaReg = /\s*,\s*/g;
|
|
|
|
const cachedFontObjectsFromString = {};
|
|
|
|
function extractSingleFontFamily(fontFamilyString) {
|
|
// SVG on the web allows for multiple font-families to be specified.
|
|
// For compatibility, we extract the first font-family, hoping
|
|
// we'll get a match.
|
|
return fontFamilyString ? fontFamilyString.split(commaReg)[0]
|
|
.replace(fontFamilyPrefix, '')
|
|
.replace(fontFamilySuffix, '') : null;
|
|
}
|
|
|
|
function parseFontString(font) {
|
|
if (cachedFontObjectsFromString.hasOwnProperty(font)) {
|
|
return cachedFontObjectsFromString[font];
|
|
}
|
|
const match = fontRegExp.exec(font);
|
|
if (!match) {
|
|
return null;
|
|
}
|
|
const fontFamily = extractSingleFontFamily(match[3]);
|
|
const fontSize = match[2] || '12';
|
|
const isBold = /bold/.exec(match[1]);
|
|
const isItalic = /italic/.exec(match[1]);
|
|
const fontWeight = isBold ? 'bold' : 'normal';
|
|
const fontStyle = isItalic ? 'italic' : 'normal';
|
|
cachedFontObjectsFromString[font] = {
|
|
fontSize,
|
|
fontFamily,
|
|
fontWeight,
|
|
fontStyle,
|
|
};
|
|
return cachedFontObjectsFromString[font];
|
|
}
|
|
|
|
export function extractFont(props) {
|
|
const {
|
|
fontStyle,
|
|
fontVariant,
|
|
fontWeight,
|
|
fontStretch,
|
|
textAnchor,
|
|
textDecoration,
|
|
letterSpacing,
|
|
wordSpacing,
|
|
kerning,
|
|
fontVariantLigatures,
|
|
} = props;
|
|
let {
|
|
fontSize,
|
|
fontFamily,
|
|
font,
|
|
} = props;
|
|
|
|
fontFamily = extractSingleFontFamily(fontFamily);
|
|
fontSize = fontSize ? '' + fontSize : null;
|
|
|
|
const ownedFont = _.pickBy({
|
|
fontStyle,
|
|
fontVariant,
|
|
fontWeight,
|
|
fontStretch,
|
|
fontSize,
|
|
fontFamily,
|
|
textAnchor,
|
|
textDecoration,
|
|
letterSpacing,
|
|
wordSpacing,
|
|
kerning,
|
|
fontVariantLigatures,
|
|
}, prop => !_.isNil(prop));
|
|
|
|
if (typeof font === 'string') {
|
|
font = parseFontString(font);
|
|
}
|
|
|
|
return _.defaults(ownedFont, font);
|
|
}
|
|
|
|
export default function(props, container) {
|
|
const {
|
|
x,
|
|
y,
|
|
dx,
|
|
dy,
|
|
alignmentBaseline,
|
|
baselineShift,
|
|
verticalAlign,
|
|
} = props;
|
|
let {
|
|
rotate,
|
|
children
|
|
} = props;
|
|
|
|
const positionX = extractLengthList(x);
|
|
const positionY = extractLengthList(y);
|
|
const deltaX = extractLengthList(dx);
|
|
const deltaY = extractLengthList(dy);
|
|
rotate = extractLengthList(rotate);
|
|
|
|
let content = null;
|
|
if (typeof children === 'string' || typeof children === 'number') {
|
|
const childrenString = children.toString();
|
|
if (container) {
|
|
children = <TSpan>{childrenString}</TSpan>;
|
|
} else {
|
|
content = childrenString;
|
|
children = null;
|
|
}
|
|
} else if (Children.count(children) > 1 || Array.isArray(children)) {
|
|
children = Children.map(children, child => {
|
|
if (typeof child === 'string' || typeof child === 'number') {
|
|
return <TSpan>{child.toString()}</TSpan>;
|
|
} else {
|
|
return child;
|
|
}
|
|
});
|
|
}
|
|
|
|
const font = extractFont(props);
|
|
|
|
return {
|
|
font,
|
|
children,
|
|
content,
|
|
positionX,
|
|
positionY,
|
|
rotate,
|
|
deltaX,
|
|
deltaY,
|
|
alignmentBaseline,
|
|
baselineShift,
|
|
verticalAlign,
|
|
};
|
|
}
|