首页 文章 精选 留言 我的

精选列表

搜索[Android],共10000篇文章
优秀的个人博客,低调大师

Android图文上传

这次介绍下如何使用Retrofit+rxjava上传图片和文字 接口的写法 public interface MarketApiService { @Multipart//这里一定要加这个 @POST("market/addNewOrder") Observable<ResultBean> addNewOrder(@QueryMap Map<String, String> map, @Part MultipartBody.Part pic); } 上传的代码 Map<String, String> params = new HashMap<String, String>(); params.put("ship_type_id", type); params.put("cons_number", consNumber); params.put("note", beizhu); File fileByUri = FileUtil.getFileByUri(imagepath, this); //这里最好写成MediaType.parse("image/*"),之前写成MediaType.parse("image/png")上传失败 RequestBody photoRequestBody = RequestBody.create(MediaType.parse("image/*"), fileByUri); MultipartBody.Part photo = MultipartBody.Part.createFormData("file", fileByUri.getName(), photoRequestBody); RetrofitUtils.getInstance().getApiServier(MarketApiService.class) .addNewOrder(params,photo) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new Consumer<ResultBean>() { @Override public void accept(ResultBean resultBean) throws Exception { } }, new Consumer<Throwable>() { @Override public void accept(Throwable throwable) throws Exception { } }); 这里的图片选择器使用的是知乎的图片选择器https://github.com/zhihu/Matisse 另外这里还有将Uri转换为File的工具类(因为知乎图片选择器返回的是Uri) public static File getFileByUri(Uri uri, Context context) { String path = null; if ("file".equals(uri.getScheme())) { path = uri.getEncodedPath(); if (path != null) { path = Uri.decode(path); ContentResolver cr = context.getContentResolver(); StringBuffer buff = new StringBuffer(); buff.append("(").append(MediaStore.Images.ImageColumns.DATA).append("=").append("'" + path + "'").append(")"); Cursor cur = cr.query(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, new String[] { MediaStore.Images.ImageColumns._ID, MediaStore.Images.ImageColumns.DATA }, buff.toString(), null, null); int index = 0; int dataIdx = 0; for (cur.moveToFirst(); !cur.isAfterLast(); cur.moveToNext()) { index = cur.getColumnIndex(MediaStore.Images.ImageColumns._ID); index = cur.getInt(index); dataIdx = cur.getColumnIndex(MediaStore.Images.ImageColumns.DATA); path = cur.getString(dataIdx); } cur.close(); if (index == 0) { } else { Uri u = Uri.parse("content://media/external/images/media/" + index); System.out.println("temp uri is :" + u); } } if (path != null) { return new File(path); } } else if ("content".equals(uri.getScheme())) { // 4.2.2以后 String[] proj = { MediaStore.Images.Media.DATA }; Cursor cursor = context.getContentResolver().query(uri, proj, null, null, null); if (cursor.moveToFirst()) { int columnIndex = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA); path = cursor.getString(columnIndex); } cursor.close(); return new File(path); } else { //Log.i(TAG, "Uri Scheme:" + uri.getScheme()); } return null; } 个人博客https://myml666.github.io/

优秀的个人博客,低调大师

Android--WebSocket

版权声明:本文为博主原创文章,转载请标明出处。 https://blog.csdn.net/chaoyu168/article/details/79625691 WebSocket 是一种双向通信协议,在建立连接后,WebSocket服务器和 Browser/Client Agent 都能主动的向对方发送或接收数据,就像 Socket一样。它类似TCP长连接,但是WebSocket使用的是ws和wss两种通信协议,所以这是完全不同于HTTP的一种网络协议,尽管它也是默认使用80和443端口。WebSocket的连接包括第一步握手和第二步数据交换。在通过WebSocket开始双向通信时,首先需要与服务器建立连接。而用于建立连接的请求是由客户端发起,服务器端将会确认连接对象的源以及协议,并发送连接许可的响应。在发送了响应之后,浏览器会将该连接升级为WebSocket。握手成功之后就建立起长连接,直到服务器或者浏览器某一方主动断开连接。客户端发起连接非常简单,只需要一句Javascript即可实现: varws=newWebSocket('ws://www.example.com/bar') 然后就是第二步,浏览器和服务器之间双向数据发送了。Nodejs是即时通信应用很完美的开发语言(此处不是为了引起撕逼),很自然地,Nodejs本身也比较完善地实现了WebSocket相关API。客户端(浏览器)发送消息到服务器最简单的方法就是通过调用socket对象的send()方法,然后Node服务器通过注册message事件进行监听,当然服务器send过来的消息也是通过对客户端message事件进行捕捉,从而实现双向的数据交互。这两者之间交换的数据可以是字符串、ArrayBuffer(二进制数据)或者Blob,所以WebSocket也是可以传输文件的。也可以通过广播事件将消息发送到所有连接到服务器的客户端。 使用框架:Java-WebSocket Gradle To use Gradle add the maven central repository to your repositories list : mavenCentral() Then you can just add the latest version to your build. compile "org.java-websocket:Java-WebSocket:1.3.8" Client Example import java.net.URI; import java.net.URISyntaxException; import org.java_websocket.client.WebSocketClient; import org.java_websocket.drafts.Draft; import org.java_websocket.drafts.Draft_6455; import org.java_websocket.handshake.ServerHandshake; public class EmptyClient extends WebSocketClient { public EmptyClient(URI serverUri, Draft draft) { super(serverUri, draft); } public EmptyClient(URI serverURI) { super(serverURI); } @Override public void onOpen(ServerHandshake handshakedata) { send("Hello, it is me. Mario :)"); System.out.println("new connection opened"); } @Override public void onClose(int code, String reason, boolean remote) { System.out.println("closed with exit code " + code + " additional info: " + reason); } @Override public void onMessage(String message) { System.out.println("received message: " + message); } @Override public void onMessage(ByteBuffer message) { System.out.println("received ByteBuffer"); } @Override public void onError(Exception ex) { System.err.println("an error occurred:" + ex); } public static void main(String[] args) throws URISyntaxException { WebSocketClient client = new EmptyClient(new URI("ws://localhost:8887")); client.connect(); } } Server Example import java.net.InetSocketAddress; import org.java_websocket.WebSocket; import org.java_websocket.handshake.ClientHandshake; import org.java_websocket.server.WebSocketServer; public class SimpleServer extends WebSocketServer { public SimpleServer(InetSocketAddress address) { super(address); } @Override public void onOpen(WebSocket conn, ClientHandshake handshake) { conn.send("Welcome to the server!"); //This method sends a message to the new client broadcast( "new connection: " + handshake.getResourceDescriptor() ); //This method sends a message to all clients connected System.out.println("new connection to " + conn.getRemoteSocketAddress()); } @Override public void onClose(WebSocket conn, int code, String reason, boolean remote) { System.out.println("closed " + conn.getRemoteSocketAddress() + " with exit code " + code + " additional info: " + reason); } @Override public void onMessage(WebSocket conn, String message) { System.out.println("received message from " + conn.getRemoteSocketAddress() + ": " + message); } @Override public void onMessage( WebSocket conn, ByteBuffer message ) { System.out.println("received ByteBuffer from " + conn.getRemoteSocketAddress()); } @Override public void onError(WebSocket conn, Exception ex) { System.err.println("an error occured on connection " + conn.getRemoteSocketAddress() + ":" + ex); } @Override public void onStart() { System.out.println("server started successfully"); } public static void main(String[] args) { String host = "localhost"; int port = 8887; WebSocketServer server = new SimpleServer(new InetSocketAddress(host, port)); server.run(); } } 还有一个封装框架挺好:RxWebSocket how to use 添加依赖: 在项目module下gradle加入: //本项目 compile 'com.dhh:websocket:1.5.0' init //if you want to use your okhttpClient OkHttpClient yourClient = new OkHttpClient(); RxWebSocketUtil.getInstance().setClient(yourClient); // show log,default false RxWebSocketUtil.getInstance().setShowLog(true); WSS support,其实就是设置okhttp的SSL,请参照okhttp的设置 //wss support RxWebSocketUtil.getInstance().setSSLSocketFactory(yourSSlSocketFactory,yourX509TrustManager); RxWebSocketUtil.getInstance().getWebSocket("wss://..."); //or OkHttpClient client = new OkHttpClient.Builder() .sslSocketFactory(yourSSlSocketFactory, yourX509TrustManager) //other config... .build(); RxWebSocketUtil.getInstance().setClient(client); open WebSocket RxWebSocketUtil.getInstance().getWebSocketInfo(url) .subscribe(new Action1<WebSocketInfo>() { @Override public void call(WebSocketInfo webSocketInfo) { mWebSocket = webSocketInfo.getWebSocket(); Log.d("MainActivity", webSocketInfo.getString()); Log.d("MainActivity", "webSocketInfo.getByteString():" + webSocketInfo.getByteString()); } }); mWebSocket.send("hello word"); // use WebSocketSubscriber RxWebSocketUtil.getInstance().getWebSocketInfo("ws://10.7.5.88:8089") //RxLifecycle : https://github.com/dhhAndroid/RxLifecycle .compose(RxLifecycle.with(this).<WebSocketInfo>bindOnDestroy()) .subscribe(new WebSocketSubscriber() { @Override public void onOpen(@NonNull WebSocket webSocket) { } @Override public void onMessage(@NonNull String text) { } @Override public void onMessage(@NonNull ByteString bytes) { } }); // use WebSokcetAction1 RxWebSocketUtil.getInstance().getWebSocketInfo("ws://10.7.5.88:8089") //RxLifecycle : https://github.com/dhhAndroid/RxLifecycle .compose(RxLifecycle.with(this).<WebSocketInfo>bindOnDestroy()) .subscribe(new WebSokcetAction1() { @Override public void onOpen(@NonNull WebSocket webSocket) { } @Override public void onMessage(@NonNull String text) { } @Override public void onMessage(@NonNull ByteString bytes) { } }); //get StringMsg RxWebSocketUtil.getInstance().getWebSocketString(url) .subscribe(new Action1<String>() { @Override public void call(String s) { } }); // get ByteString RxWebSocketUtil.getInstance().getWebSocketByteString(url) .subscribe(new Action1<ByteString>() { @Override public void call(ByteString byteString) { } }); //get WebSocket RxWebSocketUtil.getInstance().getWebSocket(url) .subscribe(new Action1<WebSocket>() { @Override public void call(WebSocket webSocket) { } }); //with timeout RxWebSocketUtil.getInstance().getWebSocketInfo(url, 10, TimeUnit.SECONDS) .subscribe(new Action1<WebSocketInfo>() { @Override public void call(WebSocketInfo webSocketInfo) { } }); // Rxbinding RxView.clicks(centect) .flatMap(new Func1<Void, Observable<String>>() { @Override public Observable<String> call(Void aVoid) { return RxWebSocketUtil.getInstance().getWebSocketString(url); } }) .subscribe(new Action1<String>() { @Override public void call(String s) { //the s !=null Log.d("MainActivity", s); textview.setText(Html.fromHtml(s)); } }); 发送消息 //用WebSocket的引用直接发 mWebSocket.send("hello word"); //url 对应的WebSocket已经打开可以这样send,否则报错 RxWebSocketUtil.getInstance().send(url, "hello"); RxWebSocketUtil.getInstance().send(url, ByteString.EMPTY); //异步发送,若WebSocket已经打开,直接发送,若没有打开,打开一个WebSocket发送完数据,直接关闭. RxWebSocketUtil.getInstance().asyncSend(url, "hello"); RxWebSocketUtil.getInstance().asyncSend(url, ByteString.EMPTY); 注销 RxJava的注销方式,就可以取消订阅. 项目里的demo里,简单实现了一个Lifecycle.仅供参考. Subscription subscription = RxWebSocketUtil.getInstance().getWebSocketString("ws://sdfs").subscribe(); //注销 if(subscription!=null&&!subscription.isUnsubscribed()) { subscription.unsubscribe(); }

优秀的个人博客,低调大师

Android编码规范

目录介绍 1.命名 1.为什么需要编码规范 2.包命名 3.类和接口命名 4.方法的命名 5.变量命名 6.成员变量命名 7.常量命名 8.异常命名 9.layout 命名 10.id 命名 11.资源命名 2.注释 1.文件注释 2.类注释 3.方法注释 4.类成员变量和常量注释 5.其他注释 6.XML注释 3.代码风格 1.缩进 2.空行 3.行宽 4.其他问题说明 4.1 版本更新情况 4.2 参考链接 4.2 个人博客 0.备注 建议结合代码,看博客更加高效,项目地址:https://github.com/yangchong211/ 博客大汇总,持续更新目录说明,记录所有开源项目和博客 如果那个项目好,可以star一下…… 1.命名 1.为什么需要编码规范? 编码规范对于程序员而言尤为重要,有以下几个原因: 一个软件的生命周期中,80%的花费在于维护 几乎没有任何一个软件,在其整个生命周期中,均由最初的开发人员来维护 编码规范可以改善软件的可读性,可以让程序员尽快而彻底地理解新的代码 如果你将源码作为产品发布,就需要确任它是否被很好的打包并且清晰无误,一如你已构建的其它任何产品 2.包命名 命名规则: 一个唯一包名的前缀总是全部小写的ASCII 字母并且是一个顶级域名 通常是com.edu.gov.mil.net.org包名的后续部分根据不同机构各自内部的命名规范而不尽相同 这类命名规范可能以特定目录名的组成来区分部门 (department) ,项目(project),机器(machine),或注册名(login names)。 例如: com.ycbjie.player 规约:包命名必须以com.ycbjie开始,后面跟有项目名称(或者缩写),再后面为模块名或层级名称。 如:com.ycbjie.项目缩写.模块名 com.ycbjie.player.bookmark 如:com.ycbjie.项目缩写.层级名 com.ycbjie.player.activities 模块包命名的含义 activity 放activity相关的文件 service 放Service相关的文件 broadcast 放广播接收者相关的文件 fragment 放fragment相关的文件 view 放自定义view或者view文件 utils 放工具类文件 bean/entry 放实体类文件 http 放请求网络文件 api 放服务器端提供接口的文件 base 放抽取公共类文件 cache 放缓存处理的文件 db 放数据库处理相关的文件 inter 放接口类文件 listener adapter 放适配器adapter相关的文件 callback 3.类和接口命名 命名规则:类名是个一名词,采用大小写混合的方式,每个单词的首字母大写 尽量使你的类名简洁而富于描述,见名知意。使用完整单词,避免缩写词(除非该缩写词被更广泛使用,像 URL,HTML) 接口一般要使用able、ible、er 等后缀 例如: class Raster; class ImageSprite;规约:类名必须使用驼峰规则,即首字母必须大写,如果为词组,则每个单词的首字母也必须要大写,类名必须使用名词,或名词词组。 如:class BookMarkAdd 正确 如:class AddBookReadPlanActivity 错误! 应为 class BookReadPlanAdd 4.方法的命名 命名规则:方法名是一个动词,采用大小写混合的方式,第一个单词的首字母小写,其后单词的首字母大写 例如: public void run(); public String getBookName(); 类中常用方法的命名: 类的获取方法(一般具有返回值)一般要求在被访问的字段名前加上get,如getFirstName(),getLastName()。一般来说,get前缀方法返回的是单个值,find前缀的方法返回的是列表值。 类的设置方法(一般返回类型为void):被访问字段名的前面加上前缀 set,如setFirstName(),setLastName(). 类的布尔型的判断方法一般要求方法名使用单词 is或has 做前缀,如isPersistent(),isString()。或者使用具有逻辑意义的单词,例如equal 或equals。 类的普通方法一般采用完整的英文描述说明成员方法功能,第一个单词尽可能采用动词,首字母小写,如openFile(),addCount()。 构造方法应该用递增的方式写。(参数多的写在后面)。 toString()方法:一般情况下,每个类都应该定义toString(),其格式为: 5.变量命名 命名规则:第一个单词的首字母小写,其后单词的首字母大写 变量名不应以下划线或美元符号开头,尽管这在语法上是允许的。 变量名应简短且富于描述。变量名的选用应该易于记忆,即,能够指出其用途。 尽量避免单个字符的变量名,除非是一次性的临时变量。临时变量通常被取名为 i,j,k,m 和 n,它们一般用于整型;c,d,e,它们一般用于字符型。 规约:变量命名也必须使用驼峰规则,但是首字母必须小写,变量名尽可能的使用名词或名词词组。要求简单易懂,不允许无意义的单词。 如:String bookYCName; 正确 如:String bookYCNameString; 错误! 6.成员变量命名 同变量命名,但不要在私有变量前添加m字样! 7.常量命名 命名规则:类常量的声明,应该全部大写,单词间用下划线隔开 例如:static final int MIN_WIDTH = 4; 例如:static final int MAX_WIDTH = 999; 例如:static final int GET_THE_CPU = 1; 8.异常命名 自定义异常的命名必须以Exception为结尾。已明确标示为一个异常。 9.layout 命名 规约:layout xml 的命名必须以 全部单词小写,单词间以下划线分割,并且使用名词或名词词组,即使用 模块名_功能名称 来命名。 如:knowledge_gained_main.xml 正确 如:list_book.xml 错误! 10.id 命名 规约:layout 中所使用的id必须以全部单词小写,单词间以下划线分割,并且使用名词或名词词组,要求能够通过id直接理解当前组件要实现的功能。 如:某TextView @+id/tvbookname 错误 !应为 @+id/tv_book_name 如:某EditText @+id/etbookname 错误 !应为 @+id/et_book_name 11.资源命名 规约:layout中所使用的所有资源(如drawable,style等)命名必须以全部单词小写,单词间以下划线分割,并且尽可能的使用名词或名词组,即使用 模块名_用途 来命名。如果为公共资源,如分割线等,则直接用用途来命名 如:menu_icon_navigate.png 正确 如:某分割线:line.png 或 separator.png 正确 2.注释 Java 程序有两类注释: 实现注释(implementation comments),实现注释是使用/.../和//界定的注释。 文档注释(document comments)。文档注释由/*.../界定。文档注释可以通过javadoc 工具转换成HTML 文件。 1.文件注释 所有的源文件都应该在开头有一个注释,其中列出类名、版本信息、日期和版权声明。 /* * 文件名 * 包含类名列表 * 版本信息,版本号 * 创建日期。 * 版权声明 */ 2.类注释 每一个类都要包含如下格式的注释,以说明当前类的功能等。 /** * <pre> * author: yangchong * blog : www.ycbjie.cn * time : 2017/01/24 * desc : 图片加载工具类 * revise: 修改备注信息 * </pre> */ 3.方法注释 每一个方法都要包含 如下格式的注释 包括当前方法的用途,当前方法参数的含义,当前方法返回值的内容和抛出异常的列表。 /** * 方法的一句话概述 * <p>方法详述(简单方法可不必详述)</p> * @param s 说明参数含义 * @return 说明返回值含义 * @throws IOException 说明发生此异常的条件 * @throws NullPointerException 说明发生此异常的条件 */ 4.类成员变量和常量注释 成员变量和常量需要使用java doc形式的注释,以说明当前变量或常量的含义 /**XXXX含义*/ 或者 //XXXx含义 5.其他注释 方法内部的注释 如果需要多行 使用/…… /形式 如果为单行是用//……形式的注释。 不要再方法内部使用 java doc 形式的注释“/……/” 6.XML注释 规约:如果当前layout 或资源需要被多处调用,或公共使用的layout(若list_item),则需要在xml写明注释。要求注释清晰易懂。 3.代码风格 1.缩进 规约:不允许使用Tab进行缩进,使用空格进行缩进,推荐缩进为2空格。 2.空行 空行将逻辑相关的代码段分隔开,以提高可读性。 下列情况应该总是使用空行: 一个源文件的两个片段(section)之间 类声明和接口声明之间 两个方法之间 方法内的局部变量和方法的第一条语句之间 一个方法内的两个逻辑段之间,用以提高可读性 规约:通常在 变量声明区域之后要用空行分隔,常量声明区域之后要有空行 分隔,方法声明之前要有空行分隔。 3.行宽 无特别规定,因为现在的显示器都比较大,所以推荐使用120进行设置。 4.其他问题说明 4.1 版本更新情况 v1.0.0 2016年11月19日 v1.0.1 2017年1月17日 v1.0.2 2018年2月8日 4.2 参考链接 阿里编码规范文档,可以直接去下载看看,强烈建议程序员认真看看。真心非常不错 4.2 个人博客 github: https://github.com/yangchong211 知乎: https://www.zhihu.com/people/yang-chong-69-24/pins/posts 简书: http://www.jianshu.com/u/b7b2c6ed9284 csdn: http://my.csdn.net/m0_37700275 喜马拉雅听书: http://www.ximalaya.com/zhubo/71989305/ 泡在网上的日子:http://www.jcodecraeer.com/member/content_list.php?channelid=1 邮箱:yangchong211@163.com 阿里云博客:https://yq.aliyun.com/users/article?spm=5176.100239.headeruserinfo.3.dT4bcV

优秀的个人博客,低调大师

Android Studio 升级

CanaryChannel :金丝雀版, 能获取最新的功能(Bug较多 并且都还没有验证) Develop Channel: 开发者版,到了这个版本大Bug都得到了解决; Beta Channel:测试版,到这里很多小bug都得到了解决,问题还有点,基本可能是我们遇不到的; Stable Channel:正式稳定版,到这里就是官方推荐的最新正式版,不过要等很久,各项功能都很稳定,基本没问题了。适合刚接触AndroidStudio的人使用,和那些最求稳定的开发人员。想我这样喜欢尝鲜的开发人员,就喜欢使用最新的beta版本

资源下载

更多资源
Nacos

Nacos

Nacos /nɑ:kəʊs/ 是 Dynamic Naming and Configuration Service 的首字母简称,一个易于构建 AI Agent 应用的动态服务发现、配置管理和AI智能体管理平台。Nacos 致力于帮助您发现、配置和管理微服务及AI智能体应用。Nacos 提供了一组简单易用的特性集,帮助您快速实现动态服务发现、服务配置、服务元数据、流量管理。Nacos 帮助您更敏捷和容易地构建、交付和管理微服务平台。

Spring

Spring

Spring框架(Spring Framework)是由Rod Johnson于2002年提出的开源Java企业级应用框架,旨在通过使用JavaBean替代传统EJB实现方式降低企业级编程开发的复杂性。该框架基于简单性、可测试性和松耦合性设计理念,提供核心容器、应用上下文、数据访问集成等模块,支持整合Hibernate、Struts等第三方框架,其适用范围不仅限于服务器端开发,绝大多数Java应用均可从中受益。

Rocky Linux

Rocky Linux

Rocky Linux(中文名:洛基)是由Gregory Kurtzer于2020年12月发起的企业级Linux发行版,作为CentOS稳定版停止维护后与RHEL(Red Hat Enterprise Linux)完全兼容的开源替代方案,由社区拥有并管理,支持x86_64、aarch64等架构。其通过重新编译RHEL源代码提供长期稳定性,采用模块化包装和SELinux安全架构,默认包含GNOME桌面环境及XFS文件系统,支持十年生命周期更新。

WebStorm

WebStorm

WebStorm 是jetbrains公司旗下一款JavaScript 开发工具。目前已经被广大中国JS开发者誉为“Web前端开发神器”、“最强大的HTML5编辑器”、“最智能的JavaScript IDE”等。与IntelliJ IDEA同源,继承了IntelliJ IDEA强大的JS部分的功能。

用户登录
用户注册