自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+

qq_33588386的博客

从事于Windows客户端开发(音视频方向)

  • 博客(42)
  • 资源 (4)
  • 收藏
  • 关注

原创 用QT自带的QMediaPlayer写一个音乐播放器

直接上代码头文件#pragma once#include <QObject>class QMediaPlayer;class QMediaPlaylist;#define SfPlayer MusicPlayer::GetInstance()class MusicPlayer : public QObject{ Q_OBJECTprivate: MusicPlayer(QObject *parent = nullptr);public: ~MusicPlaye

2022-01-26 17:31:28 829

原创 写一个QTAV的音乐播放器

关于QTAV的介绍和编译请看我之前的文章,直接上代码因为音乐播放器只有一个所以是个单例头文件:#pragma once#include <QObject>#include <QtAV/AVPlayer.h>#include <QtAVWidgets/GLWidgetRenderer2.h>using namespace QtAV;#define avplayer QtavPlayer::getInstance()class QtavPlayer :

2022-01-26 17:27:31 2235

原创 C语言 strcpy和memcpy源码实现

一、memcpy三个函数在使用过程中,均需包含以下头文件://在C中#include <string.h>//在C++中#include <cstring>二、memcpy函数是C/C++中的内存拷贝函数,它的功能是从源src所指的内存地址的起始位置开始,拷贝n个字节到目标dst所指的内存地址的起始位置中。实现如下: void* memcpy(void *dst,const void *src,size_t count) { void* ret = dst

2021-11-29 10:52:35 2475

原创 OpenCV读取视频文件

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-15 09:59:11 147

原创 OpenCV读取摄像头

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 13:54:19 1269

原创 OpenCV图像合并

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 13:51:48 856

原创 Opencv图像旋转

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 13:50:42 1255

原创 OpenCV两张图像融合

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 13:48:40 1392

原创 OpenCV图像金字塔

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 13:45:08 1004

原创 OpenCV重置图片大小尺寸

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 13:37:28 1468

原创 OpenCV调整对比度和亮度(自己实现和api实现)以及性能对比

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 11:49:00 655

原创 OpenCV二进制阈值化以及反二进制阈值化

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 11:45:32 1113

原创 OpenCV转灰度图(自己实现和api实现两种)以及性能对比

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>#include <opencv2/imgproc.hpp>#include <iostream>using namespace cv;using namespace std;void PrintMs(const char *text = ""){ sta

2021-11-12 11:42:42 865

原创 OpenCV裁剪图片

#include <opencv2/core.hpp>#include <opencv2/imgcodecs.hpp>#include <opencv2/highgui.hpp>using namespace cv;int main(int argc, char *argv[]){ Mat src = imread("1.png");// 图片路径 Rect rect(100, 100, 200, 200); Mat roi = src(rect);

2021-11-12 11:33:50 1058

原创 C++智能指针 shared_ptr

为了解决C++内存泄漏的问题,C++11引入了智能指针(Smart Pointer)。智能指针的原理是,接受一个申请好的内存地址,构造一个保存在栈上的智能指针对象,当程序退出栈的作用域范围后,由于栈上的变量自动被销毁,智能指针内部保存的内存也就被释放掉了(除非将智能指针保存起来)。C++11提供了三种智能指针:std::shared_ptr, std::unique_ptr, std::weak_ptr,使用时需添加头文件。shared_ptr使用引用计数,每一个shared_ptr的拷贝都指向相同的

2021-11-08 14:47:16 176

原创 OBS技术交流群

有喜欢OBS开源技术的加群

2021-10-15 15:57:03 905 1

转载 C++ 四种类型转换

众所周知C++关于类型转换引入了四种方式:1、static_cast2、const_cast3、dynamic_cast4、reinterpret_cast1、为什么要引入这几种类型转换,它与C语言中的强制类型转换有什么区别?2、这四种类型转换分别应用在什么场景?我们都知道C++完全兼容C语言,C语言的转换方式很简单,可以在任意类型之间转换,但这也恰恰是缺点,因为极其不安全,可能不经意间将指向const对象的指针转换成非const对象的指针,可能将基类对象指针转成了派生类对象的指针,这种转换很

2021-04-14 19:50:59 157

转载 C++ 友元类和友元函数详解

