设为首页收藏本站|繁體中文

Project1

 找回密码
 注册会员
搜索
查看: 2481|回复: 5
打印 上一主题 下一主题

[随意闲聊] FFMPEG视屏播放0.5求测试

[复制链接]

Lv2.观梦者

傻♂逼

梦石
0
星屑
374
在线时间
1606 小时
注册时间
2007-3-13
帖子
6562

烫烫烫开拓者

跳转到指定楼层
1
发表于 2011-9-11 19:45:11 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

加入我们,或者,欢迎回来。

您需要 登录 才可以下载或查看,没有帐号?注册会员

x
本帖最后由 yangff 于 2011-9-12 00:44 编辑

= =技术区连只鸟都没有……
让我感觉压力很大所以就在水区又发了一份,求测试各种分辨率=v=
把分辨率和FPS一起丢上来吧0 0·
支持格式繁多,基本上你能找到的都支持,某些蛋疼的特殊格式除外
不具备实用价值,仅供参考,使用前请阅读LGPL的协议!
播放成功,原来那些奇怪的灰度或者是绿色黄色都正常了!!!
测试结果640*480以下都是满帧
800*600开始掉了
1024*768只能勉强用了
1200*720蛋都碎了
10000*10000你开的了这么大 的bitmap??
可以完美嵌入Bitmap
暂时不支持音轨。帧率自行协调
貌似最开头一段有点问题大概0.2s左右……?
DLL编译+演示下载(GUN C)
http://ftp.66rpg.com/yangff/RMPlayer.part1.rar
http://ftp.66rpg.com/yangff/RMPlayer.part2.rar

  1. class Font
  2. def marshal_dump;end
  3. def marshal_load(obj);end
  4. end
  5. class Bitmap
  6. # 传送到内存的API函数
  7. RtlMoveMemory_pi = Win32API.new('kernel32', 'RtlMoveMemory', 'pii', 'i')
  8. RtlMoveMemory_ip = Win32API.new('kernel32', 'RtlMoveMemory', 'ipi', 'i')
  9. def _dump(limit)
  10. data = "rgba" * width * height
  11. RtlMoveMemory_pi.call(data, address, data.length)
  12. [width, height, Zlib::Deflate.deflate(data)].pack("LLa*") # 压缩
  13. end
  14. def self._load(str)
  15. w, h, zdata = str.unpack("LLa*"); b = new(w, h)
  16. RtlMoveMemory_ip.call(b.address, Zlib::Inflate.inflate(zdata), w * h * 4); b
  17. end
  18. # [[[bitmap.object_id * 2 + 16] + 8] + 16] == 数据的开头
  19. #
  20. def address
  21. buffer, ad = "xxxx", object_id * 2 + 16
  22. RtlMoveMemory_pi.call(buffer, ad, 4); ad = buffer.unpack("L")[0] + 8
  23. RtlMoveMemory_pi.call(buffer, ad, 4); ad = buffer.unpack("L")[0] + 16
  24. RtlMoveMemory_pi.call(buffer, ad, 4);
  25. return buffer.unpack("L")[0]
  26. end
  27. end
  28. module RMPlayer
  29.   REG=Win32API.new("rmplayer","RegMovie","ip","i")
  30.   GNF=Win32API.new("rmplayer","NextFrame","ii","i")
  31.   CLM=Win32API.new("rmplayer","CloseMovie","ii","i")
  32.   def self.reg(a,s)
  33.     @a=a
  34.     @s=s
  35.     @h=REG.call(@a,s)
  36.   end
  37.   def self.next
  38.     GNF.call(@a,@h)
  39.   end
  40. end
  41. class RMP < Bitmap
  42.   def initialize(w,h,s)
  43.     super(w,h)
  44.     RMPlayer.reg(address,s)
  45.   end
  46.   def next
  47.     RMPlayer.next
  48.   end
  49. end
  50. @rmp=RMP.new(352,270,"haha.flv")
  51. @v=Viewport.new(0,0,640,480)
  52. @v.z=99
  53. @s=Sprite.new(@v)
  54. @s.z=99
  55. @s.bitmap=@rmp
  56. while true
  57.   @rmp.next
  58.   Graphics.update
  59. end
