android Shape只显示指定边框用法

<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android"> <!-- focused --> <item android:drawable="@drawable/orderboard_detail_tab_middle_selected" android:state_checked="true" /> <item android:drawable="@drawable/orderboard_detail_tab_middle_selected" android:state_selected="true" /> <!-- default --> <item > <layer-list xmlns:android="http://schemas.android.com/apk/res/android"> <item android:left="-1dp" android:right="-1dp" > <shape android:shape="rectangle"> <solid android:color="@color/text_color_white" /> <stroke android:width="1dp" android:color="@color/text_color_blue" /> <padding android:left="0dp" android:right="0dp" /> <corners android:radius="0dp"/> </shape> </item> </layer-list> </item> </selector> 上面执行的结果:只画上下线 [![QQ20160830-0@2x](http://www.etongwl.com/images/2016/08/QQ20160830-0@2x-300x289.png)](http://www.etongwl.com/images/2016/08/QQ20160830-0@2x.png)

2016年8月30日 · 1 分钟 · 天边的星星

Android Toast花式使用

![](http://upload-images.jianshu.io/upload_images/828721-e0fc168c7e6ce054.jpg?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240) 之前写过一篇没时间解释了,快使用Snackbar!——Android Snackbar花式使用指南。Toast的自定义使用原理与其类似。 1.Toast源码分析 老规矩,我们先去看Toast的源码。 Toast有两种显示布局方式,一种最常见调用Toast.makeText(),看源码是这样写的 `<span class="hljs-function"><span class="hljs-keyword">public</span> <span class="hljs-keyword">static</span> Toast <span class="hljs-title">makeText</span>(<span class="hljs-params">Context context, CharSequence text, @Duration <span class="hljs-keyword">int</span> duration</span>) </span>{ Toast result = <span class="hljs-keyword">new</span> Toast(context); LayoutInflater inflate = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); View v = inflate.inflate(com.android.<span class="hljs-keyword">internal</span>.R.layout.transient_notification, <span class="hljs-keyword">null</span>); TextView tv = (TextView)v.findViewById(com.android.<span class="hljs-keyword">internal</span>.R.id.message); tv.setText(text); result.mNextView = v; result.mDuration = duration; <span class="hljs-keyword">return</span> result; }` transient_notification这个布局文件代码是这样的 `<span class="hljs-tag"><<span class="hljs-title">LinearLayout</span> <span class="hljs-attribute">xmlns:android</span>=<span class="hljs-value">"http://schemas.android.com/apk/res/android"</span> <span class="hljs-attribute">android:layout_width</span>=<span class="hljs-value">"match_parent"</span> <span class="hljs-attribute">android:layout_height</span>=<span class="hljs-value">"match_parent"</span> <span class="hljs-attribute">android:orientation</span>=<span class="hljs-value">"vertical"</span> <span class="hljs-attribute">android:background</span>=<span class="hljs-value">"?android:attr/toastFrameBackground"</span>></span> <span class="hljs-tag"><<span class="hljs-title">TextView</span> <span class="hljs-attribute">android:id</span>=<span class="hljs-value">"@android:id/message"</span> <span class="hljs-attribute">android:layout_width</span>=<span class="hljs-value">"wrap_content"</span> <span class="hljs-attribute">android:layout_height</span>=<span class="hljs-value">"wrap_content"</span> <span class="hljs-attribute">android:layout_weight</span>=<span class="hljs-value">"1"</span> <span class="hljs-attribute">android:layout_gravity</span>=<span class="hljs-value">"center_horizontal"</span> <span class="hljs-attribute">android:textAppearance</span>=<span class="hljs-value">"@style/TextAppearance.Toast"</span> <span class="hljs-attribute">android:textColor</span>=<span class="hljs-value">"@color/bright_foreground_dark"</span> <span class="hljs-attribute">android:shadowColor</span>=<span class="hljs-value">"#BB000000"</span> <span class="hljs-attribute">android:shadowRadius</span>=<span class="hljs-value">"2.75"</span> /></span> <span class="hljs-tag"></<span class="hljs-title">LinearLayout</span>></span>` 那么我们想要修改Toast的文字消息样式,其实就是修改Toast根布局和message这个TextView。 ...

2016年8月25日 · 4 分钟 · 天边的星星

android webView网页表单自动登录(单点登录)

今天帮助网友解决了一个在应用中登录后进应用的网页自动登录。 在这里分享给大家,希望能帮助更多的人。直接上代码: /** * 网页自动登录 * http://haohailai.taobao.com/ * @author xiehaibo * */ public class MainActivity extends Activity { private WebView webView1; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); webView1 = (WebView) findViewById(R.id.webView1); // 设置支持JavaScript脚本 WebSettings webSettings = webView1.getSettings(); webSettings.setJavaScriptEnabled(true); // 设置可以访问文件 webSettings.setAllowFileAccess(true); // 设置支持缩放 webSettings.setBuiltInZoomControls(true); // 设置WebViewClient webView1.setWebViewClient(new WebViewClient() { public boolean shouldOverrideUrlLoading(WebView view, String url) { view.loadUrl(url); return true; } @Override public void onPageFinished(WebView view, String url) { Log.d("admin", "网页加载完了"); String uname = "帐号"; String password = "密码"; // 加载完了再调用js登录代码 view.loadUrl("javascript: {" + "document.getElementById('username').value = '" + uname + "';" + "document.getElementById('password').value = '" + password + "';" + "var frms = document.getElementsByName('tableForm');" + "frms[0].submit(); };"); // 登录成功后加载框取消 super.onPageFinished(view, url); } @Override public void onPageStarted(WebView view, String url, Bitmap favicon) { Log.d("admin", "网页开始加载"); // 在这里可以创建一个加载框。。。 super.onPageStarted(view, url, favicon); } }); webView1.loadUrl("网页地址,包含登录表单"); } } 注意的是: ...

2016年8月22日 · 1 分钟 · 天边的星星

android获取web服务器端session并验证登陆

传统网页实现用户登陆一般采用session或cookie记录用户基本信息又或者两者结合起来使用。android也可以采用session实现用户登陆验证并记录用户登陆状态时的基本信息,session是在服务器端的;而类似cookie的记录方式,则可以在客户端采用xml文件记录用户基本信息,重要数据则可以加密存放客户端。android实现的session登陆功能与网页请求不同的是,网页形式的一次成功的登陆请求后,再点击其他页面时,session一直是存在的,在一定时间内是有效的;而采用android客户端请求的一次成功登陆后,再次发送新的请求,则会产生新的session,而不是原来的。这就需要记录session的id号,并在整个请求过程中都记录并传递这个id号,才能保证session的一致性。 以获取php session为例,主要思路实现分为客户端与服务器端3个步骤。 附件:源码下载 1.)客户端(ANDROID) 建立一个名为GetWebSession的android项目,编写GetWebSession.java,LoginSuccessActivity.java,GetUserInfoActivity.java三个activity类。 GetWebSession.java主要是实现布局界面以及发送用户名和密码到php服务器端验证,如果验证成功则跳转到LoginSuccessActivity.java类。GetWebSession.java主要涉及到与服务器端连接请求,对从服务器端返回的json数据(如用户id,session等)进行解析,并存入HashMap,传递到LoginSuccessActivity.java 代码如下: [view plain](http://www.yoyong.com/archives/178#)[copy to clipboard](http://www.yoyong.com/archives/178#)[print](http://www.yoyong.com/archives/178#)[?](http://www.yoyong.com/archives/178#) - <span class="keyword">package</span> com.login.main; - <span class="keyword">import</span> java.io.IOException; - <span class="keyword">import</span> java.io.UnsupportedEncodingException; - <span class="keyword">import</span> java.util.ArrayList; - <span class="keyword">import</span> java.util.HashMap; - <span class="keyword">import</span> java.util.List; - <span class="keyword">import</span> org.apache.http.HttpEntity; - <span class="keyword">import</span> org.apache.http.HttpResponse; - <span class="keyword">import</span> org.apache.http.client.ClientProtocolException; - <span class="keyword">import</span> org.apache.http.client.entity.UrlEncodedFormEntity; - <span class="keyword">import</span> org.apache.http.client.methods.HttpPost; - <span class="keyword">import</span> org.apache.http.impl.client.DefaultHttpClient; - <span class="keyword">import</span> org.apache.http.message.BasicNameValuePair; - <span class="keyword">import</span> org.apache.http.protocol.HTTP; - <span class="keyword">import</span> org.apache.http.util.EntityUtils; - <span class="keyword">import</span> org.json.JSONException; - <span class="keyword">import</span> org.json.JSONObject; - <span class="keyword">import</span> android.app.Activity; - <span class="keyword">import</span> android.content.Context; - <span class="keyword">import</span> android.content.Intent; - <span class="keyword">import</span> android.os.Bundle; - <span class="keyword">import</span> android.view.View; - <span class="keyword">import</span> android.view.View.OnClickListener; - <span class="keyword">import</span> android.widget.Button; - <span class="keyword">import</span> android.widget.EditText; - <span class="keyword">import</span> android.widget.Toast; - <span class="keyword">public</span> <span class="keyword">class</span> GetWebSession <span class="keyword">extends</span> Activity { - <span class="comment">/** Called when the activity is first created. */</span> - <span class="keyword">private</span> EditText user; - <span class="keyword">private</span> EditText password; - <span class="keyword">private</span> Button loginBtn; - <span class="keyword">private</span> Button logoutBtn; - <span class="comment">//主要是记录用户会话过程中的一些用户的基本信息</span> - <span class="keyword">private</span> HashMap<String, String> session =<span class="keyword">new</span> HashMap<String, String>(); - <span class="annotation">@Override</span> - <span class="keyword">public</span> <span class="keyword">void</span> onCreate(Bundle savedInstanceState) { - <span class="keyword">super</span>.onCreate(savedInstanceState); - setContentView(R.layout.main); - user=(EditText)findViewById(R.id.user); - password=(EditText)findViewById(R.id.password); - loginBtn=(Button)findViewById(R.id.loginBtn); - loginBtn.setOnClickListener(loginClick); - logoutBtn=(Button)findViewById(R.id.logoutBtn); - logoutBtn.setOnClickListener(logoutClick); - } - OnClickListener loginClick=<span class="keyword">new</span> OnClickListener() { - <span class="annotation">@Override</span> - <span class="keyword">public</span> <span class="keyword">void</span> onClick(View v) { - <span class="comment">// TODO Auto-generated method stub</span> - <span class="keyword">if</span>(checkUser()){ - Toast.makeText(v.getContext(), <span class="string">&#8220;用户登录成功!&#8221;</span>, Toast.LENGTH_SHORT).show(); - Context context = v.getContext(); - Intent intent = <span class="keyword">new</span> Intent(context, - LoginSuccessActivity.<span class="keyword">class</span>); - <span class="comment">//传递session参数,在用户登录成功后为session初始化赋值,即传递HashMap的值</span> - Bundle map = <span class="keyword">new</span> Bundle(); - map.putSerializable(<span class="string">&#8220;sessionid&#8221;</span>, session); - intent.putExtra(<span class="string">&#8220;session&#8221;</span>, map); - context.startActivity(intent); <span class="comment">// 跳转到成功页面</span> - } - <span class="keyword">else</span> - Toast.makeText(v.getContext(), <span class="string">&#8220;用户验证失败!&#8221;</span>, Toast.LENGTH_SHORT).show(); - } - }; - OnClickListener logoutClick=<span class="keyword">new</span> OnClickListener() { - <span class="annotation">@Override</span> - <span class="keyword">public</span> <span class="keyword">void</span> onClick(View v) { - <span class="comment">// TODO Auto-generated method stub</span> - System.exit(<span class="number"></span>); - } - }; - <span class="keyword">private</span> <span class="keyword">boolean</span> checkUser(){ - String username=user.getText().toString(); - String pass=password.getText().toString(); - DefaultHttpClient mHttpClient = <span class="keyword">new</span> DefaultHttpClient(); - HttpPost mPost = <span class="keyword">new</span> HttpPost(<span class="string">&#8220;http://10.0.2.2/web/php/login.php&#8221;</span>); - <span class="comment">//传递用户名和密码相当于</span> - <span class="comment">//http://10.0.2.2/web/php/login.php?username=&#8221;&password=&#8221;</span> - List<BasicNameValuePair> pairs = <span class="keyword">new</span> ArrayList<BasicNameValuePair>(); - pairs.add(<span class="keyword">new</span> BasicNameValuePair(<span class="string">&#8220;username&#8221;</span>, username)); - pairs.add(<span class="keyword">new</span> BasicNameValuePair(<span class="string">&#8220;password&#8221;</span>, pass)); - <span class="keyword">try</span> { - mPost.setEntity(<span class="keyword">new</span> UrlEncodedFormEntity(pairs, HTTP.UTF_8)); - } <span class="keyword">catch</span> (UnsupportedEncodingException e) { - <span class="comment">// TODO Auto-generated catch block</span> - e.printStackTrace(); - } - <span class="keyword">try</span> { - HttpResponse response = mHttpClient.execute(mPost); - <span class="keyword">int</span> res = response.getStatusLine().getStatusCode(); - <span class="keyword">if</span> (res == <span class="number">200</span>) { - HttpEntity entity = response.getEntity(); - <span class="keyword">if</span> (entity != <span class="keyword">null</span>) { - String info = EntityUtils.toString(entity); - System.out.println(<span class="string">&#8220;info&#8212;&#8212;&#8212;&#8211;&#8220;</span>+info); - <span class="comment">//以下主要是对服务器端返回的数据进行解析</span> - JSONObject jsonObject=<span class="keyword">null</span>; - <span class="comment">//flag为登录成功与否的标记,从服务器端返回的数据</span> - String flag=<span class="string">&#8220;&#8221;</span>; - String name=<span class="string">&#8220;&#8221;</span>; - String userid=<span class="string">&#8220;&#8221;</span>; - String sessionid=<span class="string">&#8220;&#8221;</span>; - <span class="keyword">try</span> { - jsonObject = <span class="keyword">new</span> JSONObject(info); - flag = jsonObject.getString(<span class="string">&#8220;flag&#8221;</span>); - name = jsonObject.getString(<span class="string">&#8220;name&#8221;</span>); - userid = jsonObject.getString(<span class="string">&#8220;userid&#8221;</span>); - sessionid = jsonObject.getString(<span class="string">&#8220;sessionid&#8221;</span>); - } <span class="keyword">catch</span> (JSONException e) { - <span class="comment">// TODO Auto-generated catch block</span> - e.printStackTrace(); - } - <span class="comment">//根据服务器端返回的标记,判断服务端端验证是否成功</span> - <span class="keyword">if</span>(flag.equals(<span class="string">&#8220;success&#8221;</span>)){ - <span class="comment">//为session传递相应的值,用于在session过程中记录相关用户信息</span> - session.put(<span class="string">&#8220;s_userid&#8221;</span>, userid); - session.put(<span class="string">&#8220;s_username&#8221;</span>, name); - session.put(<span class="string">&#8220;s_sessionid&#8221;</span>, sessionid); - <span class="keyword">return</span> <span class="keyword">true</span>; - } - <span class="keyword">else</span>{ - <span class="keyword">return</span> <span class="keyword">false</span>; - } - } - <span class="keyword">else</span>{ - <span class="keyword">return</span> <span class="keyword">false</span>; - } - } - } <span class="keyword">catch</span> (ClientProtocolException e) { - <span class="comment">// TODO Auto-generated catch block</span> - e.printStackTrace(); - } <span class="keyword">catch</span> (IOException e) { - <span class="comment">// TODO Auto-generated catch block</span> - e.printStackTrace(); - } - <span class="keyword">return</span> <span class="keyword">false</span>; - } - } LoginSuccessActivity.java主要获取php的session唯一的标识id以及用户的一些基本信息,session id则作为本次用户登录状态在服务器的唯一标识,即确定用户的唯一状态进行相关操作。LoginSuccessActivity.java类的方法与GetWebSession.java类似。其主要功能是获取session id后再次发送session id到服务器进行验证,根据封装的session数据验证用户操作权限等。 代码如下: ...

2016年8月22日 · 14 分钟 · 天边的星星

SQLite清空表并将自增列归零

SQL标准中有**TRUNCATE TABLE**语句,用来清空表的所有内容。但SQLite不支持这个语句。在SQLite中直接使用“**DELETE FROM TableName**”就可以了。对于大多数DBMS来说,用DELETE不如用TRUNCATE 速度快,因为TRUNCATE 不用访问整个表,不用记录数据的变动。 SQLite虽然不支持TRUNCATE,但它对DELETE做了优化:“When the WHERE is omitted(略去) from a DELETE statement and the table being deleted has no triggers(触发器), SQLite uses an optimization(优化) to erase the entire table content without having to visit each row of the table individually. **This “truncate” optimization makes the delete run much faster**.” 通常在清空表的时候,还需要把自增列归零。在SQLite中定义自增列的方法如下: <div id="crayon-51c50d9e7aa71" class="crayon-syntax crayon-theme-classic crayon-font-monaco crayon-os-pc print-yes"> <div class="crayon-plain-wrap"> </div> <div class="crayon-main"> <table class="crayon-table "> <tr class="crayon-row"> <td class="crayon-nums "> <div class="crayon-nums-content"> <div class="crayon-num"> 1 </div> </div> </td> <td class="crayon-code"> <div class="crayon-pre"> <div id="crayon-51c50d9e7aa71-1" class="crayon-line"> <span class="k">CREATE</span> <span class="k">TABLE</span> <span class="e">TableName </span><span class="sy">(</span> <span class="i">id</span> <span class="k">INTEGER</span> <span class="k">PRIMARY</span> <span class="k">KEY</span> <span class="i">AUTOINCREMENT</span><span class="sy">,</span> <span class="sy">.</span><span class="sy">.</span><span class="sy">.</span> <span class="sy">)</span><span class="sy">;</span> </div> </div> </td> </tr> </table> </div> </div> 当SQLite数据库中包含自增列时,会自动建立一个名为 sqlite_sequence 的表。这个表包含两个列:name和seq。name记录自增列所在的表,seq记录当前序号(下一条记录的编号就是当前序号加1)。如果想把某个自增列的序号归零,只需要修改 sqlite_sequence表就可以了。 <div id="crayon-51c50d9e7aa8a" class="crayon-syntax crayon-theme-classic crayon-font-monaco crayon-os-pc print-yes"> <div class="crayon-plain-wrap"> </div> <div class="crayon-main"> <table class="crayon-table "> <tr class="crayon-row"> <td class="crayon-nums "> <div class="crayon-nums-content"> <div class="crayon-num"> 1 </div> </div> </td> <td class="crayon-code"> <div class="crayon-pre"> <div id="crayon-51c50d9e7aa8a-1" class="crayon-line"> <span class="k">UPDATE</span> <span class="i">sqlite_sequence</span> <span class="k">SET</span> <span class="i">seq</span> <span class="o">=</span> <span class="cn"></span> <span class="k">WHERE</span> <span class="i">name</span> <span class="o">=</span> <span class="s">&#8216;TableName&#8217;</span><span class="sy">;</span> </div> </div> </td> </tr> </table> </div> </div> 也可以直接把该记录删掉: <div id="crayon-51c50d9e7aab0" class="crayon-syntax crayon-theme-classic crayon-font-monaco crayon-os-pc print-yes"> <div class="crayon-plain-wrap"> </div> <div class="crayon-main"> <table class="crayon-table "> <tr class="crayon-row"> <td class="crayon-nums "> <div class="crayon-nums-content"> <div class="crayon-num"> 1 </div> </div> </td> <td class="crayon-code"> <div class="crayon-pre"> <div id="crayon-51c50d9e7aab0-1" class="crayon-line"> <span class="k">DELETE</span> <span class="k">FROM</span> <span class="i">sqlite_sequence</span> <span class="k">WHERE</span> <span class="i">name</span> <span class="o">=</span> <span class="s">&#8216;TableName&#8217;</span><span class="sy">;</span> </div> </div> </td> </tr> </table> </div> </div> 要想将所有表的自增列都归零,直接清空sqlite_sequence表就可以了: <div id="crayon-51c50d9e7aac0" class="crayon-syntax crayon-theme-classic crayon-font-monaco crayon-os-pc print-yes"> <div class="crayon-toolbar"> <div class="crayon-tools"> <span class="crayon-language">Transact-SQL</span> </div> </div> <div class="crayon-plain-wrap"> </div> <div class="crayon-main"> <table class="crayon-table "> <tr class="crayon-row"> <td class="crayon-nums "> <div class="crayon-nums-content"> <div class="crayon-num"> 1 </div> </div> </td> <td class="crayon-code"> <div class="crayon-pre"> <div id="crayon-51c50d9e7aac0-1" class="crayon-line"> <span class="k">DELETE</span> <span class="k">FROM</span> <span class="i">sqlite_sequence</span><span class="sy">;</span> </div> </div> </td> </tr> </table> </div> </div> &nbsp; </div> 来自:http://zhuyanfeng.com/archives/516 ...

2016年8月15日 · 2 分钟 · 天边的星星

我的Android进阶之旅——>Android关于HttpsURLConnection一个忽略Https证书是否正确的Https请求工具类

下面是一个android HttpsURLConnection忽略Https证书是否正确的Https请求工具类,不需要验证服务器端证书是否正确 import Java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.UnsupportedEncodingException; import java.net.HttpURLConnection; import java.net.URL; import java.net.URLEncoder; import java.security.KeyManagementException; import java.security.NoSuchAlgorithmException; import java.security.NoSuchProviderException; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import java.util.Map; import java.util.Map.Entry; import javax.net.ssl.HostnameVerifier; import javax.net.ssl.HttpsURLConnection; import javax.net.ssl.SSLContext; import javax.net.ssl.SSLSession; import javax.net.ssl.SSLSocketFactory; import javax.net.ssl.TrustManager; import javax.net.ssl.X509TrustManager; /** * 忽略Https证书是否正确的Https Post请求工具类 * &lt;p/&gt; * created by OuyangPeng on 2016/1/17. */ public class HttpUtil { private static final String DEFAULT_CHARSET = "UTF-8"; // 默认字符集 private static final String _GET = "GET"; // GET private static final String _POST = "POST";// POST /** * 初始化http请求参数 */ private static HttpURLConnection initHttp(String url, String method, Map&lt;String, String&gt; headers) throws IOException { URL _url = new URL(url); HttpURLConnection http = (HttpURLConnection) _url.openConnection(); // 连接超时 http.setConnectTimeout(25000); // 读取超时 --服务器响应比较慢,增大时间 http.setReadTimeout(25000); http.setRequestMethod(method); http.setRequestProperty("Content-Type", "application/x-www-form-urlencoded"); http.setRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) [chrome](http://www.07net01.com/tags-chrome-0.html)/33.0.1750.146 Safari/537.36"); if (null != headers && !headers.isEmpty()) { for (Entry&lt;String, String&gt; entry : headers.entrySet()) { http.setRequestProperty(entry.getKey(), entry.getValue()); } } http.setDoOutput(true); http.setDoInput(true); http.connect(); return http; } /** * 初始化http请求参数 */ private static HttpsURLConnection initHttps(String url, String method, Map&lt;String, String&gt; headers) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException { TrustManager[] tm = {new MyX509TrustManager()}; SSLContext sslContext = SSLContext.getInstance("SSL"); sslContext.init(null, tm, new java.security.SecureRandom()); // 从上述SSLContext对象中得到SSLSocketFactory对象 SSLSocketFactory ssf = sslContext.getSocketFactory(); URL _url = new URL(url); HttpsURLConnection http = (HttpsURLConnection) _url.openConnection(); // 设置域名校验 http.setHostnameVerifier(new TrustAnyHostnameVerifier()); http.setSSLSocketFactory(ssf); // 连接超时 http.setConnectTimeout(25000); // 读取超时 --服务器响应比较慢,增大时间 http.setReadTimeout(25000); http.setRequestMethod(method); http.setRequestProperty("Content-Type", "application/x-www-form-urlencoded"); http.setRequestProperty("User-Agent", "Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/33.0.1750.146 Safari/537.36"); if (null != headers && !headers.isEmpty()) { for (Entry&lt;String, String&gt; entry : headers.entrySet()) { http.setRequestProperty(entry.getKey(), entry.getValue()); } } http.setDoOutput(true); http.setDoInput(true); http.connect(); return http; } /** * get请求 */ public static String get(String url, Map&lt;String, String&gt; params, Map&lt;String, String&gt; headers) { StringBuffer bufferRes = null; try { HttpURLConnection http = null; if (isHttps(url)) { http = initHttps(initParams(url, params), _GET, headers); } else { http = initHttp(initParams(url, params), _GET, headers); } InputStream in = http.getInputStream(); BufferedReader read = new BufferedReader(new InputStreamReader(in, DEFAULT_CHARSET)); String valueString = null; bufferRes = new StringBuffer(); while ((valueString = read.readLine()) != null) { bufferRes.append(valueString); } in.close(); if (http != null) { http.disconnect();// 关闭连接 } return bufferRes.toString(); } catch (Exception e) { e.printStackTrace(); return null; } } /** * get请求 */ public static String get(String url) { return get(url, null); } /** * get请求 */ public static String get(String url, Map&lt;String, String&gt; params) { return get(url, params, null); } /** * post请求 */ public static String post(String url, String params, Map&lt;String, String&gt; headers) { StringBuffer bufferRes = null; try { HttpURLConnection http = null; if (isHttps(url)) { http = initHttps(url, _POST, headers); } else { http = initHttp(url, _POST, headers); } OutputStream out = http.getOutputStream(); out.write(params.getBytes(DEFAULT_CHARSET)); out.flush(); out.close(); InputStream in = http.getInputStream(); BufferedReader read = new BufferedReader(new InputStreamReader(in, DEFAULT_CHARSET)); String valueString = null; bufferRes = new StringBuffer(); while ((valueString = read.readLine()) != null) { bufferRes.append(valueString); } in.close(); if (http != null) { http.disconnect();// 关闭连接 } return bufferRes.toString(); } catch (Exception e) { e.printStackTrace(); return null; } } /** * post请求 */ public static String post(String url, Map&lt;String, String&gt; params) { return post(url, map2Url(params), null); } /** * post请求 */ public static String post(String url, Map&lt;String, String&gt; params, Map&lt;String, String&gt; headers) { return post(url, map2Url(params), headers); } /** * 初始化参数 */ public static String initParams(String url, Map&lt;String, String&gt; params) { if (null == params || params.isEmpty()) { return url; } StringBuilder sb = new StringBuilder(url); if (url.indexOf("?") == -1) { sb.append("?"); } sb.append(map2Url(params)); return sb.toString(); } /** * map转url参数 */ public static String map2Url(Map&lt;String, String&gt; paramToMap) { if (null == paramToMap || paramToMap.isEmpty()) { return null; } StringBuffer url = new StringBuffer(); boolean isfist = true; for (Entry&lt;String, String&gt; entry : paramToMap.entrySet()) { if (isfist) { isfist = false; } else { url.append("&"); } url.append(entry.getKey()).append("="); String value = http://blog.csdn.net/ouyang_peng/article/details/entry.getValue(); if (null == value || "".equals(value.trim())) { try { url.append(URLEncoder.encode(value, DEFAULT_CHARSET)); } catch (UnsupportedEncodingException e) { e.printStackTrace(); } } } return url.toString(); } /** * 检测是否https */ private static boolean isHttps(String url) { return url.startsWith("https"); } /** * 不进行主机名确认 */ private static class TrustAnyHostnameVerifier implements HostnameVerifier { public boolean verify(String hostname, SSLSession session) { return true; } } /** * 信任所有主机 对于任何证书都不做SSL检测 * 安全验证机制,而Android采用的是X509验证 */ private static class MyX509TrustManager implements X509TrustManager { public X509Certificate[] getAcceptedIssuers() { return null; } @Override public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException { } @Override public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException { } } } ...

2016年8月10日 · 4 分钟 · 天边的星星

ButterKnife:8.1.0的使用

https://github.com/JakeWharton/butterknife 最近使用的新版的ButterKnife,跟之前有点不一样的地方。记录一下! 导入依赖项:Project Structure→app→Dependencies→add→Library Dependence然后搜索ButterKnife导入对应的依赖。 需要添加的一些插件 Project的build.gradle文件中增加classpath内容: ``` buildscript { repositories { jcenter() } dependencies { classpath &lt;span class="hljs-symbol">'com&lt;/span>.android.tools.build:gradle:&lt;span class="hljs-number">2.0&lt;/span>&lt;span class="hljs-number">.0&lt;/span>' classpath &lt;span class="hljs-symbol">'com&lt;/span>.neenbedankt.gradle.plugins:android-apt:&lt;span class="hljs-number">1.8&lt;/span>' &lt;span class="hljs-comment">//增加这一句&lt;/span> } } allprojects { repositories { jcenter() } } task clean(&lt;span class="hljs-class">&lt;span class="hljs-keyword">type&lt;/span>:&lt;/span> &lt;span class="hljs-type">Delete&lt;/span>) { delete rootProject.buildDir } 2. app的build.gradle文件中增加classpath内容: ``` `apply plugin: &lt;span class="hljs-string">'com.neenbedankt.android-apt'&lt;/span>&lt;span class="hljs-comment">//增加这一句&lt;/span> dependencies { compile fileTree(&lt;span class="hljs-keyword">include&lt;/span>: [&lt;span class="hljs-string">'*.jar'&lt;/span>], dir: &lt;span class="hljs-string">'libs'&lt;/span>) testCompile &lt;span class="hljs-string">'junit:junit:4.12'&lt;/span> compile &lt;span class="hljs-string">'com.android.support:appcompat-v7:23.4.0'&lt;/span> compile &lt;span class="hljs-string">'com.jakewharton:butterknife:8.1.0'&lt;/span> apt &lt;span class="hljs-string">'com.jakewharton:butterknife-compiler:8.1.0'&lt;/span>&lt;span class="hljs-comment">//增加这一句&lt;/span> }` 代码中的使用,具体就是之前的inject变成了现在的bind,其他变化不大: ``` `public <span class=“hljs-class”><span class=“hljs-keyword”>class</span> <span class=“hljs-title”>MainActivity</span> <span class=“hljs-keyword”><span class=“hljs-keyword”>extends</span></span> <span class=“hljs-title”>AppCompatActivity</span> {</span> <span class=“hljs-annotation”>@BindView</span>(<span class=“hljs-type”>R</span>.id.btn_qq) <span class=“hljs-type”>Button</span> qqBtn; <span class=“hljs-annotation”>@Override</span> <span class=“hljs-keyword”>protected</span> void onCreate(<span class=“hljs-type”>Bundle</span> savedInstanceState) { <span class=“hljs-keyword”>super</span>.onCreate(savedInstanceState); setContentView(<span class=“hljs-type”>R</span>.layout.activity_main); ...

2016年8月10日 · 1 分钟 · 天边的星星

隐藏弹出键盘,Edittext有光标实现方式

1、第一种方式 edittext.setRawInputType(InputType.TYPE_TEXT_FLAG_MULTI_LINE); edittext.setTextIsSelectable(true); 2、第二种方式 /** * 禁止Edittext弹出软件盘,光标依然正常显示。 */ public void disableShowSoftInput(EditText editText) { if (android.os.Build.VERSION.SDK_INT &lt;= 10) { // editText.setInputType(InputType.TYPE_NULL); editText.setRawInputType(InputType.TYPE_TEXT_FLAG_MULTI_LINE); editText.setTextIsSelectable(true); } else { Class&lt;EditText&gt; cls = EditText.class; Method method; try { method = cls.getMethod("setShowSoftInputOnFocus",boolean.class); method.setAccessible(true); method.invoke(editText, false); }catch (Exception e) { // TODO: handle exception } try { method = cls.getMethod("setSoftInputShownOnFocus",boolean.class); method.setAccessible(true); method.invoke(editText, false); }catch (Exception e) { // TODO: handle exception } } }

2016年8月3日 · 1 分钟 · 天边的星星

Android 监听锁屏/开屏事件

1. 两种方案 (1) 监听BroadcastReceiver (2)获取PowerManager事件 ### 2. BroadcastReceiver {#articleHeader1} #### 2.1. 事件 总共有3个事件: Intent.ACTION_SCREEN_ON : 屏幕点亮 Intent.ACTION_SCREEN_OFF :屏幕关闭 Intent.ACTION_USER_PRESENT: 用户解锁 #### 2.2. 权限 监听用户解锁需要在AndroidManifest中注册权限 &lt;uses-permission android:name="android.permission.RECEIVE_USER_PRESENT" /&gt; #### 2.3. IntentFilter代码 if (mContext != null) { IntentFilter filter = new IntentFilter(); filter.addAction(Intent.ACTION_SCREEN_ON); filter.addAction(Intent.ACTION_SCREEN_OFF); filter.addAction(Intent.ACTION_USER_PRESENT); mContext.registerReceiver(mScreenReceiver, filter); } ### 3. PowerManager {#articleHeader2} PowerManager manager = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE); if (manager.isScreenOn()) { if (mScreenStateListener != null) { mScreenStateListener.onScreenOn(); } } else { if (mScreenStateListener != null) { mScreenStateListener.onScreenOff(); } } ...

2016年8月2日 · 4 分钟 · 天边的星星

Fragment销毁时replace和add两个方法的区别

这个首先从一个bug说起,如图: 我们都知道fragment切换有两种方式: replace方式 transaction.replace(R.id.content, IndexFragment); add-hide-show方式 transaction.add(R.id.content, IndexFragment); transaction.hide(otherfragment); transaction.show(thisfragment); 而上面按钮中出现bug的就是采用第二种方式。然后我们来分析下用add,hide,show为什么出现这种bug,我把每个操作都打印出了以下日志: 复现bug的操作是: 1.首先打开,默认选中的是第一个tab,如上面的一张图片正常那样。 2.切换到tab2,并把tab1 hide掉; 3.再切回到tab1,并不会触发tab1对应fragment的任何生命周期; 4.然后home键进入后台,我在activity的onPause()中手动对IndexFragment赋空,模拟长时间后台,系统销毁了该引用。 IndexFragment=null; 5.再次启动,其实tab1 的fragment实例在内存中还在,只是他的引用被销毁了。 6.再切到tab2,这里其实是先把tab1的hide,在show tab2,但是tab1 的fragment引用为空,所以无法hide,就出现了tab2叠在tab1上的花屏情况。 7.再切到tab1,tab1就会重复创建对象。 同样的操作,我们使用replace的方式 使用replace方式,虽然这种方式会避免上述的bug,但也是重复创建了对象。因为replace方式,对应的FrameLayout只有一 层,而add方式,这个FrameLayout其实有2层。但是这种方式的缺点是:每次replace会把生命周期全部执行一遍,如果在这些生命周期函数 里拉取数据的话,就会不断重复的加载刷新数据。 那么最合适的处理方式是这样的: 1.在add的时候,加上一个tab参数 transaction.add(R.id.content, IndexFragment,”Tab1″); 2.然后当IndexFragment引用被回收置空的话,先通过 IndexFragment=FragmentManager.findFragmentByTag(“Tab1″); 找到对应的引用,然后继续上面的hide,show;

2016年7月27日 · 1 分钟 · 天边的星星