android fragment中引入自定义view_厉害了,用Android自定义View实现八大行星绕太阳3D旋转效果...

a8a78a66aca8beaaaa20ef40cc41b997.png

作者:史蒂芬诺夫斯基
链接:https://www.jianshu.com/p/2954f2ef8ea5

好久没写View了,最近恰巧遇到一个八大行星绕太阳旋转的假3D效果,写完之后感觉效果还不错。能玩十分钟的那种。本篇将一步步带您实现这样的一个效果,ps:我是用kotlin实现的,介于您可能还不太熟悉kotlin或者不像熟悉java那样,所以本篇使用java语言(写的过程中老是忘记写new和分号报错)。

先上最终效果图(录制的比较渣)

9024817bde684b906ad3c18e7cedc683.gif

本文目的

  • 巩固/练习 自定义View
  • 分析解决问题的思路

需要解决的问题

1.行星的整体布局,3D的视觉效果

2.行星转到太阳后面时,会被太阳挡住,转到太阳前面时,会挡住太阳

3.行星自动旋转,并且可以根据手势滑动,滑动完之后继续自动旋转

4.中间的太阳有照射的旋转动画

分析问题

1.行星的整体布局,3D的视觉效果

如果我们draw() 的之前通过CameraCanvas绕x轴旋转60°是不是就可以搞定?这种方式实则是不可行的。因为draw()之前Canvas的变化会作用于子View,从效果图可以看出,子View并没有rotateX的变换,只有缩放变换。所以我们通过子View layout时变化其位置,即计算子View的lefttoprightbottom四个值

行星绕太阳旋转其轨迹实际上就是圆形,如下图:

e5ad2341b4e485c3f68d678bd9adf04e.png

我们看手机,其实是沿着z轴方向。想象一下,如果让坐标系沿着x轴旋转60°,不就能达到我们想要的效果了嘛。

旋转60°,我们再沿着x轴方向看,如下图:

42fb8595a51aec5124ce1c51089b927e.png

图中蓝色是旋转前的轨迹,紫色是旋转之后的轨迹。假设P点是地球,P旋转前的y坐标是y0,则旋转之后地球的y坐标是:

y0 * 旋转角度的余切值,即:

y1 = y0* cos(60°)

好了。现在的结论是,只需要把图1的所有行星的y 坐标 * cos60°,就能达到效果了。

而图1中,计算各个行星旋转之前的x 、y坐标比较简单。

x0 = Radius * cos60°

y0 = Radius * sin60°

2.行星转到太阳后面时,会被太阳挡住,转到太阳前面时,会挡住太阳

e13ff15db598216b4227c1aeae7ee9ff.png

刚看到这个效果,觉得这个问题是个比较难的点,如果所有行星的父容器和太阳是平级关系,结果就是要么所有的行星都会挡住太阳,要么就是太阳都会挡住行星。不能达到行星转到太阳后面时,会被太阳挡住,转到太阳前面时,会挡住太阳 * 的这种效果

但是如果所有的行星和太阳是平级关系,即他们是同一个父容器下的子View,那么我们就可以达到这个效果,方法有三种:

  • 1、重写父容器dispatchDraw()方法,改变子View的绘制顺序(图3中先draw土星,再draw太阳,再draw地球);

  • 2、在子View draw之前依次调用bringToFront()方法(图3中先调用土星的bringToFront()方法,再调用太阳的bringToFront()方法,最后调用地球的bringToFront()方法);

  • 3、通过改变所有子View的z值(高度)以改变View的绘制顺序。

这三种方法理论是都可以实现,但是方法1 成本太高、风险也高,重新dispatchDraw()可能会发生未知问题,至于方法2,细心的朋友可能发现,每次调用bringToFront()方法,都会出发requestLayout(),降低了测量布局绘制效率,更重要的原因是在layout(问题1的解决需要重新layout方法)之后再调用requestLayout()方法,会导致循环layout-draw-layout-draw-layout-draw....

综上,我们选择方法3。简单,风险小。

3.行星自动旋转,并且可以根据手势滑动,滑动完之后继续自动旋转

