JS和C++之间的相互访问

[Qt] 利用QtWebKit完成JavaScript访问C++对象 简介           在浏览器扩展或者WebApp的项目经常用的脚本语言javascript有很多局限性,比如,javascript语言不能够夸窗口访问js对象,不能直接读写磁盘文件(这个也正是发明人设计的安全机制吧,要不然,谁还敢用浏览器啊,几行代码就可以把你偷窥的一览无余),我们可能在我们的程序中需要扩展这个功能。 那么,我们怎么解决这些问题呢?或许你可以参考一下下面的设计架构 阅读详情

      最近,工作需要,实现了JS与C++之间的相互访问。核心思想是通过一个隐藏域作为中转。JS发送数据给C++时,将数据写往某个隐藏域,同时C++每隔一段时间(如40ms)检测一次此域可有数据,有的话取出进行相关操作后清空。C++发送数据给JS时,将数据写往另外一个隐藏域后,直接使用COM触发某个隐藏Button的click事件,由它进行相关的操作。具体代码如下:

//File: WebNativeCall.js
var g_strInCommPortId = null;
var g_strOutCommPortId = null;
var g_strInCommCmdId = null;
var g_funcCallIn = null;

var funcOnLoad = function() {
    if (g_strInCommPortId != null && g_strOutCommPortId != null
    && g_strInCommCmdId != null && g_funcCallIn != null) {
        var txtInCommPort = document.createElement("input");
        txtInCommPort.setAttribute("type", "hidden");
        txtInCommPort.setAttribute("id", g_strInCommPortId);
        txtInCommPort.setAttribute("name", g_strInCommPortId);
        txtInCommPort.setAttribute("value", "");
        document.body.appendChild(txtInCommPort);

        var txtOutCommPort = document.createElement("input");
        txtOutCommPort.setAttribute("type", "hidden");
        txtOutCommPort.setAttribute("id", g_strOutCommPortId);
        txtOutCommPort.setAttribute("name", g_strOutCommPortId);
        txtOutCommPort.setAttribute("value", "");
        document.body.appendChild(txtOutCommPort);

        var btnInCommCmd = document.createElement("input");
        btnInCommCmd.setAttribute("type", "button");
        btnInCommCmd.style.setAttribute("display", "none");
        btnInCommCmd.setAttribute("id", g_strInCommCmdId);
        btnInCommCmd.setAttribute("name", g_strInCommCmdId);
        btnInCommCmd.onclick = function() {
            var data = document.getElementById(g_strInCommPortId).value;
            if (data != null && data != "") {
                g_funcCallIn(document.getElementById(g_strInCommPortId).value);
            }
        };
        document.body.appendChild(btnInCommCmd);
    };
};

if (window.addEventListener) {
    window.addEventListener("load", funcOnLoad, false);
}
else if (window.attachEvent) {
    window.attachEvent("onload", funcOnLoad);
}

function funcCallOut(strData)
{
    document.getElementById(g_strOutCommPortId).value = strData;
}


//File: Test.html
<html>
    <head>
        <title>Test the Commucation between C++ and JS</title>
        <script type="text/javascript" language="javascript" src="WebNativeCall.js"></script>
        <script type="text/javascript" language="javascript">
            g_strInCommPortId = "txtInCommPort";
            g_strOutCommPortId = "txtOutCommPort";
            g_strInCommCmdId = "btnInCommCmd";
           
            g_funcCallIn = function(CommData) {
                alert("Web Receive Data: " + CommData);
            }

            function TestCallOut() {
                funcCallOut(document.getElementById("txtOutData").value);
            }
        </script>
    </head>
    <body>
        <input type="text" id="txtOutData" name="txtOutData" value="" />
        <input type="button" id="btnCallOut" name="btnCallOut" value="CallOut" onclick="TestCallOut();" />   
    </body>
</html>


//File: VisitHtmlTool.h
/***************************************************************************

* 功能  : 网页本地访问类
* 输入参数 : 无
* 输出参数 : 无
* 返回值 : 无

***************************************************************************/
class CVisitHtmlTool               //网页本地访问类
{
public:
 typedef void (* Func_CallOut)(LPCTSTR lpszData);

 CVisitHtmlTool(CHtmlView *pHtmlView, LPCTSTR lpszInCmdTagId
  , LPCTSTR lpszInDataTagId, LPTSTR lpszOutDataTagId
  , Func_CallOut pCallOut);
 ~CVisitHtmlTool(void);

