Skip to content

Commit 995ea98

Browse files
committed
format
1 parent 272138f commit 995ea98

18 files changed

+144
-130
lines changed

AdavancedPart/Android6.0权限系统.md

+6-6
Original file line numberDiff line numberDiff line change
@@ -9,11 +9,11 @@ Android6.0权限系统
99

1010
![image](https://raw.githubusercontent.com/CharonChui/Pictures/master/runtimepermission.jpg?raw=true)
1111

12-
**注意:**上面请求权限的对话框不会自动弹出。开发者需要手动的调用。如果开发者调用了一些需要权限的功能,但是用户又拒绝授权的话,应用就会`crash`
12+
注意:上面请求权限的对话框不会自动弹出。开发者需要手动的调用。如果开发者调用了一些需要权限的功能,但是用户又拒绝授权的话,应用就会`crash`
1313

1414
系统权限被分为两类,`normal``dangerous`:
1515

16-
- `Normal Permissions`不需要用户直接授权,如果你的应用在清单文件中声明了Normal Permissions`,系统会自动授权该权限。
16+
- `Normal Permissions`不需要用户直接授权,如果你的应用在清单文件中声明了`Normal Permissions`,系统会自动授权该权限。
1717
- `Dangerous Permissions`可以让应用获取用户的私人数据。如果你的应用在清单文件中申请了`Dangerous Permissions`,那就必须要用户来授权给应用。
1818

1919
`Normal Permissions`:
@@ -72,7 +72,7 @@ Android6.0权限系统
7272

7373
所以如果你的应用没有支持运行时权限的功能,那千万不要讲`targetSdkVersion`设置为23,否则就麻烦了。
7474

75-
> ***注意:***`Android 6.0(API Level 23)`开始,即使应用的`targetSdkVersion`是比较低的版本,但是用户仍然可以在任何时候撤销对应用的授权。所以不管应用的`targetSdkVerison`是什么版本,你都要测试你的应用在不能获取权限时能不能正常运行。
75+
> 注意:从`Android 6.0(API Level 23)`开始,即使应用的`targetSdkVersion`是比较低的版本,但是用户仍然可以在任何时候撤销对应用的授权。所以不管应用的`targetSdkVerison`是什么版本,你都要测试你的应用在不能获取权限时能不能正常运行。
7676
7777
下面介绍下如何使用`Android Support Library`来检查和请求权限。`Android`框架在`6.0`开始也提供了相同的方法。然而使用`support`包会比较简单,因为这样你就不需要在请求方法时判断当前的系统版本。(后面说的这几个类都是`android.support.v4`中的)
7878

@@ -102,7 +102,7 @@ int permissionCheck = ContextCompat.checkSelfPermission(thisActivity,
102102

103103
为了能找到用户可能需要说明的情况,`android`提供了一个工具类方法`ActivityCompat.shouldShowRequestPermissionRationale().`。如果应用之前申请了该权限但是用户拒绝授权后该方法会返回`true`。(在Android 6.0之前调用的时候会直接返回false)
104104

105-
> ***注意:***如果用户之前拒绝了权限申请并且选择了请求权限对话框中的`Don’t ask again`选项,该方法就会返回`false`。如果设备策略禁止了该应用使用该权限,该方法也会返回`false`。(我测试的时候发现请求权限的对话框中并没有`Don’t asdk again`这一项)
105+
> 注意:如果用户之前拒绝了权限申请并且选择了请求权限对话框中的`Don’t ask again`选项,该方法就会返回`false`。如果设备策略禁止了该应用使用该权限,该方法也会返回`false`。(我测试的时候发现请求权限的对话框中并没有`Don’t asdk again`这一项)
106106
> ![image](https://raw.githubusercontent.com/CharonChui/Pictures/master/request_permission_dialog.png?raw=true)
107107
108108
##### 申请需要的权限
@@ -145,7 +145,7 @@ if (ContextCompat.checkSelfPermission(thisActivity,
145145
}
146146
```
147147

148-
> ***注意:***当调用`requestPermissions()`方法时,系统会显示一个标准的对话框。应用不能指定或者改变该对话框。如果你想提供一些信息或者说明给用户,你需要在调用`requestPermissions()`之前处理。
148+
> 注意:当调用`requestPermissions()`方法时,系统会显示一个标准的对话框。应用不能指定或者改变该对话框。如果你想提供一些信息或者说明给用户,你需要在调用`requestPermissions()`之前处理。
149149
150150
##### 处理请求权限的的结果
151151

@@ -183,7 +183,7 @@ public void onRequestPermissionsResult(int requestCode,
183183

184184
系统提示的对话框会描述应用所需的`permission groud`。它不会列出特定的权限。例如,如果你申请了`READ_CONTACTS`权限,系统的对话框只会说你的应用需要获取设备的联系人信息。用户只需要授权每个`permission group`一次。如果你应用需要申请其他任何一个在该`permission group`中的权限时,系统会自动授权。在申请这些授权时,系统会像用户明确通过系统对话框统一授权时一样去调用`onRequestPermissionsResult()`方法并且传递`PERMISSION_GRANTED`参数。
185185

186-
> ***注意:***虽然用户已经授权了同一`permission group`中其他的任何权限,但是应用仍然需要明确申请每个需要的权限。例外,`permission group`中的权限在以后可能会发生变化。
186+
> 注意:虽然用户已经授权了同一`permission group`中其他的任何权限,但是应用仍然需要明确申请每个需要的权限。例外,`permission group`中的权限在以后可能会发生变化。
187187
188188
例如,假设在应用的`manifest`文件中同时声明了`READ_CONTACTS``WRITE_CONTACTS`权限。如果你申请`READ_CONTACTS`权限而且用户同意了该权限,如果你想继续申请`WRITE_CONTACTS`权限,系统不会与用户有任何交互就会直接进行授权。
189189

AdavancedPart/Android开发不申请权限来使用对应功能.md

+2-2
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ Intent intent = new Intent(Intent.ACTION_CALL);
1313
intent.setData(Uri.parse("tel:1234567890"))
1414
startActivity(intent);
1515
```
16-
**错!**,你通过这段代码需要该权限的原因是因为你可以在任何时间在不需要用户操作的情况下打电话。也就是说如果我的应用申请了这个权限,我可以在你不知情的情况下每天凌晨三点去拨打骚扰电话。
16+
错!,你通过这段代码需要该权限的原因是因为你可以在任何时间在不需要用户操作的情况下打电话。也就是说如果我的应用申请了这个权限,我可以在你不知情的情况下每天凌晨三点去拨打骚扰电话。
1717

1818
正确的方式是使用`ACTION_VIEW`或者`ACTION_DIAL`:
1919
```java
@@ -22,7 +22,7 @@ intent.setData(Uri.parse("tel:1234567890"))
2222
startActivity(intent);
2323
```
2424

25-
**这个问题的完美解决方案就是不需要申请权限了。**原因就是你不是直接拨号,而是用指定的号码调起拨号器,仍然需要用户点击”拨号”来开始打电话。老实的说,这样让人感觉更好。
25+
这个问题的完美解决方案就是不需要申请权限了。原因就是你不是直接拨号,而是用指定的号码调起拨号器,仍然需要用户点击”拨号”来开始打电话。老实的说,这样让人感觉更好。
2626

2727
简单的说就是如果我想要的操作不是让用户在应用内点击某个按钮就直接开始拨打电话,而是让用户点击在应用内点击某个按钮是我们去调起拨号程序,并且显示指定号码,让用户在拨号器中点击拨号后再开始拨打电话。这样的话我们就完全不用申请拨号权限了。
2828

AdavancedPart/Android开发中的MVP模式详解.md

+6-2
Original file line numberDiff line numberDiff line change
@@ -50,11 +50,11 @@ Android开发中的MVP模式详解
5050
开始做:
5151

5252
- 先把`Model`做好吧,创建`User`类。
53+
5354
```java
5455
public class User {
5556
private String email;
5657
private String password;
57-
5858
public User(String email, String password) {
5959
this.email = email;
6060
this.password = password;
@@ -66,7 +66,9 @@ Android开发中的MVP模式详解
6666
}
6767
}
6868
```
69+
6970
- 创建`ILoginView`接口,定义登录所需要的`ui`逻辑。
71+
7072
```java
7173
public interface ILoginView {
7274
void showLoading();
@@ -78,6 +80,7 @@ Android开发中的MVP模式详解
7880

7981
- 创建`LoginPresenter`类,使用`ILoginView`接口,那该类主要有什么功能呢? 它主要是处理业务逻辑的,
8082
对于登录的话,当然是用户在`UI`页面输入邮箱和密码,然后`Presenter`去开线程、请求接口。然后得到登录结果再去让`UI`显示对应的视图。那自然就是有一个`void login(String email, String passowrd)`的方法了
83+
8184
```java
8285
public class LoginPresenter {
8386
private ILoginView mLoginView;
@@ -115,6 +118,7 @@ Android开发中的MVP模式详解
115118
}
116119
```
117120
- 创建`LoginActivity`,实现`ILoginView`的接口,然后内部调用`LoginPresenter`来处理业务逻辑。
121+
118122
```java
119123
public class LoginActivity extends AppCompatActivity implements ILoginView {
120124
private LoginPresenter mLoginPresenter;
@@ -168,7 +172,7 @@ Android开发中的MVP模式详解
168172
---
169173

170174

171-
上面只是抛砖引玉。`MVP`的有点十分明显,就是代码解耦、可以让逻辑清晰,但是同样它也会有缺点,它的缺点就是项目的复杂程度会增加,项目中会多出很多类。
175+
上面只是抛砖引玉。`MVP`的优点十分明显,就是代码解耦、可以让逻辑清晰,但是同样它也会有缺点,它的缺点就是项目的复杂程度会增加,项目中会多出很多类。
172176
之前很多人都在讨论该如何去正确的设计使用`MVP`来避免它的缺点,众说纷纭,很多人讨论的你死我活。直到`Google`发布了`MVP架构蓝图`,大家才意识到这才是规范。
173177

174178
项目地址:[android-architecture](https://github.com/googlesamples/android-architecture)

AdavancedPart/ApplicationId vs PackageName.md

+3-3
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ android {
5353
```
5454

5555
像之前一样,你需要在`Manifest`文件中指定你在代码中使用的'package name',像上面`AndroidManifest.xml`的例子。
56-
***下面进入关键部分了***当你按照上面的方式做完后,这两个包就是相互独立的了。你现在可以很简单的重构你的代码-通过修改`Manifest`中的包名来修改在你的`activitise``services`中使用的包和在重构你在代码中的引用声明。这不会影响你应用的最终`id`,也就是在`Gradle`文件中的`applicationId`
56+
下面进入关键部分了:当你按照上面的方式做完后,这两个包就是相互独立的了。你现在可以很简单的重构你的代码-通过修改`Manifest`中的包名来修改在你的`activitise``services`中使用的包和在重构你在代码中的引用声明。这不会影响你应用的最终`id`,也就是在`Gradle`文件中的`applicationId`
5757

5858
你可以通过以下`Gradle DSL`方法为应用的`flavors``build types`指定不同的`applicationId`:
5959

@@ -78,9 +78,9 @@ buildTypes {
7878
```
7979
(在`Android Studio`中你也可以通过图形化的`Project Structure`的对话框来更改上面所有的配置)
8080

81-
***注意:***为了兼容性,如果你在`build.gradle`文件中没有定义`applicationId` ,那`applicationId`就是与`AndroidManifest.xml`中配置的包名相同的默认值。在这种情况下,这两者显然脱不了干系,如果你试图重构代码中的包就将会导致同时会改变你应用程序的`id`!在`Android Studio`中新创建的项目都是同时指定他们俩。
81+
注意:为了兼容性,如果你在`build.gradle`文件中没有定义`applicationId` ,那`applicationId`就是与`AndroidManifest.xml`中配置的包名相同的默认值。在这种情况下,这两者显然脱不了干系,如果你试图重构代码中的包就将会导致同时会改变你应用程序的`id`!在`Android Studio`中新创建的项目都是同时指定他们俩。
8282

83-
***注意2:***`package name`必须在默认的`AndroidManifest.xml`文件中指定。如果有多个`manifest`文件(例如对每个`flavor`制定一个`manifest`或者每个`build type`制定一个`manifest`)时,`package name`是可选的,但是如果你指定的话,它必须与主`manifest`中指定的`pakcage`相同。
83+
注意2:`package name`必须在默认的`AndroidManifest.xml`文件中指定。如果有多个`manifest`文件(例如对每个`flavor`制定一个`manifest`或者每个`build type`制定一个`manifest`)时,`package name`是可选的,但是如果你指定的话,它必须与主`manifest`中指定的`pakcage`相同。
8484

8585
8686
---

AdavancedPart/Handler导致内存泄露分析.md

+3-3
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ Handler mHandler = new Handler() {
1717
- `Android`程序第一次创建的时候,默认会创建一个`Looper`对象,`Looper`去处理`Message Queue`中的每个`Message`,主线程的`Looper`存在整个应用程序的生命周期.
1818
- `Hanlder`在主线程创建时会关联到`Looper``Message Queue`,`Message`添加到消息队列中的时候`Message(排队的Message)`会持有当前`Handler`引用,
1919
`Looper`处理到当前消息的时候,会调用`Handler#handleMessage(Message)`.就是说在`Looper`处理这个`Message`之前,
20-
会有一条链`MessageQueue -> Message -> Handler -> Activity`,由于它的引用导致你的`Activity`被持有引用而无法被回收`
20+
会有一条链`MessageQueue -> Message -> Handler -> Activity`,由于它的引用导致你的`Activity`被持有引用而无法被回收
2121
- **在java中,no-static的内部类会隐式的持有当前类的一个引用。static的内部类则没有。**
2222

2323
## 具体分析
@@ -97,8 +97,8 @@ public class MyActivity extends Activity {
9797
}
9898
```
9999

100-
[1]: https://github.com/CharonChui/AndroidNote/blob/master/BasicKnowledge/%E5%86%85%E5%AD%98%E6%B3%84%E6%BC%8F.md "内存泄露""
101-
100+
[更多内容请看内存泄露](https://github.com/CharonChui/AndroidNote/blob/master/BasicKnowledge/%E5%86%85%E5%AD%98%E6%B3%84%E6%BC%8F.md)
101+
102102
---
103103

104104
- 邮箱 :charon.chui@gmail.com

AdavancedPart/RecyclerView专题.md

+6-8
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ RecyclerView专题
88
官方文档中是这样介绍的:
99
`A flexible view for providing a limited window into a large data set.`
1010

11-
RecyclerView比listview更先进更灵活,对于很多的视图它就是一个容器,可以有效的重用和滚动。当数据动态变化的时候请使用它。
11+
`RecyclerView``listview`更先进更灵活,对于很多的视图它就是一个容器,可以有效的重用和滚动。当数据动态变化的时候请使用它。
1212

1313

1414

@@ -29,7 +29,7 @@ RecyclerView比listview更先进更灵活,对于很多的视图它就是一个
2929
- `layout position`: 在最近一次`layout`计算是`item`的位置。这是`LayoutManager`角度中的位置。
3030
- `adapter position`: `item``adapter`中的位置。这是从`Adapter`的角度中的位置。
3131

32-
这两种`position`除了在分发`adapter.notify*`事件与之后计算布局更新的这段时间之内外都是相同的。
32+
这两种`position`除了在分发`adapter.notify`事件与之后计算布局更新的这段时间之内外都是相同的。
3333
可以通过`getLayoutPosition(),findViewHolderForLayoutPosition(int)`方法来获取最近一次布局计算的`LayoutPosition`。这些`positions`包括从最近一次布局计算的所有改变。你可以根据这些位置来方便的得到用户当前从屏幕上所看到的。例如,如果在屏幕上有一个列表,用户请求的是第五个条目,你可以通过该方法来匹配当前用户正在看的内容。
3434

3535
另一种`AdapterPosition`相关的方法是`getAdapterPosition(),findViewHolderForAdapterPosition(int)`,当及时一些数据可能没有来得及被展现到布局上时便需要获取最新的`adapter`位置可以使用这些相关的方法。例如,如果你想获取一个条目的`ViewHOlder``click`事件时,你应该使用`getAdapterPosition()`。需要知道这些方法在`notifyDataSetChange()`方法被调用和新布局还没有被计算之前是不能使用的。鉴于这个原因,你应该小心的去处理这些方法有可能返回`NO_POSITION`或者`null`的情况。
@@ -38,8 +38,8 @@ RecyclerView比listview更先进更灵活,对于很多的视图它就是一个
3838

3939
### 结构
4040

41-
- `RecyclerView.Adapter`: 创建View并将数据集合绑定到View上
42-
- `ViewHolder`: 持有所有的用于绑定数据或者需要操作的View
41+
- `RecyclerView.Adapter`: 创建`View`并将数据集合绑定到`View`
42+
- `ViewHolder`: 持有所有的用于绑定数据或者需要操作的`View`
4343
- `LayoutManager`: 布局管理器,负责摆放视图等相关操作
4444
- `ItemDecoration`: 负责绘制`Item`附近的分割线,通过`RecyclerView.addItemDecoration()`使用
4545
- `ItemAnimator`: 为`Item`的操作添加动画效果,如,增删条目等,通过`RecyclerView.setItemAnimator(new DefaultItemAnimator());`使用
@@ -333,17 +333,15 @@ mListView.setOnItemLongClickListener();
333333
...
334334
}
335335
```
336+
336337
说的和明白了,而且还让你看`SimpleOnItemTouchListener`,猜也能猜出来是一个默认的实现类。
337338
好了直接上代码:
338339
```java
339340
public class MainActivity extends AppCompatActivity {
340341
private RecyclerView mRecyclerView;
341342
private LinearLayoutManager mLayoutManager;
342343
private MyAdapter mAdapter;
343-
344344
private String[] mDatas = {"Android", "ios", "jack", "tony", "window", "mac", "1234", "hehe", "495948", "89757", "66666"};
345-
346-
347345
@Override
348346
protected void onCreate(Bundle savedInstanceState) {
349347
super.onCreate(savedInstanceState);
@@ -531,7 +529,7 @@ manager.setSpanSizeLookup(new GridLayoutManager.SpanSizeLookup() {
531529

532530
### 下拉刷新、自动加载
533531

534-
#####实现下拉刷新
532+
##### 实现下拉刷新
535533
实现下拉刷新也很简单了,可以使用`SwipeRefrshLayout`,`SwipeRefrshLayout`是`Google`官方提供的组件,可以实现下拉刷新的功能。已包含到`support.v4`包中。
536534

537535
主要方法有:

AdavancedPart/屏幕适配之百分比方案详解.md

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
屏幕适配之百分比方案详解
22
===
33

4-
`Android`设备碎片化十分严重,在开发过程中的适配工作也非常很繁琐,有关屏幕适配的介绍请看之前的文章[屏幕适配](https://github.com/CharonChui/AndroidNote/blob/master/Android%E5%9F%BA%E7%A1%80/%E5%B1%8F%E5%B9%95%E9%80%82%E9%85%8D.md)
4+
`Android`设备碎片化十分严重,在开发过程中的适配工作也非常很繁琐,有关屏幕适配的介绍请看之前的文章[屏幕适配](https://github.com/CharonChui/AndroidNote/blob/master/BasicKnowledge/%E5%B1%8F%E5%B9%95%E9%80%82%E9%85%8D.md)
55

66
最近看到`DrawerLayout``support v4`中提供的类,想到对`google`提供的这些支持库,自己一点都不熟悉,想着看看`Google`提供的支持库都有什么内容。结果看着看着在最后忽然看到了`Percent Support Library`。寻思怎么还百分比呢?仔细一看介绍,我擦,真是太有用了。
7-
> ###Percent Support Library
7+
> Percent Support Library
88
> The Percent package provides APIs to support adding and managing percentage based dimensions in your app.
99
1010
> The Percent Support library adds support for the PercentLayoutHelper.PercentLayoutParams interface and various classes, such as PercentFrameLayout and PercentRelativeLayout.
@@ -14,7 +14,7 @@
1414
> The Gradle build script dependency identifier for this library is as follows:
1515
> `com.android.support:percent:23.3.0`
1616
17-
看到了吗? 说提供了`PercentFrameLayout``PercentRelativeLayout`来支持百分比了。这样不就完美的解决了适配的问题嘛。啥也不说了,立马配置`cradle`来瞧瞧。
17+
看到了吗? 说提供了`PercentFrameLayout``PercentRelativeLayout`来支持百分比了。这样不就完美的解决了适配的问题嘛。啥也不说了,立马配置`gradle`来瞧瞧。
1818

1919
> Subclass of FrameLayout that supports percentage based dimensions and margins. You can specify dimension or a margin of child by using attributes with "Percent" suffix.
2020

0 commit comments

Comments
 (0)