自动滑动:在父容器中设置一个成员变量:角度偏移量sweepAngle,计算子View的位置时将偏移量也考虑进去。然后定时不断增加或者减小sweepAngle(增加或减小 将决定子View是顺时针or逆时针旋转)

手势:用的比较多,从后面的代码中体现。

4.中间的太阳有照射的旋转动画

效果图中的太阳由两张图片组成,一张是前景,一张是背景带亮光,让背景图绕着z轴无限旋转即可。

开始编码

核心就是行星的父容器

/**
* 行星和太阳的父容器
*
* @author guolong
* @since 2019/8/20
*/
public class StarGroupView extends FrameLayout {

// 从这个角度开始画View ,可以调整
private static final float START_ANGLE = 270f; // 270°
// 父容器的边界 单位dp
private static final int PADDING = 80;
// 绕x轴旋转的角度 70°对应的弧度
private static final double ROTATE_X = Math.PI * 7 / 18;
// 以上几个值都可以根据最终效果调整

/**
* 角度偏差值
*/
private float sweepAngle = 0f;

/**
* 行星轨迹的半径
*/
private float mRadius;

/**
* 父容器的边界 ,单位px
*/
private int mPadding;

public StarGroupView(@NonNull Context context) {
this(context, null);
}

public StarGroupView(@NonNull Context context, @Nullable AttributeSet attrs) {
this(context, attrs, 0);
}

public StarGroupView(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
// 边距转换为px
mPadding = (int) (context.getResources().getDisplayMetrics().density * PADDING);
}

@Override
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
// super.onLayout(changed, left, top, right, bottom);
mRadius = (getMeasuredWidth() / 2f - mPadding);
layoutChildren();
}

private void layoutChildren() {
int childCount = getChildCount();
if (childCount == 0) return;
// 行星之间的角度
float averageAngle = 360f / childCount;
for (int index = 0; index < childCount; index++) {
View child = getChildAt(index);
int childWidth = child.getMeasuredWidth();
int childHeight = child.getMeasuredHeight();

// 第index 个子View的角度
double angle = (START_ANGLE - averageAngle * index + sweepAngle) * Math.PI / 180;
double sin = Math.sin(angle);
double cos = Math.cos(angle);

double coordinateX = getMeasuredWidth() / 2f - mRadius * cos;
// * Math.cos(ROTATE_X) 代表将y坐标转换为旋转之后的y坐标
double coordinateY = mRadius / 2f - mRadius * sin * Math.cos(ROTATE_X);

child.layout((int) (coordinateX - childWidth / 2),
(int) (coordinateY - childHeight / 2),
(int) (coordinateX + childWidth / 2),
(int) (coordinateY + childHeight / 2));

// 假设view的最小缩放是原来的0.3倍,则缩放比例和角度的关系是
float scale = (float) ((1 - 0.3f) / 2 * (1 - Math.sin(angle)) + 0.3f);
child.setScaleX(scale);
child.setScaleY(scale);
}
}
}

然后再xml中配置View

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools"android:layout_width="match_parent"android:layout_height="match_parent"tools:context=".LandActivity">

<com.glong.demo.view.StarGroupViewandroid:layout_width="match_parent"android:layout_height="match_parent">

<TextViewandroid:id="@+id/tv1"android:layout_width="100dp"android:layout_height="100dp"android:background="@color/colorAccent"android:gravity="center"android:text="1" />

<TextViewandroid:id="@+id/tv2"android:layout_width="100dp"android:layout_height="100dp"android:background="@android:color/darker_gray"android:gravity="center"android:text="2" />

<TextViewandroid:id="@+id/tv3"android:layout_width="100dp"android:layout_height="100dp"android:background="@android:color/holo_green_dark"android:gravity="center"android:text="3" />

<TextViewandroid:id="@+id/tv4"android:layout_width="100dp"android:layout_height="100dp"android:background="@android:color/holo_blue_dark"android:gravity="center"android:text="4" />

<TextViewandroid:id="@+id/tv5"android:layout_width="100dp"android:layout_height="100dp"android:background="@android:color/holo_green_light"android:gravity="center"android:text="5" />

<TextViewandroid:id="@+id/tv6"android:layout_width="100dp"android:layout_height="100dp"android:background="@android:color/holo_orange_light"android:gravity="center"android:text="6" />

