首页 > 其他分享 >用 (Excel) VBA 读取 OneNote!

用 (Excel) VBA 读取 OneNote!

时间:2024-10-22 09:48:09浏览次数:1  
标签:Dim VBA Excel 报错 OneNote win32com

本文记录,用 VBA 读取 OneNote 的方法,这块似乎一直是空白,研究了好久才找到解决方案!小白贡献,语失莫怪!


问题背景:

我在 OneNote 里有上百篇笔记,可 OneNote 自己,却无法导出全部的标题。于是我千方百计,想要读取 OneNote 的文件,来获取标题和日志信息。尝试了各种方案,都没能读出 OneNote 的数据。最后过了好久好久,才找到了这种,基于 Excel VBA 的解决方式!那么接下来,我们就来看下它的代码!在片尾我也会讲下,尝试过的其他方式,也许哪位路过的大神,能解决掉其中的问题!


代码如下:

  1. 首先要注意,这个代码是要添加到 Excel VBA 编辑器里的!因为 OneNote 里根本就没有 vba 编辑器,所以只能通过 Excel 里的 VBA 编辑器,来实现 OneNote 的操控和读取!
  2. 然后要注意,在运行代码前,需先添加几个 Reference (引用库)!
    1. Microsoft OneNote 12.0 Object Library
    2. Microsoft OneNote 15.0 Object Library
    3. Microsoft XML, V3.0
  3. 不同的 Office 可能会出现,这几个库的版本不一样,那么就需要根据你的库的版本,去微调下这个代码!否者会报错!

'Add the following references (adjust to your office version):
'- Microsoft OneNote 12.0 Object Library
'- Microsoft OneNote 15.0 Object Library
'- Microsoft XML, v3.0

Sub ListOneNotePages()
    'OneNote will be started, if it's not running.
    Dim OneNote As OneNote.Application
    Set OneNote = New OneNote.Application

    'Get the XML that represents the OneNote pages
    Dim oneNotePagesXml As String

    'Use note hierarchy, to get all page id.
    OneNote.GetHierarchy "", OneNote12.HierarchyScope.hsPages, oneNotePagesXml

    'Use the MSXML Library to parse the XML.
    Dim doc As MSXML2.DOMDocument
    Set doc = New MSXML2.DOMDocument

    If doc.LoadXML(oneNotePagesXml) Then
        'Find all the Page nodes in the one namespace.
        Dim nodes As MSXML2.IXMLDOMNodeList
        Set nodes = doc.DocumentElement.SelectNodes("//one:Page")

        Dim node As MSXML2.IXMLDOMNode
        Dim pageName As String
        Dim sectionName As String
        Dim pageContent As String
        Dim temp As String

        'Go through each page, and print out page content
        For Each node In nodes
            pageName = node.Attributes.getNamedItem("name").Text
            Debug.Print "Page name: "; vbCrLf & " " & pageName

            Call OneNote.GetPageContent(GetAttributeValueFromNode(node, "ID"), pageContent, piBasic)
            Debug.Print " content: " & pageContent
        Next
    Else
        MsgBox "OneNote 2010 XML Data failed to load."
    End If
End Sub

Private Function GetAttributeValueFromNode(node As MSXML2.IXMLDOMNode, attributeName As String) As String
    If node.Attributes.getNamedItem(attributeName) Is Nothing Then
        GetAttributeValueFromNode = "Not found."
    Else
        GetAttributeValueFromNode = node.Attributes.getNamedItem(attributeName).Text
    End If
End Function

Remote Procedure Call Failed 报错:

  1. 这个报错,我的理解是,它是在说,无法访问你要用的那个程序!具体为什么无法访问,和什么原因,我到现在也还是不知道!
  2. 在上面 VBA 的解决方案里,我只是把代码里的 OneNote12.Application,改成了 OneNote.Application 就解决了!具体为什么,不知道!但这个报错,确实就没了!我猜测是因为 OneNote 的版本的问题,之前报错,是因为它一直找不到 OneNote14.Application 这个本版本,但细节的问题就不讨论了!
  3. 但在 Python 的 win32com 方案里,则是一直都卡在,这个报错这里,一直没能过去!也因此在 Python 的解决方案里,到了最后也无法读取任何的 OneNote Page!