 BOOL CallIn(LPCTSTR lpszData);            //向网页发数据
 VOID StartReceive();              //开始自动接收数据
 VOID StopReceive();               //停止自动接收数据
 
protected:
 static DWORD WINAPI ReceiveThread(LPVOID lpThreadParameter);
 static LRESULT CALLBACK WindowSubSolve(HWND hWnd, UINT iMsg, WPARAM wParam
  , LPARAM lParam);

 CHtmlView *m_pHtmlView;              //HtmlView指针
 LPCTSTR m_lpszInCmdTagId;             //Web端数据接收触发器标识
 LPCTSTR m_lpszInDataTagId;             //Web端接收数据保存控件标志
 LPTSTR m_lpszOutDataTagId;             //Web端发送数据保存控件标志
 
 IHTMLElement* m_pEle;              //CallOut的数据结点

 Func_CallOut m_pCallOut;             //本地端接收数据回调函数

private:
 HANDLE m_hLock;

 BOOL m_bStarted;
 WNDPROC m_pOldProc;
 LONG m_pUserData;
};


//File: VisitHtmlTool.cpp
#include "StdAfx.h"
#include "VisitHtmlTool.h"

#define WM_PUMPCALLOUTDATA (WM_USER+1)

CVisitHtmlTool::CVisitHtmlTool(CHtmlView *pHtmlView,
          LPCTSTR lpszInCmdTagId ,
          LPCTSTR lpszInDataTagId,
          LPTSTR lpszOutDataTagId,
          Func_CallOut pCallOut)
{
 m_pOldProc = NULL;
 m_pUserData = NULL;
 m_hLock = ::CreateEvent(NULL, FALSE, TRUE, NULL);

 m_bStarted = FALSE;
 m_pCallOut = pCallOut;

 m_pHtmlView = pHtmlView;
 m_lpszInCmdTagId = lpszInCmdTagId;
 m_lpszInDataTagId = lpszInDataTagId;
 m_lpszOutDataTagId = lpszOutDataTagId;
 m_pEle = NULL;
}

CVisitHtmlTool::~CVisitHtmlTool(void)
{
 StopReceive();
 ::CloseHandle(m_hLock);

 if(m_pEle)
 {
  m_pEle->Release();
  m_pEle = NULL;
 }
}

BOOL CVisitHtmlTool::CallIn(LPCTSTR lpszData)
{
 IDispatch* pDis = NULL;
 IHTMLElement* pEle = NULL;
 IHTMLElement* pEleBody = NULL; 
 IHTMLDocument2 *pDoc = NULL;
 IHTMLElementCollection* pAllCollection = NULL;
 IHTMLElementCollection* pBodyCollection = NULL;

 LONG lLength = 0;
 BSTR bstrTmp;

 WaitForSingleObject(m_hLock, INFINITE);

 if((pDoc=(IHTMLDocument2 *)m_pHtmlView->GetHtmlDocument()) == NULL)
 {
  SetEvent(m_hLock);
  return FALSE;
 }

 pDoc->get_body(&pEleBody);
 if (pEleBody == NULL)
 {
  SetEvent(m_hLock);
  return FALSE;
 }

 BOOL bRet = FALSE;
 pEleBody->get_children(&pDis);
 pDis->QueryInterface(IID_IHTMLElementCollection, (void**)&pBodyCollection);
 pDis->Release();
 pEleBody->Release();
 pBodyCollection->get_length(&lLength);

 for (int i = 0; i < lLength; i++)
 {
  pBodyCollection->item(_variant_t(i), _variant_t(0), &pDis);
  pDis->QueryInterface(IID_IHTMLElement, (void**)&pEle);
  pDis->Release();
  pEle->get_id(&bstrTmp);
  
  if(!lstrcmp(m_lpszInDataTagId, bstrTmp))
  {
   pEle->setAttribute(BSTR(TEXT("value")), _variant_t(lpszData));
   ::SysFreeString(bstrTmp);
   pEle->Release();
   bRet = TRUE;
  }
  else if(!lstrcmp(m_lpszInCmdTagId, bstrTmp))
  {
   pEle->click();
   break;
  }
  else
  {
   pEle->Release();
   ::SysFreeString(bstrTmp);
  }
 }

 pBodyCollection->Release();
 SetEvent(m_hLock);
 return bRet;
}