<TextViewandroid:id="@+id/tv7"android:layout_width="100dp"android:layout_height="100dp"android:background="#ff3311"android:gravity="center"android:text="7" />

<TextViewandroid:id="@+id/tv8"android:layout_width="100dp"android:layout_height="100dp"android:background="#11aa44"android:gravity="center"android:text="8" />

<TextViewandroid:id="@+id/tv9"android:layout_width="100dp"android:layout_height="100dp"android:background="#ff99cc"android:gravity="center"android:text="9" />

com.glong.demo.view.StarGroupView>

androidx.constraintlayout.widget.ConstraintLayout>

运行,效果如下:

b9565cfb696337593322eeb747122c3a.png

上述代码正如前面分析的,计算所有子View的lefttoprightbottom,注释写的也详细。说明两点:

1、其中,64行

double angle = (START_ANGLE - averageAngle * index + sweepAngle) * Math.PI / 180;

公式中-averageAngle * index代表逆时针添加,如果是+ averageAngle * index则是顺时针添加。

2、78到80行,计算子View的scale,这里说明下角度和scale的计算公司

float scale = (float) ((1 - 0.3f) / 2 * (1 - Math.sin(angle)) + 0.3f);

假如View的最小scale是0.3f,最大scale是1。按照效果View在270°时scale最大,在90°时scale最小,并且从270°到90°scale越来越小。正玄曲线如下:

007e25071177871365f33a69ca09a430.png

正玄曲线中,270°最小,90°时最大,我们把正玄值取反然后再加1,那么[90°,270°]对应的值就是[0,1]

即,设z = -sin(angle) + 1 当angle在90°到270°变化时 ,z将在0到1之间变化

z在0~1之间变化时,scale 要在0.3~1之间变化,如下图:

d73224455c3adb526361921f5ca98789.png

显然,

scale = (1 - 0.3) * z + 0.3 = (1-0.3)*(-sin(angle) + 1)+0.3

接下来,再把中间的太阳加进去

太阳也是StarGroupView的子View,但是和其他子View 不同的是,太阳在最中间,不参与类似行星的位置计算

简单期间我们使用tag=“center"来标识子View是中间的太阳。

修改xml文件:

    <com.glong.demo.view.StarGroupViewandroid:layout_width="match_parent"android:layout_height="match_parent">


<ImageViewandroid:layout_width="130dp"android:layout_height="130dp"android:src="@drawable/ic_launcher_background"android:tag="center" />


com.glong.demo.view.StarGroupView>

修改StarGroupView.java

public class StarGroupView extends FrameLayout {
// ... 省略部分代码

private void layoutChildren() {
int childCount = getChildCount();
if (childCount == 0) return;
// 行星之间的角度
View centerView = centerView();
float averageAngle;
if (centerView == null) {
averageAngle = 360f / childCount;
} else {
// centerView 不参与计算角度
averageAngle = 360f / (childCount - 1);
}

int number = 0;
for (int index = 0; index < childCount; index++) {
View child = getChildAt(index);
int childWidth = child.getMeasuredWidth();
int childHeight = child.getMeasuredHeight();

// 如果是centerView 直接居中布局
if ("center".equals(child.getTag())) {
child.layout(getMeasuredWidth() / 2 - childWidth / 2, getMeasuredHeight() / 2 - childHeight / 2,
getMeasuredWidth() / 2 + childWidth / 2, getMeasuredHeight() / 2 + childHeight / 2);
} else {
// 第index 个子View的角度
double angle = (START_ANGLE - averageAngle * number + sweepAngle) * Math.PI / 180;
double sin = Math.sin(angle);
double cos = Math.cos(angle);

double coordinateX = getMeasuredWidth() / 2f - mRadius * cos;
// * Math.cos(ROTATE_X) 代表将y坐标转换为旋转之后的y坐标
double coordinateY = mRadius / 2f - mRadius * sin * Math.cos(ROTATE_X);

child.layout((int) (coordinateX - childWidth / 2),
(int) (coordinateY - childHeight / 2),
(int) (coordinateX + childWidth / 2),
(int) (coordinateY + childHeight / 2));

// 假设view的最小缩放是原来的0.3倍,则缩放比例和角度的关系是
float scale = (float) ((1 - 0.3f) / 2 * (1 - Math.sin(angle)) + 0.3f);
child.setScaleX(scale);
child.setScaleY(scale);
number++;
}
}
}

/**
* 获取centerView
*
* @return 太阳
*/
private View centerView() {
View result = null;
for (int i = 0; i < getChildCount(); i++) {
View child = getChildAt(i);
if ("center".equals(child.getTag())) {
return child;
}
}
return null;
}
}