OneNote 无法启动问题:

  1. 如果发现,运行了 Python 的代码后,自己的 OneNote 显示正在恢复,无法打开!不用担心,只需去资源管理器里,把 OneNote.exe 这个任务关掉即可。然后 OneNote 就可以正常打开了!

其他解决方案:

其实在 Excel VBA 的解决方案之前,还尝试了很多很多其他的方案,那也粗略的说一下吧。

  1. 在 OneNote 中添加 COM 插件,使其能运行宏,类似于 VBA!这个插件叫做Onetastic!据说这个插件的作者,正是来自原 OneNote 的开发团队的成员,
    所以其实这个插件的质量很高,但就是要花钱买,所以最后也没采用这个方案!还有一个插件也很强悍,叫Gem for OneNote,但不符合我的需求!OneNote 的插件还有很多,感兴趣的同学,可以去看下面的链接!

  2. 就是自己开发插件,让其能在 OneNote 中运行。这个要求有点高,这种大神应该就不用,看我这篇文章了。所以如果有能力,这也确实是个选项!

  3. 就是使用 Python 的 win32com,其实 win32com 也是使用的 windows 自己的 com 接口,但 Python 毕竟是通过一个第三库,在做这件事情,所以这个库,要是运行不畅,或者出什么问题,作为小白,就真是很难解决了!就例如一直困扰我的,Remote Procedure Call Failed 的报错问题,就到现在也没能解决!这个报错很可能是,更深层的 COM 服务的问题,很可能是 onenote.dll 没了什么的,但这已经超出小白的范畴了。

  4. 就是还有各种 Python 的第三方库,例如:pyOneNote,onepy 什么的!我自己几乎都试一遍了,基本没一个好使了,都是很久之前的库了!我觉得这可能是,很少有人会去操控 OneNote,所以在这上面花心思的人就很少,这也是为什么,我找了很久,都找不到答案!所以才决定写这篇文章,希望能给需要的人,一点方便!


一些可用的 Python 代码:

至于下列代码里,为什么都是 OneNote.Application.12 我也不知道!但如果你的不好使,也可以改成 OneNote.Application.14 试试!但在我的电脑里,只有 OneNote.Application.12 好使!

# 输出页面结构信息
import win32com.client
oneapp = win32com.client.Dispatch('OneNote.Application.12')
result = oneapp.GetHierarchy("",4)
print(result)

## 输出所有页面的标题
import win32com.client
oneapp = win32com.client.Dispatch('OneNote.Application.12')
result = oneapp.GetHierarchy("",4)

from bs4 import BeautifulSoup
soup = BeautifulSoup(result, 'xml')
for tag in soup.find_all('one:Page'):
    print(tag.attrs['name'])

# 试图输出任何一个页面的内容 (报错暂时无解)
# >>> Error occurred: (-2147023170, 'The remote procedure call failed)
import win32com.client
onapp = win32com.client.Dispatch('OneNote.Application.12')
result = onapp.GetHierarchy("",4)
print(result)

pageID = "任何上面输出过的PageID"
content = onapp.GetPageContent(pageID)
print(content)

后期的应用

被 VBA 读取出来了,是 OneNote 每个页面的全部内容!信息量很大,都是 XML 形式的!之后的处理就不再赘述了,怎么处理就取决于各自的需求了!好的就写到这里了,希望能有帮助,(^_^)b


Reference:

  1. Automate Onenote 2010 From Excel 2007, using VBA - Stack Overflow
  2. Updating OneNote from VBA Excel - Stack Overflow
  3. OneNote developer reference | Microsoft Learn
  4. reading xml files in vb6 - Stack Overflow
  5. Top 11 Microsoft OneNote Add-ins
  6. Onetastic for OneNote