VOID CVisitHtmlTool::StartReceive()
{
 if(m_bStarted)
 {
  return;
 }

 m_bStarted = TRUE;
 m_pUserData = ::SetWindowLong(m_pHtmlView->GetSafeHwnd(), GWL_USERDATA, (LONG)this);
 m_pOldProc = (WNDPROC)::SetWindowLong(m_pHtmlView->GetSafeHwnd(), GWL_WNDPROC, (LONG)WindowSubSolve);

 ::CreateThread(NULL, 0, ReceiveThread, this, 0, NULL);
}

VOID CVisitHtmlTool::StopReceive()
{
 if(!m_bStarted)
 {
  return;
 }

 m_bStarted = FALSE;
 while(!m_bStarted)
 {
  SleepEx(100, TRUE);
 }
 ::SetWindowLong(m_pHtmlView->GetSafeHwnd(), GWL_WNDPROC, (LONG)m_pOldProc);
 ::SetWindowLong(m_pHtmlView->GetSafeHwnd(), GWL_USERDATA, m_pUserData);
 m_bStarted = FALSE;
}

DWORD WINAPI CVisitHtmlTool::ReceiveThread(LPVOID lpThreadParameter)
{
 CVisitHtmlTool *pThis = reinterpret_cast<CVisitHtmlTool *>(lpThreadParameter);

 while(pThis->m_bStarted)
 {
  SleepEx(40, TRUE);
  pThis->m_pHtmlView->PostMessage(WM_PUMPCALLOUTDATA);
 }

 pThis->m_bStarted = TRUE;
 return 0;
}

LRESULT CALLBACK CVisitHtmlTool::WindowSubSolve(HWND hWnd,
            UINT iMsg,
            WPARAM wParam,
            LPARAM lParam)
{
 CComVariant varData;
 CVisitHtmlTool *pThis = reinterpret_cast<CVisitHtmlTool *>(::GetWindowLong(
  hWnd, GWL_USERDATA));

 if(iMsg != WM_PUMPCALLOUTDATA)
 {
  return CallWindowProc(pThis->m_pOldProc, hWnd, iMsg, wParam, lParam);
 }

 if(WaitForSingleObject(pThis->m_hLock, 0) == WAIT_TIMEOUT)
 {
  return 0;
 }

 if(pThis->m_pEle==NULL
  || pThis->m_pEle->getAttribute(CComBSTR(TEXT("value")), 0, &varData)!=S_OK)
 {
  IDispatch* pDis = NULL;       
  IHTMLElement* pEle = NULL;
  IHTMLElement* pEleBody = NULL; 
  IHTMLDocument2 *pDoc = NULL;
  IHTMLElementCollection* pAllCollection = NULL;
  IHTMLElementCollection* pBodyCollection = NULL;

  LONG lLength = 0;
  BSTR  bstrTmp;

  if((pDoc=(IHTMLDocument2 *)pThis->m_pHtmlView->GetHtmlDocument()) == NULL)
  {
   SetEvent(pThis->m_hLock);
   return 0;
  }

  pDoc->get_body(&pEleBody);
  if (pEleBody == NULL)
  {
   SetEvent(pThis->m_hLock);
   return 0;
  }

  pEleBody->get_children(&pDis);
  pDis->QueryInterface(IID_IHTMLElementCollection, (void**)&pBodyCollection);
  pDis->Release();
  pEleBody->Release();
  pBodyCollection->get_length(&lLength);
  pThis->m_pEle = NULL;

  for (int i = 0; i < lLength; i++)
  {
   pBodyCollection->item(_variant_t(i), _variant_t(0), &pDis);
   pDis->QueryInterface(IID_IHTMLElement, (void**)&pEle);
   pDis->Release();
   pEle->get_id(&bstrTmp);

   if(!lstrcmp(pThis->m_lpszOutDataTagId, bstrTmp))
   {
    pThis->m_pEle = pEle;    
    ::SysFreeString(bstrTmp);
    break;
   }
   else
   {
    pEle->Release();
    ::SysFreeString(bstrTmp);
   }
  }

  pBodyCollection->Release();
 }

 if(pThis->m_pEle && pThis->m_pEle->getAttribute(CComBSTR(TEXT("value")), 0, &varData)==S_OK)
 {
  if(varData.vt!=VT_NULL && varData.bstrVal!=NULL && lstrcmp(varData.bstrVal, TEXT("")))
  {
   pThis->m_pEle->setAttribute(CComBSTR(TEXT("value")), _variant_t(""));

   if(pThis->m_pCallOut)
   {
    pThis->m_pCallOut(varData.bstrVal);
   }
  }
 }

 SetEvent(pThis->m_hLock);
 return 1;
}

