Skip to content
Merged
Show file tree
Hide file tree
Changes from 28 commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
918e868
fix(rn): 完善View组件渐变色宽高计算逻辑
wangshunnn Nov 26, 2025
88fe2dd
1.z-index auto 报错;2.样式编译优化:es6语法+__formatValue简化
wenwenhua Dec 10, 2025
9f754c5
del percentVisitor
wenwenhua Dec 11, 2025
c06680f
z-index auto
wenwenhua Dec 11, 2025
224617c
fix eslint
wenwenhua Dec 11, 2025
68deb03
fix(rn): update linear background size handling for percentage dimens…
wangshunnn Dec 12, 2025
15a38fe
Merge branch 'master' into fix-rn-view-linear
hiyuki Dec 23, 2025
6177871
支持 transform translateX(var(--un-translate-x, -50%)) translateY(var(-…
wenwenhua Dec 23, 2025
6d4cfdc
add calc translate percent
wenwenhua Dec 24, 2025
01dce81
Merge branch 'master' into feat-style-compile-251012
wenwenhua Dec 24, 2025
8c5413b
优化非媒体查询的_default&_media
wenwenhua Dec 24, 2025
661131f
优化非媒体查询的_default&_media
wenwenhua Dec 24, 2025
a061fa2
fix js error __getClassStyle is not function
wenwenhua Dec 24, 2025
b71205d
fix __formatValue to _f
wenwenhua Dec 24, 2025
0597ac7
del space
wenwenhua Dec 24, 2025
2b8b302
fix eslint
wenwenhua Dec 24, 2025
ef01c4d
fix 单测
wenwenhua Dec 24, 2025
379e41c
fix: 修复组件.mode后缀路径infix参数重复拼接
mackwang112 Dec 29, 2025
d43cea6
fix 偶现navigationHelper.lastSuccessCallback() null is not a function问题
Dec 29, 2025
a002c6a
Merge pull request #2371 from didi/fix-navigateBack-error
hiyuki Dec 30, 2025
83c7761
fix: 修复组件.mode后缀路径infix参数重复拼接
mackwang112 Dec 30, 2025
0efc0da
Merge branch 'master' into fix-mode-resolve
hiyuki Dec 31, 2025
de2990f
Merge branch 'master' into fix-rn-view-linear
hiyuki Dec 31, 2025
15f127f
Merge pull request #2370 from didi/fix-mode-resolve
hiyuki Dec 31, 2025
055881b
Merge branch 'master' into fix-rn-view-linear
hiyuki Dec 31, 2025
14aa457
Merge pull request #2345 from didi/fix-rn-view-linear
hiyuki Dec 31, 2025
9e49ee2
Merge branch 'master' into feat-style-compile-251012
wenwenhua Jan 4, 2026
dabdba6
feat: fix mr
wenwenhua Jan 4, 2026
b2d2ee3
Merge branch 'fix-drn-2.10.17' into feat-style-compile-251012
Blackgan3 Jan 5, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 4 additions & 2 deletions packages/api-proxy/src/platform/api/route/index.ios.js
Original file line number Diff line number Diff line change
Expand Up @@ -104,8 +104,10 @@ function navigateBack (options = {}) {
}
if (delta >= routeLength && global.__mpx?.config.rnConfig.onAppBack?.(delta - routeLength + 1)) {
nextTick(() => {
navigationHelper.lastSuccessCallback()
navigationHelper.lastSuccessCallback = null
if (navigationHelper.lastSuccessCallback) {
navigationHelper.lastSuccessCallback()
navigationHelper.lastSuccessCallback = null
}
})
} else {
navigation.pop(delta)
Expand Down
13 changes: 6 additions & 7 deletions packages/core/src/platform/builtInMixins/styleHelperMixin.ios.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { isObject, isArray, dash2hump, cached, isEmptyObject, hasOwn, getFocusedNavigation, noop } from '@mpxjs/utils'
import { isObject, isArray, dash2hump, cached, isEmptyObject, hasOwn, getFocusedNavigation } from '@mpxjs/utils'
import { StyleSheet, Dimensions } from 'react-native'
import { reactive } from '../../observer/reactive'
import Mpx from '../../index'
Expand All @@ -12,7 +12,7 @@ global.__mpxPageSizeCountMap = reactive({})

global.__GCC = function (className, classMap, classMapValueCache) {
if (!classMapValueCache.has(className)) {
const styleObj = classMap[className]?.()
const styleObj = classMap[className]?.(global.__formatValue)
styleObj && classMapValueCache.set(className, styleObj)
}
return classMapValueCache.get(className)
Expand Down Expand Up @@ -266,18 +266,17 @@ export default function styleHelperMixin () {

classString.split(/\s+/).forEach((className) => {
let localStyle, appStyle
const getAppClassStyle = global.__getAppClassStyle || noop
if (localStyle = this.__getClassStyle(className)) {
if (localStyle = this.__getClassStyle?.(className)) {
if (localStyle._media?.length) {
mergeResult(localStyle._default, getMediaStyle(localStyle._media))
} else {
mergeResult(localStyle._default)
mergeResult(localStyle)
}
} else if (appStyle = getAppClassStyle(className)) {
} else if (appStyle = global.__getAppClassStyle?.(className)) {
if (appStyle._media?.length) {
mergeResult(appStyle._default, getMediaStyle(appStyle._media))
} else {
mergeResult(appStyle._default)
mergeResult(appStyle)
}
} else if (isObject(this.__props[className])) {
// externalClasses必定以对象形式传递下来
Expand Down
15 changes: 15 additions & 0 deletions packages/webpack-plugin/lib/platform/style/wx/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -547,6 +547,15 @@ module.exports = function getSpec ({ warn, error }) {
return { prop, value: values[0].trim() }
}

const formatZIndex = ({ prop, value, selector }, { mode }) => {
// z-index auto 报错
if (value === 'auto') {
error(`Property [${prop}] does not supported [${value}] on ${selector} in ${mode} environment, please check again!`)
return { prop, value: 0 }
}
return { prop, value: value }
}

// const formatBoxShadow = ({ prop, value, selector }, { mode }) => {
// value = value.trim()
// if (value === 'none') {
Expand Down Expand Up @@ -612,6 +621,12 @@ module.exports = function getSpec ({ warn, error }) {
android: formatFontFamily,
harmony: formatFontFamily
},
{
test: 'z-index',
ios: formatZIndex,
android: formatZIndex,
harmony: formatZIndex
},
// {
// test: 'box-shadow',
// ios: formatBoxShadow,
Expand Down
20 changes: 10 additions & 10 deletions packages/webpack-plugin/lib/react/processStyles.js
Original file line number Diff line number Diff line change
Expand Up @@ -48,26 +48,29 @@ module.exports = function (styles, {
}, (err) => {
if (err) return callback(err)
try {
output += `
global.__classCaches = global.__classCaches || []
var __classCache = new Map()
global.__classCaches.push(__classCache)`
const formatValueName = '_f'
const classMap = getClassMap({
content,
filename: loaderContext.resourcePath,
mode,
srcMode,
ctorType,
warn,
error
error,
formatValueName
})
const classMapCode = Object.entries(classMap).reduce((result, [key, value]) => {
result !== '' && (result += ',')
result += `${isValidIdentifierStr(key) ? `${key}` : `['${key}']`}: () => (${shallowStringify(value)})`
result += `${isValidIdentifierStr(key) ? `${key}` : `['${key}']`}: function(${formatValueName}){return ${shallowStringify(value)};}`
return result
}, '')
if (ctorType === 'app') {
output += `
global.__classCaches = global.__classCaches || []
const __classCache = new Map()
global.__classCaches.push(__classCache)
let __appClassMap
var __appClassMap
global.__getAppClassStyle = function(className) {
if(!__appClassMap) {
__appClassMap = {${classMapCode}};
Expand All @@ -76,10 +79,7 @@ module.exports = function (styles, {
};\n`
} else {
output += `
global.__classCaches = global.__classCaches || []
const __classCache = new Map()
global.__classCaches.push(__classCache)
let __classMap
var __classMap
global.currentInject.injectMethods = {
__getClassStyle: function(className) {
if(!__classMap) {
Expand Down
37 changes: 20 additions & 17 deletions packages/webpack-plugin/lib/react/style-helper.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,9 @@ const unitRegExp = /^\s*(-?\d+(?:\.\d+)?)(rpx|vw|vh|px)?\s*$/
const hairlineRegExp = /^\s*hairlineWidth\s*$/
const varRegExp = /^--/
const cssPrefixExp = /^-(webkit|moz|ms|o)-/
function getClassMap ({ content, filename, mode, srcMode, ctorType, warn, error }) {
function getClassMap ({ content, filename, mode, srcMode, ctorType, formatValueName, warn, error }) {
const classMap = ctorType === 'page'
? {
[MPX_TAG_PAGE_SELECTOR]: {
_media: [],
_default: { flex: 1, height: "'100%'" }
}
}
? { [MPX_TAG_PAGE_SELECTOR]: { flex: 1, height: "'100%'" } }
: {}

const root = postcss.parse(content, {
Expand All @@ -30,12 +25,12 @@ function getClassMap ({ content, filename, mode, srcMode, ctorType, warn, error
value = matched[1]
needStringify = false
} else {
value = `global.__formatValue(${+matched[1]}, '${matched[2]}')`
value = `${formatValueName}(${+matched[1]}, '${matched[2]}')`
needStringify = false
}
}
if (hairlineRegExp.test(value)) {
value = `global.__formatValue(${JSON.stringify(value)}, 'hairlineWidth')`
value = `${formatValueName}(${JSON.stringify(value)}, 'hairlineWidth')`
needStringify = false
}
return needStringify ? JSON.stringify(value) : value
Expand Down Expand Up @@ -93,7 +88,7 @@ function getClassMap ({ content, filename, mode, srcMode, ctorType, warn, error
root.walkRules(rule => {
const classMapValue = {}
rule.walkDecls(({ prop, value }) => {
if (cssPrefixExp.test(prop) || cssPrefixExp.test(value)) return
if (value === 'undefined' || cssPrefixExp.test(prop) || cssPrefixExp.test(value)) return
let newData = rulesRunner({ prop, value, selector: rule.selector })
if (!newData) return
if (!Array.isArray(newData)) {
Expand Down Expand Up @@ -140,19 +135,27 @@ function getClassMap ({ content, filename, mode, srcMode, ctorType, warn, error
if (classMapKeys.length) {
classMapKeys.forEach((key) => {
if (Object.keys(classMapValue).length) {
const _default = classMap[key]?._default || {}
const _media = classMap[key]?._media || []
let _default = classMap[key]?._default
let _media = classMap[key]?._media
if (isMedia) {
// 当前是媒体查询
_default = _default || {}
_media = _media || []
_media.push({
options,
value: classMapValue
})
} else {
classMap[key] = {
_media,
_default
}
} else if (_default) {
// 已有媒体查询数据,此次非媒体查询
Object.assign(_default, classMapValue)
}
classMap[key] = {
_media,
_default
} else {
// 无媒体查询
const val = classMap[key] || {}
classMap[key] = Object.assign(val, classMapValue)
}
}
})
Expand Down
24 changes: 17 additions & 7 deletions packages/webpack-plugin/lib/resolver/AddModePlugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,21 +39,31 @@ module.exports = class AddModePlugin {

const queryObj = parseQuery(request.query || '?')
const queryInfix = queryObj.infix
if (!implicitMode) queryObj.mode = mode
queryObj.infix = `${queryInfix || ''}.${mode}`

// 如果已经确认是mode后缀的文件,添加query与mode后直接返回
if (modePattern.test(path.basename(resourcePath))) {
request.query = stringifyQuery(queryObj)
request.mode = obj.mode
// 已经被resolved到对应mode的文件,避免重复添加mode
const isResolved = (implicitMode || queryObj.mode === mode) && modePattern.test(queryObj.infix)
if (!isResolved) {
queryObj.infix = `${queryInfix || ''}.${mode}`
if (!implicitMode) queryObj.mode = mode
request.query = stringifyQuery(queryObj)
request.mode = obj.mode
}
return callback()
} else if (defaultMode && defaultModePattern.test(path.basename(resourcePath))) {
queryObj.infix = `${queryInfix || ''}.${defaultMode}`
request.query = stringifyQuery(queryObj)
request.mode = obj.mode
const isResolved = (implicitMode || queryObj.mode === mode) && defaultModePattern.test(queryObj.infix)
if (!isResolved) {
queryObj.infix = `${queryInfix || ''}.${defaultMode}`
if (!implicitMode) queryObj.mode = mode
request.query = stringifyQuery(queryObj)
request.mode = obj.mode
}
return callback()
}

if (!implicitMode) queryObj.mode = mode
queryObj.infix = `${queryInfix || ''}.${mode}`
obj.query = stringifyQuery(queryObj)
obj.path = addInfix(resourcePath, mode, extname)
obj.relativePath = request.relativePath && addInfix(request.relativePath, mode, extname)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -287,7 +287,7 @@ function backgroundSize (imageProps: ImageProps, preImageInfo: PreImageInfo, ima
} else { // 数值类型 ImageStyle
// 数值类型设置为 stretch
imageProps.resizeMode = 'stretch'
if (type === 'linear' && (!layoutWidth || !layoutHeight)) {
if (type === 'linear' && (!layoutWidth || !layoutHeight) && (isPercent(width) || isPercent(height))) {
// ios 上 linear 组件只要重新触发渲染,在渲染过程中外层容器 width 或者 height 被设置为 0,通过设置 % 的方式会渲染不出来,即使后面再更新为正常宽高也渲染不出来
// 所以 hack 手动先将 linear 宽高也设置为 0,后面再更新为正确的数值或 %。
dimensions = {
Expand Down
38 changes: 25 additions & 13 deletions packages/webpack-plugin/lib/runtime/components/react/utils.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { useEffect, useCallback, useMemo, useRef, ReactNode, ReactElement, isValidElement, useContext, useState, Dispatch, SetStateAction, Children, cloneElement, createElement, MutableRefObject } from 'react'
import { LayoutChangeEvent, TextStyle, ImageProps, Image } from 'react-native'
import { isObject, isFunction, isNumber, hasOwn, diffAndCloneA, error, warn } from '@mpxjs/utils'
import { isObject, isFunction, isNumber, hasOwn, diffAndCloneA, error, warn, isEmptyObject } from '@mpxjs/utils'
import { VarContext, ScrollViewContext, RouteContext } from './context'
import { ExpressionParser, parseFunc, ReplaceSource } from './parser'
import { initialWindowMetrics } from 'react-native-safe-area-context'
Expand Down Expand Up @@ -238,7 +238,7 @@ function transformVar (styleObj: Record<string, any>, varKeyPaths: Array<Array<s
const resolved = resolveVar(value, varContext)
if (resolved === undefined) {
delete target[key]
error(`Can not resolve css var at ${varKeyPath.join('.')}:${value}.`)
// error(`Can not resolve css var at ${varKeyPath.join('.')}:${value}.`)
return
}
target[key] = resolved
Expand Down Expand Up @@ -388,6 +388,14 @@ function transformBoxShadow (styleObj: Record<string, any>) {
}, '')
}

function transformZIndex (styleObj: Record<string, any>) {
if (!styleObj.zIndex || typeof styleObj.zIndex === 'number') return
if (styleObj.zIndex === 'auto') {
error('Property [z-index] does not supported [auto], please check again!')
styleObj.zIndex = 0
}
}

interface TransformStyleConfig {
enableVar?: boolean
externalVarContext?: Record<string, any>
Expand Down Expand Up @@ -444,17 +452,20 @@ export function useTransformStyle (styleObj: Record<string, any> = {}, { enableV
}
}

function calcVisitor ({ value, keyPath }: VisitorArg) {
function calcVisitor ({ key, value, keyPath }: VisitorArg) {
if (calcUseRegExp.test(value)) {
// calc translate & border-radius 的百分比计算
if (hasOwn(selfPercentRule, key) && /%/.test(value)) {
hasSelfPercent = true
percentKeyPaths.push(keyPath.slice())
}
calcKeyPaths.push(keyPath.slice())
}
}

function percentVisitor ({ key, value, keyPath }: VisitorArg) {
if (hasOwn(selfPercentRule, key) && PERCENT_REGEX.test(value)) {
hasSelfPercent = true
percentKeyPaths.push(keyPath.slice())
} else if ((key === 'fontSize' || key === 'lineHeight') && PERCENT_REGEX.test(value)) {
// fixme 去掉 translate & border-radius 的百分比计算
if ((key === 'fontSize' || key === 'lineHeight') && PERCENT_REGEX.test(value)) {
percentKeyPaths.push(keyPath.slice())
}
}
Expand All @@ -464,10 +475,10 @@ export function useTransformStyle (styleObj: Record<string, any> = {}, { enableV
[envVisitor, percentVisitor, calcVisitor].forEach(visitor => visitor({ target, key, value, keyPath }))
}
}

// transform 字符串格式转化数组格式(先转数组再处理css var)
transformTransform(styleObj)
// traverse var & generate normalStyle
traverseStyle(styleObj, [varVisitor])

hasVarDec = hasVarDec || !!externalVarContext
enableVar = enableVar || hasVarDec || hasVarUse
const enableVarRef = useRef(enableVar)
Expand Down Expand Up @@ -531,10 +542,11 @@ export function useTransformStyle (styleObj: Record<string, any> = {}, { enableV
transformStringify(normalStyle)
// transform rpx to px
transformBoxShadow(normalStyle)

// transform 字符串格式转化数组格式
transformTransform(normalStyle)

// transform z-index auto to 0
transformZIndex(normalStyle)
if (Array.isArray(normalStyle.transform)) {
normalStyle.transform = normalStyle.transform.filter(item => !isEmptyObject(item))
}
return {
hasVarDec,
varContextRef,
Expand Down
Loading