代码注释写的很全面,不做过多解释了,这个时候我们把PADDING改大一点,改成160,运行如下:

fd752c8638f4a1a69d400f8bdd323ed8.png

问题很明显,3应该在4的上面, 2 应该在3的上面,中间的View应该在5,6的上面。

这是因为系统默认按照View的添加顺序画View的,即我们xml文件里面的顺序。xml里面我们centerView在第一个,所以就先画centerView,导致centerView被其他View覆盖。按照上面的分析,动态改变View的z值以改变View的draw顺序。

修改StarGroupView.java代码

public class StarGroupView extends FrameLayout {

private void layoutChildren() {
// ...省略之前代码
changeZ();
}

/**
* 改变子View的z值以改变子View的绘制优先级,z越大优先级越低(最后绘制)
*/
private void changeZ() {
View centerView = centerView();
float centerViewScaleY = 1f;
if (centerView != null) {
centerViewScaleY = centerView.getScaleY();
centerView.setScaleY(0.5f);
}
List children = new ArrayList<>();for (int i = 0; i < getChildCount(); i++) {
children.add(getChildAt(i));
}// 按照scaleY排序
Collections.sort(children, new Comparator() {@Overridepublic int compare(View o1, View o2) {return (int) ((o1.getScaleY() - o2.getScaleY())*1000000);
}
});float z = 0.1f;for (int i = 0; i < children.size(); i++) {
children.get(i).setZ(z);
z += 0.1f;
}if (centerView != null) {
centerView.setScaleY(centerViewScaleY);
}
}
}

我们先给所有子View根据他的scaleY排序,由于centerView的scaleY 在layoutChildren()时并没有改变,我们把centerViewscaleY设置为0.5f,最后再还原回去。现在运行,效果如下:

a151663ca57f8cc0c226abb51175d3a8.png

到这里基本已经达到了我们想要的效果啦,接下来让其自动旋转和响应手势,肯定就难不倒我们啦。

加入自动旋转

StarGroupView中循环postDelayed(runnable,16)即可,这里为什么是16ms,大家都懂

修改StarGroupView.java:

public class StarGroupView extends FrameLayout {
// ...省略已有代码

//自动旋转角度,16ms(一帧)旋转的角度,值越大转的越快
private static final float AUTO_SWEEP_ANGLE = 0.1f;

private Runnable autoScrollRunnable = new Runnable() {
@Override
public void run() {
sweepAngle += AUTO_SWEEP_ANGLE;
// 取个模 防止sweepAngle爆表
sweepAngle %= 360;
Log.d("guolong", "auto , sweepAngle == " +sweepAngle);
layoutChildren();
postDelayed(this, 16);
}
};

public StarGroupView(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
// ...省略已有代码
postDelayed(autoScrollRunnable,100);
}
}

这样就开始自动旋转了,调节AUTO_SWEEP_ANGLE的值 改变旋转速度

加入手势

老写法,先上代码

StarGroupView.java中增加


public class StarGroupView extends FrameLayout {

//px转化为angle的比例 ps:一定要给设置一个转换,不然旋转的太欢了
private static final float SCALE_PX_ANGLE = 0.2f;


/**
* 手势处理
*/
private float downX = 0f;
/**
* 手指按下时的角度
*/
private float downAngle = sweepAngle;
/**
* 速度追踪器
*/
private VelocityTracker velocity = VelocityTracker.obtain();
/**
* 滑动结束后的动画
*/
private ValueAnimator velocityAnim = new ValueAnimator();

public StarGroupView(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
// ...
initAnim();
}

private void initAnim() {
velocityAnim.setDuration(1000);
velocityAnim.setInterpolator(new DecelerateInterpolator());
velocityAnim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
float value = (float) animation.getAnimatedValue();
// 乘以SCALE_PX_ANGLE是因为如果不乘 转得太欢了
sweepAngle += (value * SCALE_PX_ANGLE);
layoutChildren();
}
});
}

