基于openVR实现任意软件界面映射到VR眼镜

原理:就是用openVR驱动各种类型的VR眼镜驱动,然后不断给指定软件截图用opengl渲染到VR眼镜

这个代码的功能了就是后天运行,创建udp广播,收到“close”命令就启动VR渲染,“start”就是关闭渲染

mian.cpp


 
 

#include "mainwindow.h"
#include <QApplication>
#include <QSurfaceFormat>
#include <QSettings>
#include<QProcess>
#include<QMessageBox>
#include<QMutex>
#include<QDateTime>
#include<QTextStream>
#include<QFile>
#include<QDir>
static bool FindDog(){
    QProcess proc;
    proc.start("tasklist -fi \"imagename eq QVRViewer.exe\"");
    proc.waitForFinished();
    QString tmp;
    tmp = tmp.prepend(proc.readAll());
    if(tmp.contains("Console")){
        int step = tmp.indexOf("Console");
        tmp = tmp.mid(step + 10);
        if(tmp.contains("Console"))
            return true;
    }
   return false;
}


void MessageOutPut(QtMsgType type, const QMessageLogContext &context, const QString &msg)
{
    static QMutex mutex;
    mutex.lock();
    QString text;
   switch(type)
   {
   case QtDebugMsg:
       text = QString("Debug:");
       break;

   case QtWarningMsg:
       text = QString("Warning:");
       break;

   case QtCriticalMsg:
       text = QString("Critical:");
       break;

   case QtFatalMsg:
       text = QString("Fatal:");
       break;
   default:
       break;
   }
   QString current_date_time = QDateTime::currentDateTime().toString("yyyy-MM-dd hh:mm:ss");
   QString message = QString("%1 %2%3").arg(current_date_time).arg(text).arg(msg);
   QFile file("log.txt");
   file.open(QIODevice::WriteOnly | QIODevice::Append);
   QTextStream text_stream(&file);
   text_stream << message << "\r\n";
   file.flush();
   file.close();
   mutex.unlock();

}

int main(int argc, char *argv[])
{
    QCoreApplication::setOrganizationName("Skeletonbrain");
    QCoreApplication::setOrganizationDomain("skeletonbrain.com");
    QCoreApplication::setApplicationName("QVRViewer");

    QSurfaceFormat glFormat;
    glFormat.setVersion(4, 1);
    glFormat.setProfile(QSurfaceFormat::CoreProfile);
//    glFormat.setSamples(0);
    glFormat.setSwapInterval(0);

    glFormat.setOption(QSurfaceFormat::DebugContext);

    QSurfaceFormat::setDefaultFormat(glFormat);

    QApplication a(argc, argv);
    qInstallMessageHandler(MessageOutPut);//安装日志
    if(FindDog()){
        QMessageBox box;
        box.setText("该程序已运行!");
        box.exec();
        return 0;
    }

    MainWindow w;
    w.show();
    w.move(-200,-200);

    return a.exec();
}

MainWindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include<QSystemTrayIcon>
#include <QMainWindow>
#include<QMenu>
#include<QAction>
#include<QTimer>
#include <QUdpSocket>

namespace Ui {
class MainWindow;
}

class VRView;

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();

private slots:
    void HandleClose();
    void FindWindownHwnd();
    void readPendingDatagrams();
private:
    Ui::MainWindow *ui;
    VRView *vr;
    QSystemTrayIcon *m_trayIcon;
    QMenu *mMenu;
    QAction *exitAction;
    QTimer * tim;
    QUdpSocket *udpSocket;
    QString AppName;
    int  Rport;
    void initSocket();
    void ReadConfig();

};

mainwindow.cpp

 
 
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "vrview.h"
#include"WinWnd.h"
#include <QVBoxLayout>
#include <QSurfaceFormat>
#include <QSettings>
#include <QFileDialog>
#include <QStandardPaths>
#include <QOffscreenSurface>
#include<QSettings>
#include<QMessageBox>
#include<QDebug>
#include<QWindow>
#include<QDesktopWidget>
MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    this->setWindowFlags(Qt::WindowStaysOnTopHint | Qt::FramelessWindowHint | Qt::ToolTip);
    m_trayIcon = new QSystemTrayIcon(this);
    m_trayIcon->setIcon(QIcon(":/viewer.ico"));     //设置图标
    mMenu = new QMenu(this);
    exitAction = new QAction(QStringLiteral("Exit"),this);
    mMenu->addAction(exitAction);
    m_trayIcon->setContextMenu(mMenu);
    connect(exitAction,SIGNAL(triggered(bool)),this,SLOT(HandleClose()));
    m_trayIcon->show();
    m_trayIcon->showMessage("tip","QVRViewer has started",QSystemTrayIcon::Information,1000);
    ReadConfig();
    vr = NULL;
    tim = new QTimer(this);
    tim->setInterval(100);
    connect(tim,SIGNAL(timeout()),this,SLOT(FindWindownHwnd()));
    initSocket();
    tim->start();
}

MainWindow::~MainWindow()
{
    if(tim->isActive())
        tim->stop();
    if(vr != NULL)
        delete vr;
    delete ui;
}

void MainWindow::HandleClose()
{
    QApplication::quit();
}

void MainWindow::FindWindownHwnd()
{
    int hwnd = GetWndFromPid(AppName.toLatin1().data());
    if(hwnd == 0)
        return;
//    qDebug()<<"find Window:"<<hwnd;

    if(vr == NULL){
       if(abs(QWindow::fromWinId(hwnd)->width() - QApplication::desktop()->width()) < 100){
           tim->stop();
           qDebug()<<"start vr"<<hwnd;
           vr = new VRView(hwnd,this);
           this->setCentralWidget(vr);
        }
    }
}

void MainWindow::readPendingDatagrams()
{

    if (udpSocket->hasPendingDatagrams()) {
        QByteArray datagram;
        datagram.resize(udpSocket->pendingDatagramSize());
        udpSocket->readDatagram(datagram.data(), datagram.size(), NULL,NULL);
        QString cmd = QString::fromLatin1(datagram);
        qDebug()<<cmd;
        if(cmd == "close"){
            tim->start();
        }else if(cmd == "start"){
            if(tim->isActive()) tim->stop();
            if(vr != NULL){
               delete vr;
               vr = NULL;
            }
        }else{
            QMessageBox box;
            box.setText("命令错误:"+cmd);
            box.exec();
        }
    }


}

void MainWindow::initSocket()
{
    udpSocket = new QUdpSocket(this);
    udpSocket->bind(QHostAddress::Any, Rport);
    connect(udpSocket, SIGNAL(readyRead()), this, SLOT(readPendingDatagrams()));
}

void MainWindow::ReadConfig()
{
//    QSettings settings("C:\\Users\\9DVR\\Desktop\\QVR\\config\\cutApp.ini",QSettings::IniFormat);
    QSettings settings("./config/cutApp.ini",QSettings::IniFormat);
    settings.beginGroup("cutApp");
    AppName = settings.value("appName").toString();
    Rport = settings.value("port").toInt();
    settings.endGroup();
    if(AppName.isEmpty() || Rport == 0){
            QMessageBox box;
            box.setText("配置文件格式错误");
            box.exec();
            this->close();
    }

}




完整代码下载地址:http://download.csdn.net/download/xzpblog/10039362

猜你喜欢

转载自blog.csdn.net/xzpblog/article/details/78349320