私有成员只能在类的成员函数内部访问,如果想在别处访问对象的私有成员,只能通过类提供的接口(成员函数)间接地进行。这固然能够带来数据隐藏的好处,利于将来程序的扩充,但也会增加程序书写的麻烦。C++ 是从结构化的C语言发展而来的,需要照顾结构化设计程序员的习惯,所以在对私有成员可访问范围的问题上不可限制太死。C++ 设计者认为, 如果有的程序员真的非常怕麻烦,就是想在类的成员函数外部直接访问对象的私有成员,那还是做一点妥协以满足他们的愿望为好,这也算是眼前利益和长远利益的折中。因此,C++ 就有了友元(fr

2021-03-31 15:42:16 328

转载 音视频 pts dts基本概念及理解

视频的播放过程可以简单理解为一帧一帧的画面按照时间顺序呈现出来的过程,就像在一个本子的每一页画上画,然后快速翻动的感觉。但是在实际应用中,并不是每一帧都是完整的画面,因为如果每一帧画面都是完整的图片,那么一个视频的体积就会很大,这样对于网络传输或者视频数据存储来说成本太高,所以通常会对视频流中的一部分画面进行压缩(编码)处理。由于压缩处理的方式不同,视频中的画面帧就分为了不同的类别,其中包括:I 帧、P 帧、B 帧。I、P、B 帧I 帧、P 帧、B 帧的区别在于:I 帧(Intra coded fr

2021-03-31 13:46:08 1132

原创 OBS源码分析(十一)怎么在OBS添加QT库,比如:Network、Multimedia

一、在进行OBS二次开发的时候难免要添加QT的一些库,而OBS是在VS中开发的,程序每次更新之后都要重新进行配置很麻烦,所以在此记录一下二、在UI模块中找到CMakeLists.txt文件并打开,添加find_package包和链接库,如下图:然后添加链接库三、修改完之后保存编译并选择全部重新加载...

2021-03-18 18:15:17 864

原创 C++ 虚继承详解

多继承(Multiple Inheritance)是指从多个直接基类中产生派生类的能力,多继承的派生类继承了所有父类的成员。尽管概念上非常简单,但是多个基类的相互交织可能会带来错综复杂的设计问题,命名冲突就是不可回避的一个。多继承时很容易产生命名冲突,即使我们很小心地将所有类中的成员变量和成员函数都命名为不同的名字,命名冲突依然有可能发生,比如典型的是菱形继承,如下图所示:类 A 派生出类 B 和类 C,类 D 继承自类 B 和类 C,这个时候类 A 中的成员变量和成员函数继承到类 D 中变成了两份,

2021-02-08 13:54:37 2519 3

原创 OBS插件分享(一)

最近有一个需求,就是想把OBS中的某一个源的音频单独输出到一个独立的声卡,于是在Github上找到了一个现成的插件,现在把它分享给大家!1、这个插件是以滤镜的方式加载在OBS中的。如图2、编译方式源码地址:https://github.com/exeldro/obs-audio-monitor编译步骤:(1)建立OBS Studio:https://obsproject.com/wiki/Install-Instructions(2)将此存储库签出到UI / frontend-plugins

2021-02-07 13:56:10 2353

原创 OBS源码分析(十)-滤镜的创建

一、OBS的滤镜都是以插件的方式去加载的,对应的OBS项目工程是:二、滤镜的创建过程1、右击选择的源void OBSBasic::on_sources_customContextMenuRequested(const QPoint &pos){ if (ui->scenes->count()) { QModelIndex idx = ui->sources->indexAt(pos); CreateSourcePopupMenu(idx.row(), fal

2021-02-02 11:15:30 1547

原创 OBS源码分析(九)-窗口视频预览

最近接了个需求,要在源列表的每个源进行视频预览类似如下图:一、OBS所有的视频预览包括主窗口的预览都是继承OBSQTDisplay这个类。在SourceTreeItem构造函数中添加以下代码 // 预览窗口 play = new OBSQTDisplay(); play->setFixedWidth(100); auto addDrawCallback = [this]() { obs_display_add_draw_callback(play->GetDisplay(),

2021-02-02 10:27:49 1726 5

原创 c++ 11 lambda表达式

lambda的申明方式Lambda表达式是c++11的新特性,它允许程序员在函数内部创建一个匿名函数,对于一些小型的功能模块,可以使用lambda表达式来实现。很多其他语言已经有了lambda表达式,比如objective-c中block就类似。Lambda表达式的声明方式:例如:auto fadd = [](int a, int b){ return a + b;};Fadd就是一个匿名函数,后面是它的实现,auto是自动类型,也是c++11新加入的特性,auto可以自动判断.

2021-02-01 16:02:12 173 3

转载 OBS源码分析(八)分析libobs几个主要的线程

最近一段时间再看OBS的几个重要的线程,通过不断的学习和结合一些大佬的博客终于相对搞明白了这几个线程,分别是采集渲染线程和编码线程,分析如下:struct obs_core_video几个关键变量的注释:// 主画布 渲染当前场景下sources的画布 // 渲染主窗口的窗口时 直接把这个纹理贴到display中gs_texture_t *render_texture; // output画布 如果直播录像时的宽高(output宽高)和主画布宽高不一样,// 需要在该画布上对render

2021-01-13 11:38:16 2108 1

原创 C++ 11智能指针-unique_ptr

一、前言c++的内存管理是让很多人头疼的事,当我们写一个new语句时,一般就会立即把delete语句直接也写了,但是我们不能避免程序还未执行到delete时就跳转了或者在函数中没有执行到最后的delete语句就返回了,如果我们不在每一个可能跳转或者返回的语句前释放资源,就会造成内存泄露。使用智能指针可以很大程度上的避免这个问题,因为智能指针就是一个类,当超出了类的作用域是,类会自动调用析构函数,析构函数会自动释放资源二、应用unique_ptr 由 C++11 引入,旨在替代不安全的 auto_ptr

2021-01-11 18:11:35 231

原创 C++ 线程同步---信号量

最近一直在学习OBS源码,遇到很多多线程的知识,也算是恶补了一下之前没搞明白一直没机会用的信号量。一、相关的函数和头文件介绍//头文件#include <windows.h>//创建信号量APIHANDLE WINAPI CreateSemaphore( _In_opt_ LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,//指向SECURITY_ATTRIBUTES的指针; _In_ LONG lI

2021-01-07 17:02:31 337 1

原创 C++ 11新特性nullptr和NULL的区别

nullptr是c++11中的关键字,表示空指针要区分nullptr和NULL,首先要明白NULL的含义:NULL是一个宏定义,在c和c++中的定义不同,c中NULL为(void*)0,而c++中NULL为整数0//C语言中NULL定义#define NULL (void*)0 //c语言中NULL为void类型的指针,但允许将NULL定义为0//c++中NULL的定义#ifndef NULL#ifdef _cpluscplus

2021-01-07 15:17:54 247 1

原创 C语言如何支持面向对象编程

一、函数指针函数指针是个普通的指针,但是写法略不同于一般的指针,二、如何定义函数在结构体外定义,例如:// 原函数int add(int a, int b) {return a + b;}定义函数指针,例如:// 指向原函数的函数指针int (*p)(int x, int y);可以看到,关键字:​ 1. 返回值类型必须相同​ 2. 指针变量名要用()括起来​ 3. 除形参名外,参数列表必须相同赋值,将指针指向函数(不要忘了这一步)// 直接将函数名赋值给指针// 函数名就

2021-01-06 13:49:57 410 1

原创 qt creator搭建ffmpeg开发环境

一、ffmpeg第三方开发库的下载ffmpeg官网和之前有了很大变化 如下图:点击下载二、环境配置新建一个qt creator 项目,在项目根目录下新建ffmpeg文件夹,里面是include和lib文件夹,如图:在Pro文件添加这两行代码如图:然后qmake三、测试是否搭建成功我新建的项目是widget项目#include "widget.h"#include "ui_widget.h"#include <QDebug>extern "C"{ #i

2021-01-04 17:05:40 294

原创 QTAV的编译

QTAV官网这样说的:QtAV 是一个基于 Qt 和 FFmpeg 的跨平台、高性能多媒体播放框架,能够帮助你轻而易举地编写出一个播放器。以下是QTAV的官网地址:官网地址:http://www.qtav.org/Github 地址:https://github.com/wang-bin/QtAV编译 QtAV:https://github.com/wang-bin/QtAV/wiki/Build-QtAV在项目中使用 QtAV:https://github.com/wang-bin/QtAV/w

2021-01-04 10:36:49 403

原创 C++ 函数指针与回调函数

最近在研究OBS源码在源码中作者大量应用了函数指针和回调函数的这种方式,这种方式代码的可读性和效率有了很大的提高。一、函数指针的介绍函数指针:指向函数的指针变量。 因此“函数指针”本身首先应是指针变量,只不过该指针变量指向函数。这正如用指针变量可指向整型变量、字符型、数组一样,这里是指向函数。如前所述,C在编译时,每一个函数都有一个入口地址,该入口地址就是函数指针所指向的地址。有了指向函数的指针变量后,可用该指针变量调用函数,就如同用指针变量可引用其他类型变量一样,在这些概念上是大体一致的。函数指针有两

2020-12-31 14:48:52 276 2

原创 OBS源码学习(七)-源的创建

当用户点击添加源时,OBS会弹出相应的源列表。代码如下:void OBSBasic::AddSourcePopupMenu(const QPoint &pos){ if (!GetCurrentScene()) { // Tell the user he needs a scene first (help beginners). OBSMessageBox::information( this, QTStr("Basic.Main.AddSourceHelp.Title"),

2020-12-29 11:17:55 869

原创 设置QWidget可移动可改变大小可取消菜单栏的公共程序

一、NcFramelessHelper.h//Version 3.0.0#ifndef NC_FRAMELESS_HELPER_H#define NC_FRAMELESS_HELPER_H#include <QObject>class NcFramelessHelperImpl;class NcFramelessHelper : public QObject{public: explicit NcFramelessHelper( QObject* parent =

2020-12-17 16:45:11 842 1

原创 OBS源码学习(六)-将当前视频画面推流到两个不同的RTMP服务器上

一、OBS本身的推流方法在OBS设置好推流地址后保存并应用地址点击保存之后会调用SaveStream1Settings函数void OBSBasicSettings::SaveStream1Settings(){ bool customServer = IsCustomService(); const char *service_id = customServer ? "rtmp_custom" : "rtmp_common"; obs_service_t *oldService = mai

2020-12-17 15:32:51 1095

原创 OBS源码学习(五)-将OBS自动更新功能迁移到公司自己的服务器上

一、实现自己运行程序的manifest.jsonstatic void GenerateJson(string path){ //path = "D:\\OBSUpdate\\obs-studio\\build\\rundir\\Release"; string runDirPath = path; char *p = const_cast<char *>(path.c_str()); fileSearch(p); //生成hash值 std::map<string, s

2020-12-17 11:17:55 858 1

转载 一文读懂 YUV 的采样与格式

YUV 是一种颜色编码方法,和它等同的还有 RGB 颜色编码方法。RGB 颜色编码RGB 三个字母分别代表了 红(Red)、绿(Green)、蓝(Blue),这三种颜色称为 三原色,将它们以不同的比例相加,可以产生多种多样的颜色。在图像显示中,一张 1280 * 720 大小的图片,就代表着它有 1280 * 720 个像素点。其中每一个像素点的颜色显示都采用 RGB 编码方法,将 RGB 分别取不同的值,就会展示不同的颜色。RGB 图像中,每个像素点都有红、绿、蓝三个原色,其中每种原色都占用 8

2020-12-17 10:30:17 185 2

原创 OBS源码学习(四)-插件模块加载流程

一、OBS Studio在架构上采用的是微内核+插件的形式开发的,至于微内核的介绍请自行百度。OBS开源社区这样写的目的是为了提高项目的可维护性,也让新功能的扩展变得更加简单,OBS内部开发了一些常用的插件如下图:在OBS启动初始化void OBSBasic::OBSInit()时,会调用AddExtraModulePaths函数,这个函数的目的是设置插件的路径static void AddExtraModulePaths(){ char base_module_dir[512];#if defi

2020-12-16 11:05:30 3225 9

原创 OBS源码学习(三)-编译updater工程

由于项目要求要将OBS更新功能迁到公司自己的服务器上,OBS默认的是不编译updater工程,现将OBS更新工程编译步骤如下:一、下载解压并使用 CMake 生成编译 zlib https://download.csdn.net/download/XiaoStore/12315404二、编译版本 obs-studio-26.0.8三、CMake 生成配置文件时去掉勾选 DISABLE_UPDATE_MODULE四、添加环境变量 STATIC_ZLIB_PATH D:\OBSUpdate\zlib五

2020-12-15 18:05:13 505 1

QCefView源码编译以及demo的实现

本资源主要是利用源码编译QCefView,然后利用QCefView写了一个小demo,里面的工程直接可以打开编译运行都是现成的,其中QCefView-master文件夹是对QCefView源码的编译,Cef文件夹是对QCefView做得demo

2020-12-18

QT/C++实时获取CPU和内存的使用率

本资源能获取电脑的CPU和内存的使用率,也能够跨平台使用包括Windows、macOS、Linux,调用方法简单,里面是一个pri文件,直接可以加在自己的工程里面,调用方法有说明

2020-12-17

很全的音视频学习资料

本资料包括FFmpeg、H264、音视频编解码的pdf,比如:音视频编解码详解.pdf、多媒体技术基础.pdf、新一代视频压缩编码标准H.264.pdf、RTMP协议规范(中文翻译).pdf等等,资料比较各个等级的开发。

2020-12-17

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除