Comments (40)
这需要我来说明一下建立这个项目的初衷和开发过程,其实我早就想写了,并非针对你的提问,但跟你的问题还有点关系。鉴于语言表达能力所限,还是用中文吧。
Yasea项目之前,其实我对安卓推流实现几乎一无所知,只是公司为了进军移动端直播而委派给我的新任务,由于公司内部的人对此也是一无所知,所以在软硬编码方案选择上犹豫不决,只能一次又一次尝试。最先参考其它sdk用ffmpeg实现了软编码,由于ffmpeg强大的现成资源,没花多少时间鼓捣一阵后能推流了,但后来发现时间长了手机发烫的问题(当然还有体积庞大的问题),于是又开始尝试硬编码方案。
硬编码方案中,你要解决三个问题——编码、封装、协议。第一个最好办,你可以基于MediaCodec提供的API,编程十分简单;第二个没有现成的,但是我在github上有幸发现srs-sea这个优秀项目,它解决了安卓硬编码输出的h.264/AAC裸流封装为FLV;第三个颇费周折,我上哪去找rtmp的库呢?当时还没有非要用纯Java实现的想法,所以我能找啥就用啥。rtmpdump?最有名的开源librtmp,但代码烂,非首选;rtmp服务器里面抠,代码量太大驾驭不了,倒是看中了SRS里面的srs-librtmp作为备选方案,为此我在github上还建立了repo,并且实现了。
本来以为随便测试一下就这样应付过去算了,直到我无意发现了SimpleRtmp,这是个纯Java实现的RTMP,而且三年没更新了。其实当时我完全可以不必理它的,因为我对Java生疏,不想读源码,但是SimpleRtmp的代码规范简洁,以及注释充分,让我心念一动——何不做成Java一条龙呢?**这是一个创新实现,放眼全世界恐怕没有先例。**就是这个念头让我在清明节花了三天时间把代码和RTMP全部熟悉了一遍,直到胸有成竹,接下来一天时间居然被我用纯Java实现了推流,而且测试通过了好多部安卓手机,效果还不错。
我有点兴奋,但当时并没考虑开源,因为优先考虑给公司产品提供方案。不过开会讨论下来,硬编码仍是作为一个备选方案被搁置了,团队以软编码方案优先。当然我理解团队决定,毕竟考虑到安卓兼容性的问题,在产品应用上是有风险的。
本来呢,这样也就算了,我也算尽忠职守了。不过呢,我想想以前花的力气要真白费了怪可惜的,毕竟github上这方面都没有先例,反正公司看了也不当业务首选,何不开源算了。因为代码主要用了srs-sea,我就随意取了一个名字叫yasea。
我是个闷*的家伙,没事爱到网上吹牛逼,比如知乎上有个问题,如何实现一个直播系统之类,一帮专家们在那里说的长篇大论头头是道,但谁也不肯透露他们做的东西具体怎样的,反正都是一堆SDK,我就说了一句我做了一个yasea,然后贴了一张很一般的效果图。我还给SRS作者写信,跟他说我做了一个yasea,然后表示一下感谢之类的屁话。我还在半夜突发奇想半夜上Hackernews说我做了一个yasea,然后洗洗睡了。
结果第二天知乎上有人私信我了,说你的yasea貌似不支持Nginx-RTMP啊。SRS的作者邮箱回复了,说用Java写RTMP很有趣,然后是一堆鼓励的屁话。一个印度人还在github上提issue说能不能实现MP4录制啊,这玩意儿很有价值但太稀缺了之类。
本来嘛,我可以不理他们的,开源项目就让它自身自灭好了。不过我还算有点好高骛远,何不按照他们的意见试试看呢?于是我居然**全部回复并且承诺了这帮家伙,然后继续做下去了。不过我发现他们的问题和意见其实很有价值,比如Nginx-RTMP为啥推不了,不同服务器有哪些交互,为啥有的安卓机器帧率设置不了,有的芯片的编码器对分辨率数值很敏感,为啥推流一定要搞MP4录制还不是FLV的等等。我发现了很多文档上查不到,而且别人也不会告诉我的秘密。**而且,我对市面上的商业产品——比如映客——背后使用了哪些以技术以及为什么这么设计豁然开朗。
这里趁机正式回复一下你的问题吧——**为啥用硬编码?因为先对软编码,长时间推流手机不发烫是真的。**当然有个前提条件,你不能加特效,无论是美颜软件,还是摄像头自身支持美化磨皮,时间一长就烫得不行,怎么优化都没用,手机GPU优化目前还远远不够。映客这方面都没做好还有,**发烫跟帧率、用Java而不是C实现YUV变换都没有关系。**一个不用任何特效的中低端手机,比一个有特效摄像头的高端手机,十分钟内就能感受到温度的差别,而且是摄像头的位置,而不是电池的位置。
至于编码器芯片,我测过高通、联发科、三星和华为四大厂家基本都涵盖了,至于手机品牌就不用累述。但我不保证每个版本我都测过了,我不是土豪,不是所有手机都在手,比如华为最新的Ascend和Mate,据说用了自家编码器(据说还是强抗烫的那种),yasea就没试过。顺便说一下MTK这个屌丝,就是它对分辨率很敏感,必须是32x(UV分量16x,Y就是32x)不然编码有问题,软编码就没有这个限制。
至于固定参数,的确存在你所说的那种,某些编码器profile和level都是写死的,连fps都是写死的,所以很多人问我为啥设置了fps=24实际输出帧率还这么低,播放不平滑之类。这方面我真的无能为力,因为设备厂商没有标准化,他们就没有强制义务来支持安卓API这种东西——当然谷歌的亲儿子Nexus是支持的。
这些都是基于相当的、规模的、日积月累的对比测试与人的交流得到的靠谱结论。
说了一大堆,这厮对软硬编码有没有整体的看法呢?那就是,市面上大部分安卓采用软编码是一种保险折衷的,同时也是一种稍显平庸的方案。对于“平庸”的理解,一来大家都这么干,依赖很多第三方库,比如无所不能的ffmpeg,还有各种莫名其妙的美颜,导致很多应用体积庞大,耗电量高(当然我也承认某些方案确实做了很多出色的优化,但远没有出色到令人稀奇的地步,大部分我都能看透是怎么一种手段,用了什么库)。相对而言硬编码是一种本质的、激进的,同时也是充满未知风险的方案。比如iOS你可以毫不犹豫地选择硬编码,因为苹果做得好(但也有发烫问题,原因同上),你几乎没有理由不选,省了很多开发;问题在于前面所述的硬件兼容性(实际上我告诉你最新的Android 6.1安装包都有ABI兼容问题,采用了OpenJDK的缘故,这个你肯定不知道吧,以后那些应用发行商要更加头疼了,一次编译到处运行,狡猾的谷记,呵呵呵呵……),所以这个问题只能走一步看一步,一不小心很可能是死刑。但也正因为如此,yasea选择开源,你可以不敢冒商业上的风险,但在开源上你仍然亦步亦趋,我认为这不值得付出这么多努力,因为背后你所能获得的信息和资源(甚至人脉),要远胜于一个只会在公司里闷头苦干拿工资的闷逼。
**生命在于体验,开源在于创新和冒险。**我也不能免俗,还是用鸡汤的方式作个结尾吧。
from yasea.
不错的项目,正在研究
看了下代码,能开源绝对要赞,提点建议:
- 用到了的开源代码,最好能保持源项目的目录结构和包名类名
- 如果对用到的开源项目做了修改,最好能 push 给上游,争取上游能合并自己的改动
这样开源才能越做越好。
from yasea.
great job!!!!!!!!!!!!!!!
from yasea.
继续努力
from yasea.
感谢作者分享精彩心路历程 。持续关注 yasea 。
from yasea.
Great Job!
from yasea.
那些大厂也是心机婊,亏的是我们这些开发者,人家没有义务来帮你做每一个需求,有些还很强硬
from yasea.
感谢分享,努力学习
from yasea.
感谢作者为开源做出的贡献。yasea加油!
from yasea.
Very Good.
from yasea.
Thinks
from yasea.
非常感谢!
from yasea.
佩服
from yasea.
请问yasea支持app后台推流、实时切换分辨率么?
from yasea.
建了yasea的群,群号:314547660。小问题我们可以在群里讨论,希望作者也可以加进来哈~!
from yasea.
谢谢分享,加油
from yasea.
楼主有没有碰到过
dequeueOutputBuffer
在部分机器上频繁上报
INFO_TRY_AGAIN_LATER?
from yasea.
@guohai 你把传给编码器的presentationTimeUs改成墙上时间试试。
from yasea.
@begeekmyfriend can you write down your answer in English :) ?
from yasea.
@gouravd It is the story about why and how I made yasea, difficult for me in English expression :P
from yasea.
MTK平台的Gallery2项目中有一个MediaCodecRecorder.java, 其中有用到MediaMuxer把音频和视频数据保存到文件, 即mMediaMuxer.writeSampleData(trackInfo.index, encodedData, bufferInfo);我想把这里的encodedData的视频数据推到服务器, 偿试了flvMuxer.writeSampleData(videoFlvTrack, encodedData, bufferInfo);可是数据并没有传到服务器, 我断点看了一下, 第次if (avc.is_sps(frame))和if (avc.is_pps(frame))都是不成立的, 所以没办法上传服务器, 请教一下,我要如何修改才能实现这个功能?
from yasea.
@llxxhm please open a new issue
from yasea.
@begeekmyfriend 已经新建了issue: #47, 其实我的诉求和#10 是一样的
from yasea.
ProfileLevel固定是BaseLine是因为Native写死了,不过可以通过调用隐藏API解决,问题是无法设置ReferenceFrame…
from yasea.
Now there is soft encoding with x264 in yasea!
from yasea.
good
from yasea.
谢谢
from yasea.
楼主威武!!
from yasea.
楼主威武!!我就是基于你的项目做得美颜功能。非常感谢。
from yasea.
将屏幕截图用MediaCodec进行编码的时候,同样遇到你说的这种问题。
第一个就是profile的问题。说是编码器内部写死baseline,找了不少资料,发现也有不少人提过这个问题。
但是在红米1上的测试结果。默认profile类型为high。
需要手工修改为baseline。
并且在红米1和魅族mx5上测试编码结果,完全无法实现流畅。
nexus5的效果确实出奇的好,魅族u10也是。
哎,说到底这定制过的系统在加上硬件不兼容带来的问题真是蛋疼的一b。
from yasea.
谢谢您的分享!
(1)我看项目有个CPP,此项目是有用到C++吗?
(2)与传统C++对比,效率如何呢?
from yasea.
非常感谢您的无私分享!我们也是在进行硬编码时碰到难以解决的兼容性问题打算使用软编码。但是用ffmpeg和x264编译Android平台so文件的时候碰到很多问题,没能成功编译。您可以分享一下相关经验吗?
from yasea.
楼主 请问一下publishType值设置为record或者append 服务端能直接录制吗 我用的fms4.5 是无法录制的
from yasea.
@kaedea 大佬,"ProfileLevel固定是BaseLine是因为Native写死了,不过可以通过调用隐藏API解决",请问这个隐藏api是什么,感谢
from yasea.
@lmylr 如果设备硬件不支持,你改了也白搭
from yasea.
@begeekmyfriend 这个没事,只要让部分硬件支持的设备能规避系统的限制就可以了,楼主知道那个隐藏api吗?
from yasea.
注意到已经支持软编码, 是不是意味着没有特别需要注意的地方,可以商用了?
from yasea.
本项目为免费开源,商用得失概不负责。
from yasea.
好的,谢谢分享,加油
from yasea.
哪位朋友能帮忙解惑:
1、MediaCodec 就是硬编码吗?
2、我看 yasea 支持硬编和软编的切换,是说 MediaCodec 也可以配置硬编和软编吗?
from yasea.
Related Issues (20)
- How to introduce it in Android Studio? HOT 1
- Can we use .acv file in filter? HOT 1
- Add APK to releases HOT 1
- 请问如何获取camera的流(帧)呢? HOT 1
- 请问如何无预览推流呢?
- 推屏幕 HOT 1
- 测试低带宽出现Network weak HOT 2
- 如何支持RTMPS HOT 4
- 小屏幕推流导致拉流清晰度低 HOT 6
- 推流成功几分钟后就闪退
- 空指针异常 HOT 3
- Error in decoding the stream when using Hardware Encoder HOT 2
- 华为meat40 pro中切换摄像头报错
- 安卓11和12框架使用问题
- Heavy pixelated video
- 推流界面处于onpause状态时怎么让摄像头继续采集数据 HOT 1
- Is Streaming possible over 5G? HOT 1
- Video streaming paused when screen locked HOT 1
- 收音问题 HOT 7
- 推流的视频很糊 HOT 1
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from yasea.