复制代码
  1. #ifndef INT64_C
  2. #define INT64_C(c) (c ## LL)
  3. #define UINT64_C(c) (c ## ULL)
  4. #endif

  5.         #include <Windows.h>
  6.         #include "libavutil/avstring.h"
  7.         #include "libavformat/avformat.h"
  8.         //#include "libavformat/rtsp.h"
  9.         #include "libavdevice/avdevice.h"
  10.         #include "libswscale/swscale.h"
  11.         #include "libavcodec/opt.h"
  12.         #include <libavcodec/avcodec.h>

  13. AVFormatContext *pFormatCtx;
  14. int          i, videoStream;
  15. AVCodecContext   *pCodecCtx;
  16. AVCodec       *pCodec;
  17. AVFrame       *pFrame;
  18. AVFrame       *pFrameRGB;
  19. int          numBytes;
  20. uint8_t       *buffer;


  21. int __declspec(dllexport) RegMovie(int pBitmap,char * src)
  22. {
  23.         avcodec_init() ;
  24.         av_register_all();
  25.         pFormatCtx = avformat_alloc_context();
  26.         if(av_open_input_file(&pFormatCtx,src, NULL, 0, NULL)!=0)return -1;// Couldn't open file
  27.         if(av_find_stream_info(pFormatCtx)<0) return -2;// Couldn't find stream information
  28.         //dump_format(pFormatCtx, 0, src, false);
  29.         videoStream=-1;
  30.         for(i=0; i<pFormatCtx->nb_streams; i++)
  31.        //if(&pFormatCtx->streams->codec.codec_type==CODEC_TYPE_VIDEO)
  32.            if ((pFormatCtx->streams[i]->codec->codec_type)==AVMEDIA_TYPE_VIDEO)
  33.        {
  34.          videoStream=i;
  35.          break;
  36.        }
  37.         if(videoStream==-1)
  38.                    return -3; // Didn't find a video stream
  39.         pCodecCtx=pFormatCtx->streams[videoStream]->codec;
  40.         pCodec=avcodec_find_decoder(pCodecCtx->codec_id);
  41.         if(pCodec==NULL)
  42.        return -4; // Codec not found
  43.         if(pCodec->capabilities & CODEC_CAP_TRUNCATED)
  44.        pCodecCtx->flags|=CODEC_FLAG_TRUNCATED;
  45.         if(avcodec_open(pCodecCtx, pCodec)<0)
  46.        return -5; // Could not open codec
  47.         pFrame=avcodec_alloc_frame();
  48.         pFrameRGB=avcodec_alloc_frame();
  49.         if(pFrameRGB==NULL)
  50.        return -6;
  51.                 // Determine required buffer size and allocate buffer
  52.         numBytes=avpicture_get_size(PIX_FMT_RGB24, pCodecCtx->width,
  53.                    pCodecCtx->height);
  54.         buffer=malloc(numBytes);//new uint8_t[numBytes];

  55.         // Assign appropriate parts of buffer to image planes in pFrameRGB
  56.         avpicture_fill((AVPicture *)pFrameRGB, buffer, PIX_FMT_RGB24,
  57.                    pCodecCtx->width, pCodecCtx->height);
  58.         return 0;
  59. }
  60. int GetNextFrame(AVFormatContext *pFormatCtx, AVCodecContext *pCodecCtx,
  61.    int videoStream, AVFrame *pFrame)
  62. {
  63.    static AVPacket packet;
  64.    static int      bytesRemaining=0;
  65.    //static uint8_t  *rawData;
  66.    static int fFirstTime=1;
  67.    int bytesDecoded;
  68.    int frameFinished;

  69. //  我 们第一次调用时,将 packet.data 设置为NULL指明它不用释放了
  70.    if(fFirstTime)
  71.    {
  72.        fFirstTime=0;
  73.        packet.data=NULL;
  74.    }

  75. // 解码直到成功解码完整的一帧
  76.    while(1)
  77.    {
  78.         //  除非解码完毕,否则一直在当前包中工作
  79.        while(bytesRemaining > 0)
  80.        {
  81.        //  解码下一块数 据
  82.            bytesDecoded=avcodec_decode_video2(pCodecCtx, pFrame,
  83.                &frameFinished, &packet);

  84.                // 出错了?
  85.            if(bytesDecoded < 0)
  86.            {
  87.                fprintf(stderr, "Error while decoding frame\n");
  88.                return 0;
  89.            }

  90.            bytesRemaining-=bytesDecoded;

  91.                // 我们完成当前帧了吗?接着我们返回
  92.            if(frameFinished)
  93.                return 1;
  94.        }

  95.        // 读取下一包,跳过所有不属于这个流的包
  96.        do
  97.        {
  98.            // 释放旧的包
  99.            if(packet.data!=NULL)
  100.                av_free_packet(&packet);

  101.            // 读取新的包
  102.            if(av_read_packet(pFormatCtx, &packet)<0)
  103.                goto loop_exit;
  104.        } while(packet.stream_index!=videoStream);

  105.        bytesRemaining=packet.size;
  106.    }

  107. loop_exit:

  108.        // 解码最后一帧的余下部分
  109.    bytesDecoded=avcodec_decode_video2(pCodecCtx, pFrame,
  110.                &frameFinished, &packet);

  111.        // 释放最后一个包
  112.    if(packet.data!=NULL)
  113.        av_free_packet(&packet);

  114.    return frameFinished!=0;
  115. }
  116. void frame(int iHeight,int iWidth,uint8_t *iYuvBuf,AVFrame *pFrame)
  117. {
  118.   int i,j,k;
  119.   for(i=0;i<iHeight;i++)
  120.       memcpy(iYuvBuf+iWidth*i, pFrame->data[0]+pFrame->linesize[0]*i,iWidth);
  121.   for(j=0;j<iHeight/2;j++)
  122.       memcpy(iYuvBuf+iWidth*i+iWidth/2*j,pFrame->data[1]+pFrame->linesize[1]*j,iWidth/2);
  123.   for(k=0;k<iHeight/2;k++)
  124.       memcpy(iYuvBuf+iWidth*i*2+iWidth/2*k, pFrame->data[2]+pFrame->linesize[2]*k, iWidth/2);
  125. }
  126. int __declspec(dllexport) NextFrame(int Bitmap,int playerHandle)
  127. {
  128.         int * pBitmap=(int *)Bitmap;
  129.         if (GetNextFrame(pFormatCtx, pCodecCtx, videoStream, pFrame))
  130.         {
  131.                 //struct SwsContext * img_convert_ctx;
  132.                 //img_convert_ctx=sws_getContext( pCodecCtx->width/12, pCodecCtx->height/12,PIX_FMT_RGB32,pCodecCtx->width,pCodecCtx->height,PIX_FMT_YUV420P,2,NULL,NULL,NULL);
  133.                 uint8_t *data = malloc (3*pCodecCtx->width*pCodecCtx->height);
  134.                 uint8_t *src[3]= {data, data+pCodecCtx->width*pCodecCtx->height, data+pCodecCtx->width*pCodecCtx->height+pCodecCtx->width*pCodecCtx->height};
  135.                 //int stride[3]={pCodecCtx->width, pCodecCtx->width, pCodecCtx->width};
  136.                 //sws_scale(img_convert_ctx,(const uint8_t*  const*)pFrame->data,pFrame->linesize,0,pCodecCtx->height,src,stride);
  137.                 int p=0;
  138.                 int r,g,b=0;
  139.                 double y,u,v;
  140.                 int off=pCodecCtx->width*pCodecCtx->height;
  141.                 int off1=pCodecCtx->width*pCodecCtx->height*1;
  142.                 frame(pCodecCtx->height,pCodecCtx->width,data,pFrame);
  143.                 //pBitmap[pCodecCtx->width*pCodecCtx->height-1]=0xffffaaff;
  144.             for (int i=pCodecCtx->height-1;i>=0;i--){
  145.                 for (int j=0;j<pCodecCtx->width;j++)
  146.                 {        //if (i*pCodecCtx->width+j<pCodecCtx->height*pCodecCtx->width)
  147.                         pBitmap[p]=0xff000000 ;
  148.                         y=(double)src[0][i*pCodecCtx->width+j];//pFrame->pp;//data[0][p+off];
  149.                     u=(double)src[1][(i/2*pCodecCtx->width+j)/2];//pFrame->pp;//data[0][p+off1];
  150.                         v=(double)src[2][(i/2*pCodecCtx->width+j)/2];//pFrame->pp//data[0][p+off1+off];
  151.                         r=(int)(1.164f*(y-16)+1.596f*(v-128));
  152.                         g=(int)(1.164f*(y-16)-0.813f*(v - 128) - 0.391f*(u - 128));
  153.                         b=(int)(1.164f*(y-16)+2.018f*(u - 128));
  154.                         if (r>255) r=255; if (r<0) r=0;
  155.                         if (g>255) g=255; if (g<0) g=0;
  156.                         if (b>255) b=255; if (b<0) b=0;
  157.                         pBitmap[p]|= b; //b
  158.                         pBitmap[p]|= g << 8; // g
  159.                         pBitmap[p]|= r << 16; // r
  160.                         // | data[((j+i*pCodecCtx->width+pCodecCtx->width*pCodecCtx->height) << 8)];// | data[((j+i*pCodecCtx->width+pCodecCtx->width*pCodecCtx->height*2) << 16)] | (0xff << 24);
  161.                         p++;
  162.                 }}
  163.                 free(data);
  164.                 return 1;        }
  165.                
  166.         return -1;
  167. }
  168. int __declspec(dllexport) CloseMovie(int pBitmap,int playerHandle)
  169. {

  170. }