@Override
public boolean onTouchEvent(MotionEvent event) {
float x = event.getX();
velocity.addMovement(event);
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
downX = x;
downAngle = sweepAngle;

// 取消动画和自动旋转
velocityAnim.cancel();
removeCallbacks(autoScrollRunnable);
return true;
case MotionEvent.ACTION_MOVE:
float dx = downX - x ;
sweepAngle = (dx * SCALE_PX_ANGLE + downAngle);
layoutChildren();
break;
case MotionEvent.ACTION_UP:
velocity.computeCurrentVelocity(16);
// 速度为负值代表顺时针
scrollByVelocity(velocity.getXVelocity());
postDelayed(autoScrollRunnable, 16);
}
return super.onTouchEvent(event);
}

private void scrollByVelocity(float velocity) {
float end;
if (velocity < 0)
end = -AUTO_SWEEP_ANGLE;
else
end = 0f;
velocityAnim.setFloatValues(-velocity, end);
velocityAnim.start();
}
}

手势处理的代码比较简单,这里就不再赘述了,需要注意的是

  • 1.ACTION_DOWN需返回true,不然收不到后续的ACTION_MOVE事件;

  • 2.ACTION_DOWN时需要暂停动画和自动旋转

  • 3.这里根据手指离开屏幕时的速度做Animator动画,当然你也可以用scroller实现。

  • 4.第59行,我们给dx * SCALE_PX_ANGLE代表一个像素可以转换成SCALE_PX_ANGLE角度

最后,加上中间太阳旋转的动画

res/anim/sun_anim.xml

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"android:shareInterpolator="true"android:interpolator="@android:interpolator/linear">
<rotateandroid:duration="8000"android:fromDegrees="0"android:pivotX="50%"android:pivotY="50%"android:repeatCount="-1"android:toDegrees="360" />
set>

在Activity中

public class LandActivity extends AppCompatActivity {

@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// ....省略部分代码

View sunView = findViewById(R.id.sun_view);
sunView.startAnimation((AnimationUtils.loadAnimation(this, R.anim.sun_anim)));
}
}

最后的最后,我们可以给外部提供startpause方法用来暂停和开始动画

public class StarGroupView extends FrameLayout {

// 省略...
public void pause() {
velocityAnim.cancel();
removeCallbacks(autoScrollRunnable);
}

public void start() {
postDelayed(autoScrollRunnable, 16);
}
}

最终不到算上注释260代码搞定!

最终效果

bd7a3e8e7211b4b0b64ab5f9ed1457d1.gif

我把完整的Demo代码和星球效果代码放在github上了:https://github.com/glongdev/Demos

以上就是本文全部内容,喜欢❤️的话就转发一下、点个在看支持一下吧!

---END---

推荐阅读:
Android 9.0 Toast源码改变引发的问题
Android自定义ViewGroup实现标题栏的悬浮吸顶渐变效果
牛逼!Android Jetpack Compose UI组件库最新进展,写法完全类似Flutter
漫画设计模式:策略模式
30个极大提高开发效率的Visual Studio Code插件
93aef5ce9ae1944aa1179e26f1ec164f.png每一个“在看”,我都当成真的喜欢fbf3c20620d84213f980dfd0d8abc8f6.gif

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/528766.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

计算机消失了一个磁盘,win7系统重装后莫名奇妙消失一个分区磁盘的解决方法...

很多小伙伴都遇到过win7系统重装后莫名奇妙消失一个分区磁盘的困惑吧&#xff0c;一些朋友看过网上零散的win7系统重装后莫名奇妙消失一个分区磁盘的处理方法&#xff0c;并没有完完全全明白win7系统重装后莫名奇妙消失一个分区磁盘是如何解决的&#xff0c;今天小编准备了简单…

icloud无法验证服务器,iPhone提示“验证失败 连接到icloud时出错”怎么解决?