Qt QScript 之 C++/JavaScript相互调用 ECMAScript 是一个语言规范(Language Specification),可以理解为一种脚本语言规范。目前这个语言规范由这个组织在维护。而JavaScript 是ECMAScript 这种语言规范的一种具体实现。当前存在几种JavaScript实现,比如Apple的,Google的[v8] (https://v8.dev/)这两种是比较有名气的。总的来说, 一些更详细细节请参考感兴趣的同学可以自行定位学习, 最好的文档都是看官方的, 看别人的都带有个人主观经验, 并不一定是最合适自己的。 阅读详情

相关推荐

QT集成CEF10-JavaScript与C++互调

我们为什么要使用CEF? 很多情况下都是为了能够实现JavaScript与 native C++之间的相互调用。即网页中的JavaScript调用的时候,触发本地C++代码的执行,比如访问硬件等JavaScript无法完成的功能。本地C++代码也可以回调JavaScript,比如本地代码收到操作系统的一些通知后,将通知内容转交给JavaScript代码来执行。 ​ CEF中,JavaScript代码是运行在Renderer进行中的,理解这一点非常重要,native代码写的地方不合适,JavaScript代码

paopao_wu的专栏 3410

WebAssembly笔记(4)-JavaScript和C++的交互

一 JS调用C++函数从JS中调用C++函数,需要把C++函数声明为导出,有好几种方法,本文采用最原始也是效率最高的方法,就是函数签名加上EMSCRIPTEN_KEEPALIVE。1.1 EMSCRIPTEN_KEEPALIVE作用是告诉C++编译器这个函数会被用到,不要在“tree shaking”的时候删掉,并且会将函数名加上前缀 _ 导出给 JS。另外还需加上 extern "C" 告诉 ...

楚游香的博客 2355

CEF系列之 如何使用前端JS 向 C++传递信息

需求 有这么个需求: CEF浏览器上,点击一个按钮,要求弹出一个原生对话框,在这个原生对话框上,加载CEF浏览器传来的网址。 这个就涉及到了JS给C++传送信息,也就是JS调用C++功能。 JS写法 NimCefWebInstance.call('CEF_SendToCppExerciseInfo',{url},(error,result) 其中,NimCe...

目前打算换一个工作,有招聘windows c++方向的也欢迎联系,北京、济南 最好 1809

基于V8引擎的C++和JS的相互交互

基于什么原因略! 1.脚本引擎的基本功能 V8只是一个JS引擎。去除它的特点功能出处,它必须要实现JS引擎的几个基础功能: 脚本执行: 脚本可能是一个表达式;一段js代码;或者一个文件 执行表达式返回js表达式对应的值 C++来取设JS的内容 获取JS内容的数据(包括基础数据类型、数组、日期等)、对象(类的一个实例)、类或函数 设置JS内容的数据 J...

dkopg24406的专栏 433

通过QT实现C++和JavaScript混合编程

C++是编译性语言,修改了代码之后必须进行编译才能生效。当项目比较大的时候,项目的编译时间可能很长,如果仅仅因为一个小修改就需要将整个项目编译一遍,开发效率会很低。而JavaScript是脚本语言,修改之后不需要编译,能立即生效,这就能弥补C++在大型项目中的不足,从而提升开发效率。 在大型项目中我们一般将项目拆分成对效率要求比较高且比较稳定的引擎模块,以及业务变动比较大需要经常修改的业务模块。对于引擎模块由于比较稳定我们通过C++实现,而对于一些独立的业务模块由于经常需要变动和修改我们通过JavaScr

yang1fei2的博客 3283

Qt与网页中的JavaScript函数相互调用的实现

在Qt中调用网页中的JavaScript函数,我们可以使用QWebEngineView类来加载网页并执行其中的JavaScript代码。在Qt中调用网页中的JavaScript函数,我们可以使用QWebEngineView类来加载网页并执行其中的JavaScript代码。通过上述步骤,我们可以实现Qt与网页中JavaScript函数的相互调用。希望这篇文章对你有帮助!在网页中调用Qt对象的函数,我们需要使用JavaScript的。在网页中调用Qt对象的函数,我们需要使用JavaScript的。

CodeGu的博客 514

JavaScript引擎研究与C、C++与互调用(转)

JavaScript引擎研究与C、C++与互调用(转)

whl0071的专栏 3117

C++与JavaScript交互:创建数组及其他对象

JavaScript中的Array对象是一种特殊的数据结构,它可以存储任意类型的元素,包括数字、字符串、对象甚至是其他数组。数组对象的特性包括:动态大小:数组的大小不需要在声明时定义,可以根据需要自动伸缩。索引:数组元素通过索引来访问,索引从0开始递增。

weixin_42453228的博客 346

C++ 【随想录】(六)C++后端向JS前端转换

需要包含的头文件 #include"comutil.h" #include"<string> BSTR转string BSTR bstrText = ::SysAllocString(L"Test"); string str = _com_util::ConvertBSTRToString(bstrText); SysFreeS...

用可见的方式来记录和分享每一次收获 1094

pdf.js 移动端手势缩放功能实现与原生事件集成

本文详细解析了如何为pdf.js的viewer.html移动端页面实现流畅的双指捏合手势缩放功能。通过深入分析pdf.js的缩放机制,并利用原生触摸事件(touchstart、touchmove、touchend)进行集成,在不修改核心源码的前提下,为用户提供媲美原生应用的顺滑缩放体验,有效提升了移动端PDF阅读的专业性和用户满意度。

brandy的博客 490

论文笔记:Group Equivariant Convolutional Networks

Group Equivariant Convolutional Networks 1、四个问题 要解决什么问题? 对卷积神经网络进行扩展,并提出一个在特定的变换(旋转、平移等,也可表示为一个特殊的群)下具有等变性的网络。 用了什么方法解决? 提出了一种新的卷积神经网络结构——群等变卷积神经网络(Group equivariant Convolutional Neural Network)...

hongbin_xu的博客 1万+

Qt QWebEngine 加载网页及交互,实现C++与JS 相互调用

本篇主要介绍QT开发过程中如何利用QWebengine加载网页,通过C++与JS 相互调用,实现QT程序与HTML网页的交互。QtWebEngine 是Qt的一个子模块,它提供了一个 Web 浏览器引擎,可以轻松地将互联网上的内容嵌入到 Qt 应用程序中。Qt WebEngine Widgets Module 用于创建基于小部件的 Web 应用程序Qt WebEngine Module 用于创建基于 Qt Quick 的 Web 应用程序。

北极星的技术笔记 1万+

QGC二次开发实战指南(一):从零构建自定义地面站界面

本文详细介绍了QGC二次开发实战指南,从零开始构建自定义地面站界面。通过QT和QML技术结合MAVLINK协议,开发者可以打造适合特定业务场景的无人机监控系统,提升操作效率与用户体验。文章包含环境搭建、界面设计、数据绑定等完整开发流程,是QGC二次开发的实用教程。

weixin_28693683的博客 496

V8 引擎 C++ 与 js的相互访问(二)

V8 引擎基本概念 Google V8 引擎使用 C++ 代码编写,实现了 ECMAScript 规范的第五版,可以运行在所有的主流 操作系统中,甚至可以运行在移动终端 ( 基于 ARM 的处理器,如 HTC G7 等 )。V8 最早被开发用以嵌入到 Google 的开源浏览器 Chrome 中,但是 V8 是一个可以独立的模块,完全可以嵌入您自己的应用,著名的 Node.js( 一个异步的服...

qq_35886593的博客 3763

知识图谱与人工智能本体论:构建机器认知的语义基石

本文探讨了知识图谱与人工智能本体论如何作为机器认知的语义基石,让AI从‘知道数据’迈向‘理解知识’。文章详细拆解了本体论的核心构件与构建方法,并阐述了从本体到知识图谱的实践路径,包括知识获取、融合、存储及推理应用,最终分析了其在智能搜索与专家系统等场景中带来的根本性重塑。

nginx7reverse的博客 910

Ubuntu终端接入Codex:一行脚本搞定AI编程助手安装与配置

在开发者日常工作中,命令行终端是最高频的操作环境,而AI编程助手的出现正在改变传统的编码方式。通过将大模型能力与终端工具链结合,开发者无需切换窗口即可完成命令查询、代码生成、项目理解和自动执行等任务。Ubuntu作为服务器和开发机的主流系统,搭配Node.js生态和API Key认证,即可在本地闭环运行AI助手。本文从环境准备、密钥配置、权限管理到自动化脚本封装,系统拆解在终端中接入Codex的完整流程,并分享高频用法与实测排障经验,帮助开发者安全、高效地让AI融入命令行工作流。

weixin_29061041的博客 322

22.WebBrowser中JS和C++代码互相调用

WebBrowser内嵌的网页中JS与本地C++代码可以相互调用,这样就可以最大程度利用C++强大的计算能力和与本地硬件通信。本文详细演示了JS和C++代码互相调用的方法,JS调用C++的类独立封装可直接修改使用。

文洲的专栏 6148

Waymo数据集里的隐藏彩蛋:5个激光雷达数据融合实战(附Python代码)

本文深入解析Waymo数据集中5个激光雷达的数据融合技术,提供Python实战代码,帮助开发者掌握多传感器协同工作的关键方法。通过时间同步、坐标转换和运动补偿等技术,实现高精度3D场景重建,提升自动驾驶系统的环境感知能力。

weixin_30399821的博客 81

Qt之javascript(QJSEngine)

Qt之javascript(QJSEngine) c++调用js 调用js函数,QJSValue::call() QJSValue fun = myEngine.evaluate("(function(a, b) { return a + b; })"); QJSValueList args; args << 1 << 2; QJSValue threeAgain = fun.call(args); 执行脚本 QJSEngine::evalu

Black_Silencer的博客 2050

Vins-Fusion 外参camera-imu 标定

Vins-Fusion是一种基于优化的多传感器状态估计器,一大特色是支持实时camera-imu外参校准(相机和IMU之间的旋转)。Vins-Fusion 外参camera-imu校准是利用两帧间计算相机位姿和imu预积分得到位姿,构建最小二乘问题,并通过SVD求解camera-imu外参旋转矩阵。

u010196944的博客 2490

ABAP 7.40 新语法介绍系列之六:使用 FILTER 关键字对 ABAP 内表进行过滤

笔者之前写过的关于 ABAP 740 新语法的文章:本文介绍另一个新的关键字:FILTER.FILTER 是 ABAP 740 中引入的一个关键字,用于简化数据操作,它能够将内部表(Internal Table)中的数据按特定的条件进行过滤,并生成一个新的内部表。FILTER 的引入旨在使代码更加现代化和高效,尤其是在面对大量数据需要过滤的情况下。传统上,开发人员可能需要使用 LOOP AT 结合条件判断来实现,但使用 FILTER 关键字后,代码显得更加简洁且易于维护。

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 1170

QT开发模式(二):QML/JS/C++混合编程

不管是QT开发还是其它平台上开发,界面和业务逻辑分离都会是很重要的设计思想,QML/JS/C++混合开发很契合这个思想,如果你还没有用这种方式开发过,不妨试试看,可能会得到很多意外的收货。

红军不怕远征难,万水千山只等闲 2856

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

C++使用Google V8 引擎集成JS脚本能力

V8 引擎简介 Google V8 引擎使用 C++ 代码编写,实现了 ECMAScript 规范的第五版 ,可以运行在所有的主流操作系统中,甚至可以运行在移动终端 ( 基于 ARM 的处理器,如 HTC G7 等 )。V8 最早被开发用以嵌入到 Google 的开源浏览器 Chrome 中,但是 V8 是一个可以独立的模块,完全可以嵌入您自己的应用,著名的 Node.js( 一个异步的服务器框架,可以在服务端使用 JavaScript 写出高效的网络服务器 ) 就是基于 V8 引擎的。 和其他 JavaS

weixin_42684313的博客 3511

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

OV9734 DATASHEET,完整规格书

OV9734完整规格书,包括电气参数,尺寸规格,寄存器配置表等

QML/JS/C++

【QML 快速入门】QML 类型 - fengMisaka - 博客园 在QtC++中调用QML中的JavascriptFunction_青山绿水北京爷_新浪博客 C++调用QML中的函数 - xianyongchao - 博客园 C++调用qml函数 - Avatarx - 博客园 qml中调用js中的函数_cqltbe131421的博客-优快云博客_qml调用js qml和js相互调用实现_quietbxj的博客-优快云博客_js调用qml对象 qml 引入js_QML中(QML或J..

Liuqz2009的专栏 1338

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

Android C++系列:通过 JNI 访问 Java 字段和方法调用

在前面的两篇文章中,介绍了 Android 通过 JNI 进行基础类型、字符串和数组的相关操作,并描述了 Java 和 Native 在类型和签名之间的转换关系。有了之前那些基础,就可以实现 Java 和 Native 的相互调用了,在 Native 中去访问 Java 类的字段并调用相应的方法。

轻口味的专栏 1216
上一篇: 语音识别LoadCmdFromFile错误码0x80045052原因
下一篇: Makefile之wildcard
Matrix_Designer
博客等级 码龄16年 58粉丝 296原创
评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值