复制代码
哎呀,蛋疼什么的最有爱了

Lv5.捕梦者 (管理员)

老黄鸡

梦石
0
星屑
42365
在线时间
7600 小时
注册时间
2009-7-6
帖子
13506

开拓者贵宾

2
发表于 2011-9-11 22:28:57 | 只看该作者
你妹的乱触。
回复 支持 反对

使用道具 举报

Lv2.观梦者

梦石
0
星屑
275
在线时间
1373 小时
注册时间
2005-10-16
帖子
5113

贵宾

3
发表于 2011-9-11 22:32:04 | 只看该作者
代码为什么少了第一行

点评

class Font……手滑  发表于 2011-9-11 23:35
我只个搬答案的
叔叔我已经当爹了~
婚后闪人了……
回复 支持 反对

使用道具 举报

Lv2.观梦者

傻♂逼

梦石
0
星屑
374
在线时间
1606 小时
注册时间
2007-3-13
帖子
6562

烫烫烫开拓者

4
 楼主| 发表于 2011-9-12 00:44:41 | 只看该作者
更新范例……附带奇妙的福利
哎呀,蛋疼什么的最有爱了
回复 支持 反对

使用道具 举报

Lv1.梦旅人

梦石
0
星屑
59
在线时间
536 小时
注册时间
2010-6-20
帖子
1489
5
发表于 2012-12-15 18:07:10 | 只看该作者
这是什么?VX视频播放器?

点评

挖坟……  发表于 2012-12-15 18:13

评分

参与人数 1星屑 -30 收起 理由
Password -30 把什么时候的老坟挖出来了…….

查看全部评分

[url=http://rpg.blue/thread-329159-1-1.html]http://attach.66rpg.com/bbs/attachment/forum/201308/24/132414sa8au7zgh7ab21gx.png[/url]   [b]
无尽之旅--永无止尽的旅程。[/b]
回复 支持 反对

使用道具 举报

Lv3.寻梦者

伴侣:北岛谜烟

梦石
0
星屑
3012
在线时间
3547 小时
注册时间
2012-8-7
帖子
12181

贵宾

6
发表于 2012-12-15 18:14:18 | 只看该作者
{:2_273:}播放器,快播 {:2_251:}
本人收不到提醒(点评|回复|@人),总之有事情到空间留言一起普通普通
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册会员

本版积分规则

拿上你的纸笔,建造一个属于你的梦想世界,加入吧。
 注册会员
找回密码

站长信箱:[email protected]|手机版|小黑屋|无图版|Project1游戏制作

GMT+8, 2024-11-19 01:52

Powered by Discuz! X3.1

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表