有不少使用苹果设备的朋友们在设备屏幕上面&#xff0c;可能会遇到了“验证失败 连接到icloud时出错”提示&#xff0c;不知道这是什么原因&#xff0c;如何解决。下面我就来谈谈出现这种现象的原因与解决办法。提示&#xff1a;“验证失败 连接到icloud时出错”&#xff0c;是…

esim办理出现差错_经营二氧化碳如何办理危化证?快来看!

点击关注我的气体网&#xff0c;置顶公众号行业资讯丨供求商机丨企业动态丨企业推荐更多信息和资源一网打尽━━━━━━安全复工二氧化碳相信大家都不陌生&#xff0c;我们平常一呼一吸间&#xff0c;呼出来的气体就是二氧化碳。还有我们平常喝的碳酸饮料&#xff0c;里边充入…

文件服务器有病毒,服务器共享文件会被病毒加密吗

前段时间纷纷扬扬的勒索病毒&#xff0c;让很多计算机用户害怕&#xff0c;就怕自己的共享文件被病毒加密而丢失&#xff0c;那么&#xff0c;服务器共享文件会被病毒加密吗&#xff1f;哪种网络条件下共享文件不易传播病毒呢&#xff1f;今天我们就跟随佰佰安全网一起来了解关…

swing快速入门(二十七)

注释很详细&#xff0c;直接上代码 上一篇 新增内容 1.为按钮指定图标 2. 列表框的并列 3.菜单项绑定快捷键 4.控件悬浮提示信息 5.菜单项设置小图标 6.五种布局风格右键选择切换 package swing21_30;import javax.swing.*; import java.awt.*; import java.awt.event.…

k8s pod里访问不到外部ip_K8S容器网络如何实现通信?

Kubernetes&#xff08;简称K8S&#xff09;正迅速成为云计算中部署和管理软件的新标准&#xff0c;那么K8S的容器网络是如何通信的呢&#xff1f;在了解容器网络通信原理之前&#xff0c;我们先学习下K8S中主要组件的定义&#xff0c;包括&#xff1a;节点(Node)、容器、POD、…

tps 数据库写并发衡量_硬核干货!抗住百万高并发的 6 个关键技术!

一、什么是高并发高并发&#xff08;High Concurrency&#xff09;是互联网分布式系统架构设计中必须考虑的因素之一&#xff0c;它通常是指&#xff0c;通过设计保证系统能够同时并行处理很多请求。高并发相关常用的一些指标有响应时间&#xff08;Response Time&#xff09;&…

ioc spring 上机案例_抛开Spring去理解IOC思想 - 原来IOC容器这么简单

很多小伙伴们看到标题可能就会想到抛开Spring就不会存在IOC思想了&#xff0c;其实不然在接下来的文章中就会讲述到。很多小伙伴在理解IOC的时候通常会和Spring放到一起去学习&#xff0c;首先呢Spring设计的非常之巧妙而且里面包含了很多除去IOC的其他功能。这样会导致我们在S…

余弦信号频谱表达式_信号傅里叶变换系列文章(1):傅里叶级数、傅里叶系数以及傅里叶变换...

傅里叶级数是周期信号的时域表达式&#xff0c;而傅里叶变换是非周期信号或周期信号的频谱&#xff08;频域函数&#xff09;&#xff0c;要想了解它们之间的关系&#xff0c;需要你耐心看完下面内容。学过"信号与系统"等课程的人往往会被许多问题所困惑&#xff0c;…

5s的app显示无法连接服务器,苹果iphone5s手机无法连接App Store问题解决方法汇总...

iphone5s无法连接App Store怎么办&#xff1f;大家在使用iphone5s过程中可能会遇到无法连接app store的问题&#xff0c;那怎么办呢&#xff1f;本文小编就主要给大家讲解一下如何解决iphone5s无法连接App Store的问题。iphone5s无法连接App Store解决方法如下&#xff1a;1)还…

变频器输出功率_100米的深井泵,如何接变频器,怎样控制

深井水泵的控制上&#xff0c;不外是为了保证负载水流的恒定性&#xff0c;一般可以通过恒压闭环方式来完成&#xff0c;如果有储水池的&#xff0c;液位闭环也可以。而深井水泵选用变频器&#xff0c;变频器装地面&#xff0c;你的线路有100米这么长&#xff0c;一般需要考虑加…

