magento2后台修改eav属性对应的模板
简介
很多情况下我们需要修改后台eav属性对应的模板文件。以下是通过修改模板文件让客户无法在后台修改multiple select,也就是disable multiple select。
代码
1 | <!-- |
接下来修改modifyMeta
1 | //Silk\AdvancedEstimatedShippingDate\Ui\DataProvider\Product\Form\Modifier\esd |
最后加上template文件
1 | <!-- |
很多情况下我们需要修改后台eav属性对应的模板文件。以下是通过修改模板文件让客户无法在后台修改multiple select,也就是disable multiple select。
1 | <!-- |
接下来修改modifyMeta
1 | //Silk\AdvancedEstimatedShippingDate\Ui\DataProvider\Product\Form\Modifier\esd |
最后加上template文件
1 | <!-- |
由于 Ubuntu 是基于 Debian 的 linux 操作系统,在默认的情况下,是没有超级用户(superuser, root)的,但有些系统操作必须有超级用户的权限才能进行,如手动释放内存等。 在其他 linux 操作系统(如 fedora)下,可以使用 su 切换到超级用户。 当输入 su 命令后,系统会要求输入 root 的密码。 可是,在 Ubuntu 下我们根本不知道 root 的密码是什么。 这样,在 Ubuntu 下切换到超级用户需要使用其他方法,主要有两种: 1) sudo -i sudo 是 su 的加强版,意思是 do something as the supervisor。不需要密码就可以得到 root 的权限。 但是它也有很多限制,比如,在默认的情况下,只能在 5 分钟之内使用 root 权限。 2)如果想一直使用 root 权限,还是要使用 su,还是要得到 root 密码的。 用 sudo passwd root
可以设置 root 的密码。 之后就可以自由使用 su 命令啦。
本篇文章是对PHP函数ip2long转换IP时数值太大产生负数的解决方法进行了详细的分析介绍,需要的朋友参考下 【造成原因】:Because PHP’s integer type is signed, and many IP addresses will result in negative integers. 【解决办法】:其官方手册中提到,可以“you need to use the “%u” formatter of sprintf() or printf() to get the string representation of the unsigned IP address” 即,printf( ‘%u’,ip2long(‘IP地址’ ) ); 或者将其先转换为二进制然后在转换为十进制,bindec(decbinip2long( ‘IP地址’ ) ) ); 【测试】
$strIp = '182.118.0.0';
echo ip2long($strIp); //此时输出的-1233780736
echo 'br/';
echo bindec( decbin( ip2long( $strIp ) ) ); // 输出3061186560,与MySQL函数输出一致~
【注】: number bindec ( string $binary_string ); //二进制转换为十进制 string decbin ( int $number ); //十进制转换为二进制
Indexer.php 添加同义词
通过带参数的选项 --add-synonym
来实现,参数值为单条或多条同义词记录,每条记录之间用冒号(:) 分隔原词和同义词,多条记录之间用逗号分割。您可以对同一个“原词”增加多个不同的“同义词”, 如果库内已存在完全一致的记录,则指令不起作用也不会报错。用法如下:
# 给 search 增加同义词 find
util/Indexer.php demo –add-synonym search:find
# 再给 search 增加另一个同义词 seek
util/Indexer.php demo –add-synonym search:seek
# 给 “搜索” 增加 “检索” “查找” 两个同义词
util/Indexer.php demo -add-synonym 搜索:检索,搜索:查找
# 给 “Hello world” 增加同义词 “你好”,参数含空格请用引号包围
util/Indexer.php demo –add-synonym “Hello world:你好”
删除同义词作法和添加同义词很相似,只不过采用选项 --del-synonym
,同时参数中的同义词可以 省略表示删除该“原词”的所有同义词记录。用法如下:
# 删除 search 的全部同义词、同时删除 “搜索” 的同义词 “检索”
util/Indexer.php demo –del-synonym search,搜索:检索
invalidate()函数的主要作用是请求View树进行重绘,该函数可以由应用程序调用,或者由系统函数间接调用,例如setEnable(), setSelected(), setVisiblity()都会间接调用到invalidate()来请求View树重绘,更新View树的显示。 注:requestLayout()和requestFocus()函数也会引起视图重绘 下面我们通过源码来了解invalidate()函数的工作原理,首先我们来看View类中invalidate()的实现过程:
[java] view plaincopy
invalidate()函数会转而调用invalidate(true),继续往下看:
[java] view plaincopy
/**
* This is where the invalidate() work actually happens. A full invalidate()
* causes the drawing cache to be invalidated, but this function can be called with
* invalidateCache set to false to skip that invalidation step for cases that do not
* need it (for example, a component that remains at the same dimensions with the same
* content).
*
* @param invalidateCache Whether the drawing cache for this view should be invalidated as
* well. This is usually true for a full invalidate, but may be set to false if the
* View’s contents or dimensions have not changed.
*/
void invalidate(boolean invalidateCache) {
if (ViewDebug.TRACE_HIERARCHY) {
ViewDebug.trace(this, ViewDebug.HierarchyTraceType.INVALIDATE);
}
if (skipInvalidate()) {
return;
}
if ((mPrivateFlags & (DRAWN | HAS_BOUNDS)) == (DRAWN | HAS_BOUNDS) ||
(invalidateCache && (mPrivateFlags & DRAWING_CACHE_VALID) == DRAWING_CACHE_VALID) ||
(mPrivateFlags & INVALIDATED) != INVALIDATED || isOpaque() != mLastIsOpaque) {
mLastIsOpaque = isOpaque();
mPrivateFlags &= ~DRAWN;
mPrivateFlags |= DIRTY;
if (invalidateCache) {
mPrivateFlags |= INVALIDATED;
mPrivateFlags &= ~DRAWING_CACHE_VALID;
}
final AttachInfo ai = mAttachInfo;
final ViewParent p = mParent;
//noinspection PointlessBooleanExpression,ConstantConditions
if (!HardwareRenderer.RENDER_DIRTY_REGIONS) {
if (p != null && ai != null && ai.mHardwareAccelerated) {
// fast-track for GL-enabled applications; just invalidate the whole hierarchy
// with a null dirty rect, which tells the ViewAncestor to redraw everything
p.invalidateChild(this, null);
return;
}
}
if (p != null && ai != null) {
final Rect r = ai.mTmpInvalRect;
r.set(0, 0, mRight - mLeft, mBottom - mTop);
// Don’t call invalidate – we don’t want to internally scroll
// our own bounds
p.invalidateChild(this, r);
}
}
}
下面我们来具体进行分析invalidate(true)函数的执行流程: 1、首先调用skipInvalidate(),该函数主要判断该View是否不需要重绘,如果不许要重绘则直接返回,不需要重绘的条件是该View不可见并且未进行动画 2、接下来的if语句是来进一步判断View是否需要绘制,其中表达式 (mPrivateFlags & (DRAWN | HAS_BOUNDS)) == (DRAWN | HAS_BOUNDS)的意思指的是如果View需要重绘并且其大小不为0,其余几个本人也未完全理解,还望高手指点~~如果需要重绘,则处理相关标志位 3、对于开启硬件加速的应用程序,则调用父视图的invalidateChild函数绘制整个区域,否则只绘制dirty区域(r变量所指的区域),这是一个向上回溯的过程,每一层的父View都将自己的显示区域与传入的刷新Rect做交集。 接下来看invalidateChild()的 实现过程:
[java] view plaincopy
public final void invalidateChild(View child, final Rect dirty) {
if (ViewDebug.TRACE_HIERARCHY) {
ViewDebug.trace(this, ViewDebug.HierarchyTraceType.INVALIDATE_CHILD);
}
ViewParent parent = this;
final AttachInfo attachInfo = mAttachInfo;
if (attachInfo != null) {
// If the child is drawing an animation, we want to copy this flag onto
// ourselves and the parent to make sure the invalidate request goes
// through
final boolean drawAnimation = (child.mPrivateFlags & DRAW_ANIMATION) == DRAW_ANIMATION;
if (dirty == null) {
if (child.mLayerType != LAYER_TYPE_NONE) {
mPrivateFlags |= INVALIDATED;
mPrivateFlags &= ~DRAWING_CACHE_VALID;
child.mLocalDirtyRect.setEmpty();
}
do {
View view = null;
if (parent instanceof View) {
view = (View) parent;
if (view.mLayerType != LAYER_TYPE_NONE) {
view.mLocalDirtyRect.setEmpty();
if (view.getParent() instanceof View) {
final View grandParent = (View) view.getParent();
grandParent.mPrivateFlags |= INVALIDATED;
grandParent.mPrivateFlags &= ~DRAWING_CACHE_VALID;
}
}
if ((view.mPrivateFlags & DIRTY_MASK) != 0) {
// already marked dirty - we’re done
break;
}
}
if (drawAnimation) {
if (view != null) {
view.mPrivateFlags |= DRAW_ANIMATION;
} else if (parent instanceof ViewRootImpl) {
((ViewRootImpl) parent).mIsAnimating = true;
}
}
if (parent instanceof ViewRootImpl) {
((ViewRootImpl) parent).invalidate();
parent = null;
} else if (view != null) {
if ((view.mPrivateFlags & DRAWN) == DRAWN ||
(view.mPrivateFlags & DRAWING_CACHE_VALID) == DRAWING_CACHE_VALID) {
view.mPrivateFlags &= ~DRAWING_CACHE_VALID;
view.mPrivateFlags |= DIRTY;
parent = view.mParent;
} else {
parent = null;
}
}
} while (parent != null);
} else {
// Check whether the child that requests the invalidate is fully opaque
final boolean isOpaque = child.isOpaque() && !drawAnimation &&
child.getAnimation() == null;
// Mark the child as dirty, using the appropriate flag
// Make sure we do not set both flags at the same time
int opaqueFlag = isOpaque ? DIRTY_OPAQUE : DIRTY;
if (child.mLayerType != LAYER_TYPE_NONE) {
mPrivateFlags |= INVALIDATED;
mPrivateFlags &= ~DRAWING_CACHE_VALID;
child.mLocalDirtyRect.union(dirty);
}
final int[] location = attachInfo.mInvalidateChildLocation;
location[CHILD_LEFT_INDEX] = child.mLeft;
location[CHILD_TOP_INDEX] = child.mTop;
Matrix childMatrix = child.getMatrix();
if (!childMatrix.isIdentity()) {
RectF boundingRect = attachInfo.mTmpTransformRect;
boundingRect.set(dirty);
//boundingRect.inset(-0.5f, -0.5f);
childMatrix.mapRect(boundingRect);
dirty.set((int) (boundingRect.left - 0.5f),
(int) (boundingRect.top - 0.5f),
(int) (boundingRect.right + 0.5f),
(int) (boundingRect.bottom + 0.5f));
}
do {
View view = null;
if (parent instanceof View) {
view = (View) parent;
if (view.mLayerType != LAYER_TYPE_NONE &&
view.getParent() instanceof View) {
final View grandParent = (View) view.getParent();
grandParent.mPrivateFlags |= INVALIDATED;
grandParent.mPrivateFlags &= ~DRAWING_CACHE_VALID;
}
}
if (drawAnimation) {
if (view != null) {
view.mPrivateFlags |= DRAW_ANIMATION;
} else if (parent instanceof ViewRootImpl) {
((ViewRootImpl) parent).mIsAnimating = true;
}
}
// If the parent is dirty opaque or not dirty, mark it dirty with the opaque
// flag coming from the child that initiated the invalidate
if (view != null) {
if ((view.mViewFlags & FADING_EDGE_MASK) != 0 &&
view.getSolidColor() == 0) {
opaqueFlag = DIRTY;
}
if ((view.mPrivateFlags & DIRTY_MASK) != DIRTY) {
view.mPrivateFlags = (view.mPrivateFlags & ~DIRTY_MASK) | opaqueFlag;
}
}
parent = parent.invalidateChildInParent(location, dirty);
if (view != null) {
// Account for transform on current parent
Matrix m = view.getMatrix();
if (!m.isIdentity()) {
RectF boundingRect = attachInfo.mTmpTransformRect;
boundingRect.set(dirty);
m.mapRect(boundingRect);
dirty.set((int) boundingRect.left, (int) boundingRect.top,
(int) (boundingRect.right + 0.5f),
(int) (boundingRect.bottom + 0.5f));
}
}
} while (parent != null);
}
}
}
大概流程如下,我们主要关注dirty区域不是null(非硬件加速)的情况: 1、判断子视图是否是不透明的(不透明的条件是isOpaque()返回true,视图未进行动画以及child.getAnimation() == null),并将判断结果保存到变量isOpaque中,如果不透明则将变量opaqueFlag设置为DIRTY_OPAQUE,否则设置为DIRTY。 2、定义location保存子视图的左上角坐标 3、如果子视图正在动画,那么父视图也要添加动画标志,如果父视图是ViewGroup,那么给mPrivateFlags添加DRAW_ANIMATION标识,如果父视图是ViewRoot,则给其内部变量mIsAnimating赋值为true 4、设置dirty标识,如果子视图是不透明的,则父视图设置为DIRTY_OPAQUE,否则设置为DIRTY 5、调用parent.invalidateChildInparent(),这里的parent有可能是ViewGroup,也有可能是ViewRoot(最后一次while循环),首先来看ViewGroup, ViewGroup中该函数的主要作用是对dirty区域进行计算 以上过程的主体是一个do{}while{}循环,不断的将子视图的dirty区域与父视图做运算来确定最终要重绘的dirty区域,最终循环到ViewRoot(ViewRoot的parent为null)为止,并将dirty区域保存到ViewRoot的mDirty变量中
[java] view plaincopy
/**
* Don’t call or override this method. It is used for the implementation of
* the view hierarchy.
*
* This implementation returns null if this ViewGroup does not have a parent,
* if this ViewGroup is already fully invalidated or if the dirty rectangle
* does not intersect with this ViewGroup’s bounds.
*/
public ViewParent invalidateChildInParent(final int[] location, final Rect dirty) {
if (ViewDebug.TRACE_HIERARCHY) {
ViewDebug.trace(this, ViewDebug.HierarchyTraceType.INVALIDATE_CHILD_IN_PARENT);
}
if ((mPrivateFlags & DRAWN) == DRAWN ||
(mPrivateFlags & DRAWING_CACHE_VALID) == DRAWING_CACHE_VALID) {
if ((mGroupFlags & (FLAG_OPTIMIZE_INVALIDATE | FLAG_ANIMATION_DONE)) !=
FLAG_OPTIMIZE_INVALIDATE) {
dirty.offset(location[CHILD_LEFT_INDEX] - mScrollX,
location[CHILD_TOP_INDEX] - mScrollY);
final int left = mLeft;
final int top = mTop;
if ((mGroupFlags & FLAG_CLIP_CHILDREN) != FLAG_CLIP_CHILDREN ||
dirty.intersect(0, 0, mRight - left, mBottom - top) ||
(mPrivateFlags & DRAW_ANIMATION) == DRAW_ANIMATION) {
mPrivateFlags &= ~DRAWING_CACHE_VALID;
location[CHILD_LEFT_INDEX] = left;
location[CHILD_TOP_INDEX] = top;
if (mLayerType != LAYER_TYPE_NONE) {
mLocalDirtyRect.union(dirty);
}
return mParent;
}
} else {
mPrivateFlags &= ~DRAWN & ~DRAWING_CACHE_VALID;
location[CHILD_LEFT_INDEX] = mLeft;
location[CHILD_TOP_INDEX] = mTop;
if ((mGroupFlags & FLAG_CLIP_CHILDREN) == FLAG_CLIP_CHILDREN) {
dirty.set(0, 0, mRight - mLeft, mBottom - mTop);
} else {
// in case the dirty rect extends outside the bounds of this container
dirty.union(0, 0, mRight - mLeft, mBottom - mTop);
}
if (mLayerType != LAYER_TYPE_NONE) {
mLocalDirtyRect.union(dirty);
}
return mParent;
}
}
return null;
}
该函数首先调用offset将子视图的坐标位置转换为在父视图(当前视图)的显示位置,这里主要考虑scroll后导致子视图在父视图中的显示区域会发生变化,接着调用union函数求得当前视图与子视图的交集,求得的交集必定是小于dirty的范围,因为子视图的dirty区域有可能超出其父视图(当前视图)的范围,最后返回当前视图的父视图。 再来看ViewRoot中invalidateChildInparent的执行过程:
[java] view plaincopy
该函数仅仅调用了ViewRoot的invalidateChild,下面继续看invalidateChild的源码:
[java] view plaincopy
具体分析如下: 1、判断此次调用是否在UI线程中进行 2、将dirty的坐标位置转换为ViewRoot的屏幕显示区域 3、更新mDirty变量,并调用scheduleTraversals发起重绘请求 至此一次invalidate()就结束了 总结:invalidate主要给需要重绘的视图添加DIRTY标记,并通过和父视图的矩形运算求得真正需要绘制的区域,并保存在ViewRoot中的mDirty变量中,最后调用scheduleTraversals发起重绘请求,scheduleTraversals会发送一个异步消息,最终调用performTraversals()执行重绘,performTraversals()的具体过程以后再分析。 以上所有代码基于Android 4.0.4,并结合《Android内核剖析》分析总结而成,源码中涉及到的部分细节本人也未完全理解,还望高手指点~~
select case order_state when ‘0’ then ‘已取消’ when ‘10’ then ‘已下单’ when ‘20’ then if(payment_code = ‘offline’,’货到付款’,’已付款’) when ‘30’ then ‘已发货’ when ‘40’ then ‘已完成’ end from shopnc_order;
1.修改成中文
$g_default_language = ‘english’;//582
修改成
$g_default_language = ‘chinese_simplified’;
2.管理员添加可直接弄密码
$g_send_reset_password = ON;//257
修改成
$g_send_reset_password = OFF;
create database bugtracker default character set=utf8;
添加centos系统对rar文件的支持。 [root@localhost ~]# wget http://www.rarsoft.com/rar/rarlinux-4.0.1.tar.gz [root@localhost ~]# tar -zxvf rarlinux-4.0.1.tar.gz rar/ rar/readme.txt rar/default.sfx rar/whatsnew.txt rar/license.txt rar/order.htm rar/rar rar/unrar rar/rar_static rar/technote.txt rar/rarfiles.lst rar/makefile rar/rar.txt [root@localhost ~]# cd rar [root@localhost rar]# make mkdir -p /usr/local/bin mkdir -p /usr/local/lib cp rar unrar /usr/local/bin cp rarfiles.lst /etc cp default.sfx /usr/local/lib [root@localhost rar]# rar x moumou.rar -bash: /usr/local/bin/rar: /lib/ld-linux.so.2: bad ELF interpreter: No such file or directory 处理这个问题 [root@localhost rar]# cp rar_static /usr/local/bin/rar cp: overwrite `/usr/local/bin/rar’? y 已可以正常解压 root@localhost rar]# rar x moumou.rar RAR 4.01 Copyright (c) 1993-2011 Alexander Roshal 28 May 2011 Shareware version Type RAR -? for help Extracting from moumou.rar Creating moumou OK Creating moumou/css OK Extracting moumou/css/default.css OK
encodeURI(uriname) //uriname为中文字符