标签:Dim,VBA,Excel,报错,OneNote,win32com
From: https://www.cnblogs.com/bitssea/p/18491769

相关文章

  • 【新专栏】Excel数据分析与模拟决策-送完整电子版内容
     专栏入口:Excel数据分析与模拟决策购买专栏,即送对应完整版电子书及配套的Excel文件。......
  • Python 在Excel中插入、替换、提取、或删除图片
    Excel是主要用于处理表格和数据的工具,我们也能在其中插入、编辑或管理图片,为工作表增添视觉效果,提升报告的吸引力。本文将详细介绍如何使用Python操作Excel中的图片,包含以下4个基础示例:Python在Excel中插入图片Python替换Excel中的图片Python提取Excel中的图片Python删除......
  • Excel-Ctrl+Enter键的妙用
    一、Ctrl+Enter键的妙用 1.1 Ctrl+Enter键在多连续区域输入相同内容比如我要在一块区域内输入相同的数据,我首先选中这块区域,然后在第一个表格内输入数据-输入之后-(不要按回车键)按Ctrl+Enter键,即可全部表格输入同一数据  1.2 Ctrl+Enter键在非连续区域输入相同内容 先......
  • python 合并同列数据 组合 新的excel
    importpandasaspdfromopenpyxlimportload_workbook#读取Excel文件file_path='test.xlsx'#替换为你的Excel文件路径df=pd.read_excel(file_path)#显示读取的数据print(df)#打开工作簿wb=load_workbook(file_path)ws=wb.active#获取活动工作表......
  • 批量修改文件夹内各种格式文件名(与文件夹名保持一致)——EXCEL VBA 实现
     如下图:加入我们有3个文件夹,需要将3个文件夹内所有文件名改为与所在文件夹名一致,可用excelvba实现。方法如下: 一、打开此xlsm文件打开excel,  alt+F11快捷键打开代码编辑窗口。二、将文件夹路径修改为你的文件夹路径,如下图:需要重命名的文件夹全部放入一个总文件......
  • Access与Excel最重要的区别是什么
    Excel和Access之间的主要区别在于Excel是电子表格程序,而Access是数据库程序。Access使用ID号来存储数据,并且此列表是完全可编辑的,但在Excel工作表中,数据将存储在行和列中。一、Access与Excel最重要的区别Excel和Access之间的主要区别在于Excel是电子表格程......
  • mysql:excel 表格数据导入 mysql 的快捷方式
    (一)表格格式:1、创建新表、空表或打开有数据表2、表格以.csv形式保存3、保存表格时,直接选择“是”————(二)导入mysql数据库里:1、随便点个数据库选择TableDateImportWizard导入excel文件2、选择导入表格路径,然后点击Next。3、选择表格加入那个数据库......
  • PHP将整形数字转为Excel下标
    1、背景这两天在接到一个需求,需要导出一个班级所有学员的所有成绩,在最后excel表处理的时候发现导出的列超过了26列,后面会出现AA之类的下标,所以写了一个函数把数字整型转为Excel对应的下标。2、转换函数/***@Notes:将整数转为excel对应的列标*@Functionint_to_chr*@p......
  • Excel 2024 打开第二个文件很慢的解决方法
    1.问题描述该问题具体表现为:当打开第一个Excel文件后,在不关闭它的情况下接着打开第二个Excel文件,第二个Excel文件会延迟几秒之后才会正常打开。注意,前提是第一个Excel文件打开速度是正常的,否则本解决方案大概率对你无效。我的环境是Windows10+Office2024,本方案同样适用于......
  • .NET导出Excel的四种方法及评测
    .NET导出Excel的四种方法及评测 .NET导出Excel的四种方法及评测导出Excel是.NET的常见需求,开源社区、市场上,都提供了不少各式各样的Excel操作相关包。本文,我将使用NPOI、EPPlus、OpenXML、Aspose.Cells四个市面上常见的库,各完成一个导出Excel示例。然后对其代码风格和性能做......