云服务器cvm系统,云服务器 cvm 自带系统

云服务器 cvm 自带系统 内容精选换一换如果Linux操作系统云服务器未安装密码重置插件&#xff0c;可以参见本节内容重新设置密码。本节操作重置的是root用户的密码&#xff0c;您可以重置完root密码后登录云服务器后再更换秘钥或重置非root用户的密码。Windows操作系统请参见重…

js距离单位换算_英语中常用的度量衡等单位,与我们用的不一样,这些差异点快收藏...

在日常生活中&#xff0c;我们几乎每天都会用到度量衡等度量单位&#xff0c;比如&#xff1a;去市场买菜&#xff0c;会用到几斤几两&#xff0c;量距离要知道多长&#xff0c;卖房子必须知道房屋的面积等等。度量单位在我们的生活中是非常重要的&#xff0c;可以说已经到了你…

开发缺点_开发移动端手机APP有哪些优缺点?

在当今移动互联网高速发达的现在&#xff0c;如果非要说什么工具最重要&#xff0c;那么一定要数手机APP了。企业可以借助它来进行移动端的营销&#xff0c;提高企业品牌推广力度和盈利&#xff1b;用户也可以借助它解决日常生活衣食住行等各方面的问题&#xff0c;因此备受人们…

用户修改了信息jwt服务器怎么识别,jwt验证登录信息

为什么要告别session&#xff1f;有这样一个场景&#xff0c;系统的数据量达到千万级&#xff0c;需要几台服务器部署&#xff0c;当一个用户在其中一台服务器登录后&#xff0c;用session保存其登录信息&#xff0c;其他服务器怎么知道该用户登录了&#xff1f;(单点登录)&…

获取朋友圈照片_朋友圈可以发 30 秒视频啦!用微视这个新功能就能办到

对于许多热爱分享生活中所见所闻的朋友来说&#xff0c;在发朋友圈时可能都会有这样的感觉&#xff1a;只能分享 15 秒以内的视频&#xff0c;完全不够用啊。如果你也有同样的困扰&#xff0c;今天&#xff0c;A 君就给你介绍一个实用新功能&#xff0c;让你能够在朋友圈中尽情…

苹果手机更改照片大小kb_苹果手机照片视频删除了怎样恢复?专业人士建议你这样做...

照片视频记录我们的点点滴滴&#xff0c;成长中的酸甜苦辣。当我们手机相册中的照片视频误删了我们该怎么做呢&#xff1f;如何才能挽回我们的损失&#xff1f;来看看专家让你怎么做。方法一&#xff1a;【最近删除】苹果自带有一个照片回收站【最近删除】恢复功能可以恢复里面…

复制过去格式不一样_不一样的立春节气:一个新的轮回开启,万物更新,疫情终将过去...

今天是立春&#xff0c;二十四节气中第一个节气&#xff0c;也是一个充满希望的节气。我国自古是农业大国&#xff0c;春种秋收&#xff0c;二十四节气是我国劳动人民独创的&#xff0c;也是先辈们了解自然的智慧结晶。它反映了季节的变化&#xff0c;影响着千家万户的衣食住行…

字符去多余空格_【Excel技巧】批量去空格删换行,用这两个函数简单又快速

今天分享两个函数TRIM函数和CLEAN函数。估计有些人还没见过这两个函数吧&#xff0c;不知道它们是用来干嘛的。跟你说啊&#xff0c;这两个函数都是用来清理、规范数据的。别不信&#xff0c;现在我们一起来看看他们的用法。一、TRIM函数比如&#xff0c;从网页上复制一份数据粘…

逗号后面统一加空格_用99个空格来提取Excel单元格数据,真的是脑洞大开!!!...

回复[目录]学习113篇Excel教程全套Excel视频教程&#xff0c;微信扫码观看需要从规格型号中提取容值、封装、耐压三组数据&#xff0c;如下&#xff1a; 数据源在A列&#xff0c;数据量很大&#xff0c;需要提取的容值、封装和耐压三项数据在单元格中的字节位置不固定。能找到的…