├── .DS_Store
├── LICENSE
├── Other
├── .DS_Store
├── Install.sh
├── Products
│ ├── .DS_Store
│ └── Debug
│ │ ├── .DS_Store
│ │ └── WeChatPlugin.framework
│ │ ├── Headers
│ │ └── WeChatPlugin.h
│ │ ├── Modules
│ │ └── module.modulemap
│ │ ├── Resources
│ │ ├── Info.plist
│ │ ├── MMStatusCell.nib
│ │ ├── MMStatusImageMediaView.nib
│ │ ├── MMStatusLinkMediaView.nib
│ │ ├── MMTimeLineViewController.nib
│ │ ├── TKAutoReplyWindowController.nib
│ │ ├── TKRemoteControlCommands.plist
│ │ ├── TKRemoteControlScript.scpt
│ │ ├── TKRemoteControlWindowController.nib
│ │ ├── Tabbar-TimeLine-HI@2x.png
│ │ ├── Tabbar-TimeLine-Selected-HI@2x.png
│ │ ├── Tabbar-TimeLine-Selected@2x.png
│ │ ├── Tabbar-TimeLine@2x.png
│ │ ├── comment_icon_highlighted@2x.png
│ │ ├── comment_icon_normal@2x.png
│ │ ├── en.lproj
│ │ │ └── Localizable.strings
│ │ ├── like_icon_highlighted@2x.png
│ │ ├── like_icon_normal@2x.png
│ │ ├── link_icon@2x.png
│ │ ├── time_icon@2x.png
│ │ └── zh-Hans.lproj
│ │ │ └── Localizable.strings
│ │ ├── Versions
│ │ ├── A
│ │ │ ├── Headers
│ │ │ │ └── WeChatPlugin.h
│ │ │ ├── Modules
│ │ │ │ └── module.modulemap
│ │ │ ├── Resources
│ │ │ │ ├── Info.plist
│ │ │ │ ├── MMStatusCell.nib
│ │ │ │ ├── MMStatusImageMediaView.nib
│ │ │ │ ├── MMStatusLinkMediaView.nib
│ │ │ │ ├── MMTimeLineViewController.nib
│ │ │ │ ├── TKAutoReplyWindowController.nib
│ │ │ │ ├── TKRemoteControlCommands.plist
│ │ │ │ ├── TKRemoteControlScript.scpt
│ │ │ │ ├── TKRemoteControlWindowController.nib
│ │ │ │ ├── Tabbar-TimeLine-HI@2x.png
│ │ │ │ ├── Tabbar-TimeLine-Selected-HI@2x.png
│ │ │ │ ├── Tabbar-TimeLine-Selected@2x.png
│ │ │ │ ├── Tabbar-TimeLine@2x.png
│ │ │ │ ├── comment_icon_highlighted@2x.png
│ │ │ │ ├── comment_icon_normal@2x.png
│ │ │ │ ├── en.lproj
│ │ │ │ │ └── Localizable.strings
│ │ │ │ ├── like_icon_highlighted@2x.png
│ │ │ │ ├── like_icon_normal@2x.png
│ │ │ │ ├── link_icon@2x.png
│ │ │ │ ├── time_icon@2x.png
│ │ │ │ └── zh-Hans.lproj
│ │ │ │ │ └── Localizable.strings
│ │ │ └── WeChatPlugin
│ │ └── Current
│ │ │ ├── Headers
│ │ │ └── WeChatPlugin.h
│ │ │ ├── Modules
│ │ │ └── module.modulemap
│ │ │ ├── Resources
│ │ │ ├── Info.plist
│ │ │ ├── MMStatusCell.nib
│ │ │ ├── MMStatusImageMediaView.nib
│ │ │ ├── MMStatusLinkMediaView.nib
│ │ │ ├── MMTimeLineViewController.nib
│ │ │ ├── TKAutoReplyWindowController.nib
│ │ │ ├── TKRemoteControlCommands.plist
│ │ │ ├── TKRemoteControlScript.scpt
│ │ │ ├── TKRemoteControlWindowController.nib
│ │ │ ├── Tabbar-TimeLine-HI@2x.png
│ │ │ ├── Tabbar-TimeLine-Selected-HI@2x.png
│ │ │ ├── Tabbar-TimeLine-Selected@2x.png
│ │ │ ├── Tabbar-TimeLine@2x.png
│ │ │ ├── comment_icon_highlighted@2x.png
│ │ │ ├── comment_icon_normal@2x.png
│ │ │ ├── en.lproj
│ │ │ │ └── Localizable.strings
│ │ │ ├── like_icon_highlighted@2x.png
│ │ │ ├── like_icon_normal@2x.png
│ │ │ ├── link_icon@2x.png
│ │ │ ├── time_icon@2x.png
│ │ │ └── zh-Hans.lproj
│ │ │ │ └── Localizable.strings
│ │ │ └── WeChatPlugin
│ │ └── WeChatPlugin
├── Screenshots
│ ├── .DS_Store
│ └── wechatplugin.png
├── Uninstall.sh
└── insert_dylib
├── README.md
├── WeChatPlugin.xcodeproj
├── project.pbxproj
├── project.xcworkspace
│ ├── contents.xcworkspacedata
│ └── xcuserdata
│ │ ├── TK.xcuserdatad
│ │ └── UserInterfaceState.xcuserstate
│ │ ├── linden.xcuserdatad
│ │ └── UserInterfaceState.xcuserstate
│ │ └── timeaside.xcuserdatad
│ │ └── UserInterfaceState.xcuserstate
└── xcuserdata
│ ├── TK.xcuserdatad
│ ├── xcdebugger
│ │ └── Breakpoints_v2.xcbkptlist
│ └── xcschemes
│ │ ├── WeChatPlugin.xcscheme
│ │ └── xcschememanagement.plist
│ ├── linden.xcuserdatad
│ ├── xcdebugger
│ │ └── Breakpoints_v2.xcbkptlist
│ └── xcschemes
│ │ ├── WeChatPlugin.xcscheme
│ │ └── xcschememanagement.plist
│ └── timeaside.xcuserdatad
│ ├── xcdebugger
│ └── Breakpoints_v2.xcbkptlist
│ └── xcschemes
│ ├── WeChatPlugin.xcscheme
│ └── xcschememanagement.plist
└── WeChatPlugin
├── .DS_Store
├── Info.plist
├── Sources
├── .DS_Store
├── Category
│ ├── .DS_Store
│ ├── MMChatsTableCellView+Hook.h
│ ├── MMChatsTableCellView+Hook.m
│ ├── NSDate+StatusTimeDescription.h
│ ├── NSDate+StatusTimeDescription.m
│ ├── NSObject+ObjectMap.h
│ ├── NSObject+ObjectMap.m
│ ├── NSString+XMLDictionary.h
│ ├── NSString+XMLDictionary.m
│ ├── NSViewController+Hook.h
│ ├── NSViewController+Hook.m
│ ├── WeChat+Hook.h
│ └── WeChat+Hook.m
├── Common
│ ├── Category
│ │ ├── NSButton+Action.h
│ │ ├── NSButton+Action.m
│ │ ├── NSTextField+Action.h
│ │ ├── NSTextField+Action.m
│ │ ├── NSView+Action.h
│ │ └── NSView+Action.m
│ ├── Color.h
│ └── TKPrefixHeader.pch
├── Config
│ ├── TKWeChatPluginConfig.h
│ └── TKWeChatPluginConfig.m
├── Controllers
│ ├── TKRemoteControlController.h
│ └── TKRemoteControlController.m
├── Image
│ ├── .DS_Store
│ ├── Tabbar-TimeLine-HI@2x.png
│ ├── Tabbar-TimeLine-Selected-HI@2x.png
│ ├── Tabbar-TimeLine-Selected@2x.png
│ ├── Tabbar-TimeLine@2x.png
│ ├── comment_icon_highlighted@2x.png
│ ├── comment_icon_normal@2x.png
│ ├── like_icon_highlighted@2x.png
│ ├── like_icon_normal@2x.png
│ ├── link_icon@2x.png
│ └── time_icon@2x.png
├── JRSwizzle
│ ├── JRSwizzle.h
│ └── JRSwizzle.m
├── Models
│ ├── TKAutoReplyModel.h
│ ├── TKAutoReplyModel.m
│ ├── TKBaseModel.h
│ ├── TKBaseModel.m
│ ├── TKIgnoreSessonModel.h
│ ├── TKIgnoreSessonModel.m
│ ├── TKRemoteControlModel.h
│ └── TKRemoteControlModel.m
├── Status
│ ├── .DS_Store
│ ├── Model
│ │ ├── .DS_Store
│ │ ├── MMStatus.h
│ │ ├── MMStatus.m
│ │ ├── MMStatusImageMediaObject.h
│ │ ├── MMStatusImageMediaObject.m
│ │ ├── MMStatusLinkMediaObject.h
│ │ ├── MMStatusLinkMediaObject.m
│ │ ├── MMStatusMediaObject.h
│ │ └── MMStatusMediaObject.m
│ └── View
│ │ ├── .DS_Store
│ │ ├── MMStatusCell.h
│ │ ├── MMStatusCell.m
│ │ ├── MMStatusCell.xib
│ │ ├── MMStatusCellDelegate.h
│ │ ├── MMStatusImageMediaView.h
│ │ ├── MMStatusImageMediaView.m
│ │ ├── MMStatusImageMediaView.xib
│ │ ├── MMStatusImagePreviewView.h
│ │ ├── MMStatusImagePreviewView.m
│ │ ├── MMStatusLinkMediaView.h
│ │ ├── MMStatusLinkMediaView.m
│ │ ├── MMStatusLinkMediaView.xib
│ │ ├── MMStatusMediaView.h
│ │ └── MMStatusMediaView.m
├── TimeLine
│ ├── .DS_Store
│ ├── Controller
│ │ ├── .DS_Store
│ │ ├── MMTimeLineMainViewController.h
│ │ ├── MMTimeLineViewController.h
│ │ └── MMTimeLineViewController.m
│ ├── Mgr
│ │ ├── .DS_Store
│ │ ├── MMTimeLineMgr.h
│ │ ├── MMTimeLineMgr.m
│ │ └── MMTimeLineMgrDelegate.h
│ └── View
│ │ ├── .DS_Store
│ │ └── MMTimeLineViewController.xib
├── Utils
│ ├── .DS_Store
│ ├── TKHelper.h
│ ├── TKHelper.m
│ ├── XMLReader.h
│ └── XMLReader.m
├── Vendor
│ ├── fishhook.c
│ └── fishhook.h
├── Views
│ ├── AutoReply
│ │ ├── TKAutoReplyCell.h
│ │ ├── TKAutoReplyCell.m
│ │ ├── TKAutoReplyContentView.h
│ │ └── TKAutoReplyContentView.m
│ └── RemoteControl
│ │ ├── TKRemoteControlCell.h
│ │ └── TKRemoteControlCell.m
└── WindowControllers
│ ├── AutoReply
│ ├── TKAutoReplyWindowController.h
│ ├── TKAutoReplyWindowController.m
│ └── TKAutoReplyWindowController.xib
│ └── RemoteControl
│ ├── TKRemoteControlWindowController.h
│ ├── TKRemoteControlWindowController.m
│ └── TKRemoteControlWindowController.xib
├── TKRemoteControlCommands.plist
├── TKRemoteControlScript.scpt
├── WeChatPlugin.h
├── en.lproj
└── Localizable.strings
├── main.mm
└── zh-Hans.lproj
└── Localizable.strings
/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/.DS_Store
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2018 Loveletter
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/Other/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/.DS_Store
--------------------------------------------------------------------------------
/Other/Install.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | app_name="WeChat"
4 | shell_path="$(dirname "$0")"
5 | wechat_path="/Applications/WeChat.app"
6 | framework_name="WeChatPlugin"
7 | app_bundle_path="/Applications/${app_name}.app/Contents/MacOS"
8 | app_executable_path="${app_bundle_path}/${app_name}"
9 | app_executable_backup_path="${app_executable_path}_backup"
10 | framework_path="${app_bundle_path}/${framework_name}.framework"
11 |
12 | # 对 WeChat 赋予权限
13 | if [ ! -w "$wechat_path" ]
14 | then
15 | echo -e "\n\n为了将小助手写入微信, 请输入密码 : "
16 | sudo chown -R $(whoami) "$wechat_path"
17 | fi
18 |
19 | # 备份 WeChat 原始可执行文件
20 | if [ ! -f "$app_executable_backup_path" ]
21 | then
22 | cp "$app_executable_path" "$app_executable_backup_path"
23 | result="y"
24 | else
25 | read -t 150 -p "已安装微信小助手,是否覆盖?[y/n]:" result
26 | fi
27 |
28 | if [[ "$result" == 'y' ]]; then
29 | cp -r "${shell_path}/Products/Debug/${framework_name}.framework" ${app_bundle_path}
30 | ${shell_path}/insert_dylib --all-yes "${framework_path}/${framework_name}" "$app_executable_backup_path" "$app_executable_path"
31 | fi
32 |
--------------------------------------------------------------------------------
/Other/Products/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/.DS_Store
--------------------------------------------------------------------------------
/Other/Products/Debug/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/.DS_Store
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Modules/module.modulemap:
--------------------------------------------------------------------------------
1 | framework module WeChatPlugin {
2 | umbrella header "WeChatPlugin.h"
3 |
4 | export *
5 | module * { export * }
6 | }
7 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | BuildMachineOSBuild
6 | 17D47
7 | CFBundleDevelopmentRegion
8 | en
9 | CFBundleExecutable
10 | WeChatPlugin
11 | CFBundleIdentifier
12 | Net.CodeTips.WeChatPlugin
13 | CFBundleInfoDictionaryVersion
14 | 6.0
15 | CFBundleName
16 | WeChatPlugin
17 | CFBundlePackageType
18 | FMWK
19 | CFBundleShortVersionString
20 | 1.0
21 | CFBundleSupportedPlatforms
22 |
23 | MacOSX
24 |
25 | CFBundleVersion
26 | 1
27 | DTCompiler
28 | com.apple.compilers.llvm.clang.1_0
29 | DTPlatformBuild
30 | 9C40b
31 | DTPlatformVersion
32 | GM
33 | DTSDKBuild
34 | 17C76
35 | DTSDKName
36 | macosx10.13
37 | DTXcode
38 | 0920
39 | DTXcodeBuild
40 | 9C40b
41 | NSHumanReadableCopyright
42 | Copyright © 2018年 CodeTips. All rights reserved.
43 |
44 |
45 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/MMStatusCell.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/MMStatusCell.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/MMStatusImageMediaView.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/MMStatusImageMediaView.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/MMStatusLinkMediaView.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/MMStatusLinkMediaView.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/MMTimeLineViewController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/MMTimeLineViewController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/TKAutoReplyWindowController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/TKAutoReplyWindowController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/TKRemoteControlCommands.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | executeCommand
8 | open /System/Library/Frameworks/ScreenSaver.framework/Versions/A/Resources/ScreenSaverEngine.app || open /System/Library/CoreServices/ScreenSaverEngine.app
9 | keyword
10 | ScreenSave
11 | function
12 | 屏幕保护
13 | enable
14 |
15 | command
16 | #remote.screensaver
17 |
18 |
19 | executeCommand
20 | /System/Library/CoreServices/Menu\ Extras/User.menu/Contents/Resources/CGSession -suspend
21 | keyword
22 | LockScreen
23 | function
24 | 锁屏
25 | enable
26 |
27 | command
28 | #remote.lockscreen
29 |
30 |
31 | executeCommand
32 | sleep
33 | keyword
34 | Sleep
35 | function
36 | 休眠
37 | enable
38 |
39 | command
40 | #remote.sleep
41 |
42 |
43 | executeCommand
44 | shutdown
45 | keyword
46 | Shutdown
47 | function
48 | 关机
49 | enable
50 |
51 | command
52 | #remote.shutdown
53 |
54 |
55 | executeCommand
56 | restart
57 | keyword
58 | Restart
59 | function
60 | 重启
61 | enable
62 |
63 | command
64 | #remote.restart
65 |
66 |
67 | executeCommand
68 | empty
69 | keyword
70 | EmptyTrash
71 | function
72 | 清空废纸篓
73 | enable
74 |
75 | command
76 | #remote.emptytrash
77 |
78 |
79 |
80 |
81 | executeCommand
82 | killQQ
83 | keyword
84 | KillQQ
85 | function
86 | 退出 QQ
87 | enable
88 |
89 |
90 |
91 | executeCommand
92 | killWeChat
93 | keyword
94 | KillWeChat
95 | function
96 | 退出 WeChat
97 | enable
98 |
99 |
100 |
101 | executeCommand
102 | killChrome
103 | keyword
104 | KillChrome
105 | function
106 | 退出 Chrome
107 | enable
108 |
109 |
110 |
111 | executeCommand
112 | killSafari
113 | keyword
114 | KillSafari
115 | function
116 | 退出 Safari
117 | enable
118 |
119 |
120 |
121 | executeCommand
122 | killAll
123 | keyword
124 | KillAll
125 | function
126 | 退出所有程序
127 | enable
128 |
129 |
130 |
131 |
132 |
133 | executeCommand
134 | musicToggle
135 | keyword
136 | Toggle
137 | function
138 | 播放/暂停
139 | enable
140 |
141 |
142 |
143 | executeCommand
144 | musicNext
145 | keyword
146 | Next
147 | function
148 | 下一首
149 | enable
150 |
151 |
152 |
153 | executeCommand
154 | musicPrevious
155 | keyword
156 | Previous
157 | function
158 | 上一首
159 | enable
160 |
161 |
162 |
163 | executeCommand
164 | musicVolumeUp
165 | keyword
166 | VolumeUp
167 | function
168 | 增大音量
169 | enable
170 |
171 |
172 |
173 | executeCommand
174 | musicVolumeDown
175 | keyword
176 | VolumeDown
177 | function
178 | 减小音量
179 | enable
180 |
181 |
182 |
183 | executeCommand
184 | musicLike
185 | keyword
186 | LikeChange
187 | function
188 | 喜欢/取消喜欢
189 | enable
190 |
191 |
192 |
193 |
194 |
195 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/TKRemoteControlScript.scpt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/TKRemoteControlScript.scpt
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/TKRemoteControlWindowController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/TKRemoteControlWindowController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine-HI@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine-Selected-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine-Selected-HI@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine-Selected@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine-Selected@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/Tabbar-TimeLine@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/comment_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/comment_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/comment_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/comment_icon_normal@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/en.lproj/Localizable.strings:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/en.lproj/Localizable.strings
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/like_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/like_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/like_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/like_icon_normal@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/link_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/link_icon@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/time_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/time_icon@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Resources/zh-Hans.lproj/Localizable.strings:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Resources/zh-Hans.lproj/Localizable.strings
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Modules/module.modulemap:
--------------------------------------------------------------------------------
1 | framework module WeChatPlugin {
2 | umbrella header "WeChatPlugin.h"
3 |
4 | export *
5 | module * { export * }
6 | }
7 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | BuildMachineOSBuild
6 | 17D47
7 | CFBundleDevelopmentRegion
8 | en
9 | CFBundleExecutable
10 | WeChatPlugin
11 | CFBundleIdentifier
12 | Net.CodeTips.WeChatPlugin
13 | CFBundleInfoDictionaryVersion
14 | 6.0
15 | CFBundleName
16 | WeChatPlugin
17 | CFBundlePackageType
18 | FMWK
19 | CFBundleShortVersionString
20 | 1.0
21 | CFBundleSupportedPlatforms
22 |
23 | MacOSX
24 |
25 | CFBundleVersion
26 | 1
27 | DTCompiler
28 | com.apple.compilers.llvm.clang.1_0
29 | DTPlatformBuild
30 | 9C40b
31 | DTPlatformVersion
32 | GM
33 | DTSDKBuild
34 | 17C76
35 | DTSDKName
36 | macosx10.13
37 | DTXcode
38 | 0920
39 | DTXcodeBuild
40 | 9C40b
41 | NSHumanReadableCopyright
42 | Copyright © 2018年 CodeTips. All rights reserved.
43 |
44 |
45 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMStatusCell.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMStatusCell.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMStatusImageMediaView.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMStatusImageMediaView.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMStatusLinkMediaView.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMStatusLinkMediaView.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMTimeLineViewController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/MMTimeLineViewController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKAutoReplyWindowController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKAutoReplyWindowController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKRemoteControlCommands.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | executeCommand
8 | open /System/Library/Frameworks/ScreenSaver.framework/Versions/A/Resources/ScreenSaverEngine.app || open /System/Library/CoreServices/ScreenSaverEngine.app
9 | keyword
10 | ScreenSave
11 | function
12 | 屏幕保护
13 | enable
14 |
15 | command
16 | #remote.screensaver
17 |
18 |
19 | executeCommand
20 | /System/Library/CoreServices/Menu\ Extras/User.menu/Contents/Resources/CGSession -suspend
21 | keyword
22 | LockScreen
23 | function
24 | 锁屏
25 | enable
26 |
27 | command
28 | #remote.lockscreen
29 |
30 |
31 | executeCommand
32 | sleep
33 | keyword
34 | Sleep
35 | function
36 | 休眠
37 | enable
38 |
39 | command
40 | #remote.sleep
41 |
42 |
43 | executeCommand
44 | shutdown
45 | keyword
46 | Shutdown
47 | function
48 | 关机
49 | enable
50 |
51 | command
52 | #remote.shutdown
53 |
54 |
55 | executeCommand
56 | restart
57 | keyword
58 | Restart
59 | function
60 | 重启
61 | enable
62 |
63 | command
64 | #remote.restart
65 |
66 |
67 | executeCommand
68 | empty
69 | keyword
70 | EmptyTrash
71 | function
72 | 清空废纸篓
73 | enable
74 |
75 | command
76 | #remote.emptytrash
77 |
78 |
79 |
80 |
81 | executeCommand
82 | killQQ
83 | keyword
84 | KillQQ
85 | function
86 | 退出 QQ
87 | enable
88 |
89 |
90 |
91 | executeCommand
92 | killWeChat
93 | keyword
94 | KillWeChat
95 | function
96 | 退出 WeChat
97 | enable
98 |
99 |
100 |
101 | executeCommand
102 | killChrome
103 | keyword
104 | KillChrome
105 | function
106 | 退出 Chrome
107 | enable
108 |
109 |
110 |
111 | executeCommand
112 | killSafari
113 | keyword
114 | KillSafari
115 | function
116 | 退出 Safari
117 | enable
118 |
119 |
120 |
121 | executeCommand
122 | killAll
123 | keyword
124 | KillAll
125 | function
126 | 退出所有程序
127 | enable
128 |
129 |
130 |
131 |
132 |
133 | executeCommand
134 | musicToggle
135 | keyword
136 | Toggle
137 | function
138 | 播放/暂停
139 | enable
140 |
141 |
142 |
143 | executeCommand
144 | musicNext
145 | keyword
146 | Next
147 | function
148 | 下一首
149 | enable
150 |
151 |
152 |
153 | executeCommand
154 | musicPrevious
155 | keyword
156 | Previous
157 | function
158 | 上一首
159 | enable
160 |
161 |
162 |
163 | executeCommand
164 | musicVolumeUp
165 | keyword
166 | VolumeUp
167 | function
168 | 增大音量
169 | enable
170 |
171 |
172 |
173 | executeCommand
174 | musicVolumeDown
175 | keyword
176 | VolumeDown
177 | function
178 | 减小音量
179 | enable
180 |
181 |
182 |
183 | executeCommand
184 | musicLike
185 | keyword
186 | LikeChange
187 | function
188 | 喜欢/取消喜欢
189 | enable
190 |
191 |
192 |
193 |
194 |
195 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKRemoteControlScript.scpt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKRemoteControlScript.scpt
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKRemoteControlWindowController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/TKRemoteControlWindowController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine-HI@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine-Selected-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine-Selected-HI@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine-Selected@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine-Selected@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/Tabbar-TimeLine@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/comment_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/comment_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/comment_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/comment_icon_normal@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/en.lproj/Localizable.strings:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/en.lproj/Localizable.strings
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/like_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/like_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/like_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/like_icon_normal@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/link_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/link_icon@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/time_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/time_icon@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/zh-Hans.lproj/Localizable.strings:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/Resources/zh-Hans.lproj/Localizable.strings
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/A/WeChatPlugin:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/A/WeChatPlugin
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Modules/module.modulemap:
--------------------------------------------------------------------------------
1 | framework module WeChatPlugin {
2 | umbrella header "WeChatPlugin.h"
3 |
4 | export *
5 | module * { export * }
6 | }
7 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | BuildMachineOSBuild
6 | 17D47
7 | CFBundleDevelopmentRegion
8 | en
9 | CFBundleExecutable
10 | WeChatPlugin
11 | CFBundleIdentifier
12 | Net.CodeTips.WeChatPlugin
13 | CFBundleInfoDictionaryVersion
14 | 6.0
15 | CFBundleName
16 | WeChatPlugin
17 | CFBundlePackageType
18 | FMWK
19 | CFBundleShortVersionString
20 | 1.0
21 | CFBundleSupportedPlatforms
22 |
23 | MacOSX
24 |
25 | CFBundleVersion
26 | 1
27 | DTCompiler
28 | com.apple.compilers.llvm.clang.1_0
29 | DTPlatformBuild
30 | 9C40b
31 | DTPlatformVersion
32 | GM
33 | DTSDKBuild
34 | 17C76
35 | DTSDKName
36 | macosx10.13
37 | DTXcode
38 | 0920
39 | DTXcodeBuild
40 | 9C40b
41 | NSHumanReadableCopyright
42 | Copyright © 2018年 CodeTips. All rights reserved.
43 |
44 |
45 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMStatusCell.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMStatusCell.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMStatusImageMediaView.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMStatusImageMediaView.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMStatusLinkMediaView.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMStatusLinkMediaView.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMTimeLineViewController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/MMTimeLineViewController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKAutoReplyWindowController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKAutoReplyWindowController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKRemoteControlCommands.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | executeCommand
8 | open /System/Library/Frameworks/ScreenSaver.framework/Versions/A/Resources/ScreenSaverEngine.app || open /System/Library/CoreServices/ScreenSaverEngine.app
9 | keyword
10 | ScreenSave
11 | function
12 | 屏幕保护
13 | enable
14 |
15 | command
16 | #remote.screensaver
17 |
18 |
19 | executeCommand
20 | /System/Library/CoreServices/Menu\ Extras/User.menu/Contents/Resources/CGSession -suspend
21 | keyword
22 | LockScreen
23 | function
24 | 锁屏
25 | enable
26 |
27 | command
28 | #remote.lockscreen
29 |
30 |
31 | executeCommand
32 | sleep
33 | keyword
34 | Sleep
35 | function
36 | 休眠
37 | enable
38 |
39 | command
40 | #remote.sleep
41 |
42 |
43 | executeCommand
44 | shutdown
45 | keyword
46 | Shutdown
47 | function
48 | 关机
49 | enable
50 |
51 | command
52 | #remote.shutdown
53 |
54 |
55 | executeCommand
56 | restart
57 | keyword
58 | Restart
59 | function
60 | 重启
61 | enable
62 |
63 | command
64 | #remote.restart
65 |
66 |
67 | executeCommand
68 | empty
69 | keyword
70 | EmptyTrash
71 | function
72 | 清空废纸篓
73 | enable
74 |
75 | command
76 | #remote.emptytrash
77 |
78 |
79 |
80 |
81 | executeCommand
82 | killQQ
83 | keyword
84 | KillQQ
85 | function
86 | 退出 QQ
87 | enable
88 |
89 |
90 |
91 | executeCommand
92 | killWeChat
93 | keyword
94 | KillWeChat
95 | function
96 | 退出 WeChat
97 | enable
98 |
99 |
100 |
101 | executeCommand
102 | killChrome
103 | keyword
104 | KillChrome
105 | function
106 | 退出 Chrome
107 | enable
108 |
109 |
110 |
111 | executeCommand
112 | killSafari
113 | keyword
114 | KillSafari
115 | function
116 | 退出 Safari
117 | enable
118 |
119 |
120 |
121 | executeCommand
122 | killAll
123 | keyword
124 | KillAll
125 | function
126 | 退出所有程序
127 | enable
128 |
129 |
130 |
131 |
132 |
133 | executeCommand
134 | musicToggle
135 | keyword
136 | Toggle
137 | function
138 | 播放/暂停
139 | enable
140 |
141 |
142 |
143 | executeCommand
144 | musicNext
145 | keyword
146 | Next
147 | function
148 | 下一首
149 | enable
150 |
151 |
152 |
153 | executeCommand
154 | musicPrevious
155 | keyword
156 | Previous
157 | function
158 | 上一首
159 | enable
160 |
161 |
162 |
163 | executeCommand
164 | musicVolumeUp
165 | keyword
166 | VolumeUp
167 | function
168 | 增大音量
169 | enable
170 |
171 |
172 |
173 | executeCommand
174 | musicVolumeDown
175 | keyword
176 | VolumeDown
177 | function
178 | 减小音量
179 | enable
180 |
181 |
182 |
183 | executeCommand
184 | musicLike
185 | keyword
186 | LikeChange
187 | function
188 | 喜欢/取消喜欢
189 | enable
190 |
191 |
192 |
193 |
194 |
195 |
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKRemoteControlScript.scpt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKRemoteControlScript.scpt
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKRemoteControlWindowController.nib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/TKRemoteControlWindowController.nib
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine-HI@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine-Selected-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine-Selected-HI@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine-Selected@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine-Selected@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/Tabbar-TimeLine@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/comment_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/comment_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/comment_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/comment_icon_normal@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/en.lproj/Localizable.strings:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/en.lproj/Localizable.strings
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/like_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/like_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/like_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/like_icon_normal@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/link_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/link_icon@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/time_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/time_icon@2x.png
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/zh-Hans.lproj/Localizable.strings:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/Resources/zh-Hans.lproj/Localizable.strings
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/WeChatPlugin:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/Versions/Current/WeChatPlugin
--------------------------------------------------------------------------------
/Other/Products/Debug/WeChatPlugin.framework/WeChatPlugin:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Products/Debug/WeChatPlugin.framework/WeChatPlugin
--------------------------------------------------------------------------------
/Other/Screenshots/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Screenshots/.DS_Store
--------------------------------------------------------------------------------
/Other/Screenshots/wechatplugin.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/Screenshots/wechatplugin.png
--------------------------------------------------------------------------------
/Other/Uninstall.sh:
--------------------------------------------------------------------------------
1 | # !/bin/bash
2 |
3 | app_name="WeChat"
4 | framework_name="WeChatPlugin"
5 | app_bundle_path="/Applications/${app_name}.app/Contents/MacOS"
6 | app_executable_path="${app_bundle_path}/${app_name}"
7 | app_executable_backup_path="${app_executable_path}_backup"
8 | framework_path="${app_bundle_path}/${framework_name}.framework"
9 | # 备份WeChat原始可执行文件
10 | if [ -f "$app_executable_backup_path" ]
11 | then
12 | rm "$app_executable_path"
13 | rm -rf "$framework_path"
14 | mv "$app_executable_backup_path" "$app_executable_path"
15 | echo "\n\t卸载成功"
16 | else
17 | echo "\n\t未发现微信小助手"
18 | fi
19 |
--------------------------------------------------------------------------------
/Other/insert_dylib:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/Other/insert_dylib
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # WeChatPlugin-macOS
2 |
3 |  [](https://github.com/CodeTips/WeChatPlugin-macOS/blob/master/LICENSE)
4 |
5 |
6 |
7 | ### 说明
8 |
9 | * 包含功能: 自动回复、消息防撤回、远程控制、微信多开、会话置底、免认证登录、窗口置顶、会话多选删除、通知快捷回复、浏览朋友圈。
10 | * 部分功能基于[WeChatPlugin-MacOS](https://github.com/TKkk-iOSer/WeChatPlugin-MacOS)开发,远程控制功能增强,配合[WeChatPlugin-iOS](https://github.com/CodeTips/WeChatPlugin-iOS)和越狱插件[WeChatPlugin](https://github.com/CodeTips/WeChatPlugin)可实现一键锁屏、关机等功能。菜单显示优化,本地化支持。原作者(**TK**)关键字去除,***个人强迫症***。
11 | * 朋友圈功能基于[WeChatPlugin](https://github.com/Natoto/WeChatPlugin)开发,优化图片显示逻辑,修复刷新导致显示异常的问题。目前最新版微信已经不支持。
12 | * 若使用中遇到遇到问题,请去以上提到的项目找解决方案,或者 **Issue me!**
13 |
14 | ### 依赖
15 |
16 | * [XMLReader](https://github.com/amarcadet/XMLReader)
17 | * [insert_dylib](https://github.com/Tyilo/insert_dylib)
18 | * [fishhook](https://github.com/facebook/fishhook)
19 |
20 | ### 最后
21 | * 使用愉快~
22 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/project.xcworkspace/contents.xcworkspacedata:
--------------------------------------------------------------------------------
1 |
2 |
4 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/project.xcworkspace/xcuserdata/TK.xcuserdatad/UserInterfaceState.xcuserstate:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin.xcodeproj/project.xcworkspace/xcuserdata/TK.xcuserdatad/UserInterfaceState.xcuserstate
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/project.xcworkspace/xcuserdata/linden.xcuserdatad/UserInterfaceState.xcuserstate:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin.xcodeproj/project.xcworkspace/xcuserdata/linden.xcuserdatad/UserInterfaceState.xcuserstate
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/project.xcworkspace/xcuserdata/timeaside.xcuserdatad/UserInterfaceState.xcuserstate:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin.xcodeproj/project.xcworkspace/xcuserdata/timeaside.xcuserdatad/UserInterfaceState.xcuserstate
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/TK.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/TK.xcuserdatad/xcschemes/WeChatPlugin.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
31 |
32 |
33 |
34 |
35 |
36 |
47 |
51 |
52 |
53 |
59 |
60 |
61 |
62 |
63 |
64 |
70 |
71 |
77 |
78 |
79 |
80 |
82 |
83 |
86 |
87 |
88 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/TK.xcuserdatad/xcschemes/xcschememanagement.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | SchemeUserState
6 |
7 | WeChatPlugin.xcscheme
8 |
9 | orderHint
10 | 0
11 |
12 |
13 | SuppressBuildableAutocreation
14 |
15 | 528B4F911EA7383800BC6A89
16 |
17 | primary
18 |
19 |
20 |
21 |
22 |
23 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/linden.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/linden.xcuserdatad/xcschemes/WeChatPlugin.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
31 |
32 |
33 |
34 |
35 |
36 |
47 |
50 |
51 |
52 |
58 |
59 |
60 |
61 |
62 |
63 |
69 |
70 |
76 |
77 |
78 |
79 |
81 |
82 |
85 |
86 |
87 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/linden.xcuserdatad/xcschemes/xcschememanagement.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | SchemeUserState
6 |
7 | WeChatPlugin.xcscheme
8 |
9 | orderHint
10 | 0
11 |
12 |
13 | SuppressBuildableAutocreation
14 |
15 | 528B4F911EA7383800BC6A89
16 |
17 | primary
18 |
19 |
20 |
21 |
22 |
23 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/timeaside.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist:
--------------------------------------------------------------------------------
1 |
2 |
5 |
6 |
8 |
20 |
21 |
22 |
23 |
24 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/timeaside.xcuserdatad/xcschemes/WeChatPlugin.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
31 |
32 |
33 |
34 |
35 |
36 |
47 |
50 |
51 |
52 |
58 |
59 |
60 |
61 |
62 |
63 |
69 |
70 |
76 |
77 |
78 |
79 |
81 |
82 |
85 |
86 |
87 |
--------------------------------------------------------------------------------
/WeChatPlugin.xcodeproj/xcuserdata/timeaside.xcuserdatad/xcschemes/xcschememanagement.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | SchemeUserState
6 |
7 | WeChatPlugin.xcscheme
8 |
9 | orderHint
10 | 0
11 |
12 |
13 | SuppressBuildableAutocreation
14 |
15 | 528B4F911EA7383800BC6A89
16 |
17 | primary
18 |
19 |
20 |
21 |
22 |
23 |
--------------------------------------------------------------------------------
/WeChatPlugin/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | en
7 | CFBundleExecutable
8 | $(EXECUTABLE_NAME)
9 | CFBundleIdentifier
10 | $(PRODUCT_BUNDLE_IDENTIFIER)
11 | CFBundleInfoDictionaryVersion
12 | 6.0
13 | CFBundleName
14 | $(PRODUCT_NAME)
15 | CFBundlePackageType
16 | FMWK
17 | CFBundleShortVersionString
18 | 1.0
19 | CFBundleVersion
20 | $(CURRENT_PROJECT_VERSION)
21 | NSHumanReadableCopyright
22 | Copyright © 2018年 CodeTips. All rights reserved.
23 | NSPrincipalClass
24 |
25 |
26 |
27 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Category/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/MMChatsTableCellView+Hook.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMChatsTableCellView+hook.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/15.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSObject (MMChatsTableCellViewHook)
12 |
13 | + (void)hookMMChatsTableCellView;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSDate+StatusTimeDescription.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSDate+StatusTimeDescription.h
3 | // MacWeChatTimeLinePlugin
4 | //
5 | // Created by nato on 2017/3/17.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSDate (StatusTimeDescription)
12 |
13 | - (NSString *)statusTimeDescription;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSDate+StatusTimeDescription.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSDate+StatusTimeDescription.m
3 | // MacWeChatTimeLinePlugin
4 | //
5 | // Created by nato on 2017/3/17.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "NSDate+StatusTimeDescription.h"
10 |
11 | @implementation NSDate (StatusTimeDescription)
12 |
13 | - (NSString *)statusTimeDescription {
14 | NSCalendar *calendar = [NSCalendar currentCalendar];
15 | NSString *res = [[NSString stringWithFormat:@"%@", [self dateByAddingTimeInterval:8 * 60 * 60]] substringToIndex:19];
16 | if ([calendar isDateInToday:self]) {
17 | return [res substringFromIndex:11];
18 | }
19 | else {
20 | NSString *year = [res substringToIndex:4];
21 | if ([[NSString stringWithFormat:@"%@", [NSDate dateWithTimeIntervalSinceNow:8 * 60 * 60]] hasPrefix:year]) {
22 | return [res substringFromIndex:5];
23 | }
24 | else {
25 | return res;
26 | }
27 | }
28 | }
29 |
30 | @end
31 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSObject+ObjectMap.h:
--------------------------------------------------------------------------------
1 | //Copyright (c) 2012 The Board of Trustees of The University of Alabama
2 | //All rights reserved.
3 | //
4 | //Redistribution and use in source and binary forms, with or without
5 | //modification, are permitted provided that the following conditions
6 | //are met:
7 | //
8 | //1. Redistributions of source code must retain the above copyright
9 | //notice, this list of conditions and the following disclaimer.
10 | //2. Redistributions in binary form must reproduce the above copyright
11 | //notice, this list of conditions and the following disclaimer in the
12 | //documentation and/or other materials provided with the distribution.
13 | //3. Neither the name of the University nor the names of the contributors
14 | //may be used to endorse or promote products derived from this software
15 | //without specific prior written permission.
16 | //
17 | //THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18 | //"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19 | //LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
20 | //FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21 | //THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
22 | //INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
23 | //(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
24 | // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25 | //HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
26 | //STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27 | //ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
28 | //OF THE POSSIBILITY OF SUCH DAMAGE.
29 |
30 |
31 | #import
32 | #import
33 |
34 | #define OMDateFormat @"yyyy-MM-dd'T'HH:mm:ss.SSS"
35 | #define OMTimeZone @"UTC"
36 |
37 |
38 | typedef NS_ENUM(NSInteger, CAPSDataType) {
39 | CAPSDataTypeJSON,
40 | CAPSDataTypeXML,
41 | CAPSDataTypeSOAP
42 | };
43 |
44 | @interface NSObject (ObjectMap)
45 |
46 | // Universal Method
47 | -(NSDictionary *)propertyDictionary;
48 | -(NSString *)nameOfClass;
49 |
50 |
51 | #pragma mark - Init Methods
52 | /**
53 | Initializes an instance of a new object using JSON.
54 |
55 | @param data The JSON data to deserialize into the returned object.
56 |
57 | @return The newly-initialized object.
58 | */
59 | - (instancetype)initWithJSONData:(NSData *)data;
60 |
61 |
62 | /**
63 | Initializes an instance of a new object using XML.
64 |
65 | @param data The XML data to deserialize into the returned object.
66 |
67 | @return The newly-initialized object.
68 | */
69 | - (instancetype)initWithXMLData:(NSData *)data;
70 |
71 |
72 | /**
73 | Initializes an instance of a new object using SOAP.
74 |
75 | @param data The SOAP data to deserialize into the returned object.
76 |
77 | @return The newly-initialized object.
78 | */
79 | - (instancetype)initWithSOAPData:(NSData *)data;
80 |
81 |
82 | /**
83 | Initializes an instance of a new object using unspecified object data and a specified type.
84 |
85 | @param data The unspecified data to deserialize into the returned object.
86 | @param type The type of unspecified data to deserialize.
87 |
88 | @return The newly-initialized object.
89 | */
90 | - (instancetype)initWithObjectData:(NSData *)data type:(CAPSDataType)type;
91 |
92 |
93 |
94 | #pragma mark - Top Level Array from JSON
95 | /**
96 | Initializes an array of objects that are of a certain class from JSON data.
97 |
98 | @param objectClass The type of object to deserialize into.
99 | @param data The JSON data to deserialize into the array.
100 |
101 | @return The newly-initialized array.
102 | */
103 | + (NSArray *)arrayOfType:(Class)objectClass FromJSONData:(NSData *)data;
104 |
105 |
106 |
107 | #pragma mark - Serialized Data/Strings from Objects
108 | -(NSData *)JSONData;
109 | -(NSString *)JSONString;
110 | -(NSData *)XMLData;
111 | -(NSString *)XMLString;
112 | -(NSData *)SOAPData;
113 | -(NSString *)SOAPString;
114 | -(NSDictionary *)objectDictionary;
115 |
116 |
117 | #pragma mark - New Object with properties of another Object
118 | -(id)initWithObject:(NSObject *)oldObject error:(NSError **)error;
119 |
120 | #pragma mark - Base64 Encode/Decode
121 | +(NSString *)encodeBase64WithData:(NSData *)objData;
122 | +(NSData *)base64DataFromString:(NSString *)string;
123 |
124 | @end
125 |
126 | @interface SOAPObject : NSObject
127 | @property (nonatomic, retain) id Header;
128 | @property (nonatomic, retain) id Body;
129 | @end
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSString+XMLDictionary.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSString+XMLDictionary.h
3 | // WeChatManagerClient
4 | //
5 | // Created by nato on 2016/11/11.
6 | // Copyright © 2016年 nato. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSString (XMLDictionary)
12 |
13 | - (NSDictionary *)xmlDictionary;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSString+XMLDictionary.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSString+XMLDictionary.m
3 | // WeChatManagerClient
4 | //
5 | // Created by nato on 2016/11/11.
6 | // Copyright © 2016年 nato. All rights reserved.
7 | //
8 |
9 | #import "NSString+XMLDictionary.h"
10 | #import "XMLReader.h"
11 |
12 | @implementation NSString (XMLDictionary)
13 |
14 | - (NSDictionary *)xmlDictionary {
15 | return [XMLReader dictionaryForXMLString:self error:nil];
16 | }
17 |
18 | @end
19 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSViewController+Hook.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSViewController+Hook.h
3 | // WeChatPlugin
4 | //
5 | // Created by Loveletter on 26/02/2018.
6 | // Copyright © 2018 CodeTips. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSObject (NSViewController)
12 |
13 | + (void)hookNSViewController;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/NSViewController+Hook.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSViewController+Hook.m
3 | // WeChatPlugin
4 | //
5 | // Created by Loveletter on 26/02/2018.
6 | // Copyright © 2018 CodeTips. All rights reserved.
7 | //
8 |
9 | #import "NSViewController+Hook.h"
10 | #import "WeChatPlugin.h"
11 | #import "MMTimeLineMainViewController.h"
12 | #import "MMTimeLineViewController.h"
13 |
14 | @implementation NSObject (NSViewController)
15 |
16 | + (void)hookNSViewController
17 | {
18 | if (!CBGetClass(SnsTimeLineRequest)) {
19 | return;
20 | }
21 | CBRegisterClass(MMContactsViewController, MMTimeLineMainViewController);
22 |
23 | tk_hookMethod(objc_getClass("LeftViewController"), @selector(setViewControllers:), [self class], @selector(cb_setViewControllers:));
24 | tk_hookMethod(objc_getClass("MMViewController"), @selector(viewDidLoad), [self class], @selector(cb_mmDidLoad));
25 | tk_hookMethod(objc_getClass("MMPreviewViewController"), @selector(viewDidLoad), [self class], @selector(cb_preViewDidLoad));
26 | tk_hookMethod(objc_getClass("MMPreviewPanel"), @selector(show), [self class], @selector(cb_preshow));
27 | }
28 |
29 |
30 | - (void)cb_setViewControllers:(NSArray *)vcs {
31 |
32 | MMTimeLineMainViewController *timeLineMainVC = [[objc_getClass("MMTimeLineMainViewController") alloc] initWithNibName:@"MMContactsViewController" bundle:[NSBundle mainBundle]];
33 | [timeLineMainVC setTitle:[[NSBundle mainBundle] localizedStringForKey:@"Tabbar.Chats" value:@"" table:0x0]];
34 |
35 |
36 | MMTimeLineViewController *timeLineVC = [[objc_getClass("MMTimeLineViewController") alloc] initWithNibName:@"MMTimeLineViewController" bundle:[NSBundle pluginBundle]];
37 | timeLineMainVC.detailViewController = (id)timeLineVC;
38 |
39 | MMTabbarItem *tabBarItem = [[objc_getClass("MMTabbarItem") alloc] initWithTitle:@"朋友圈" onStateImage:[[NSBundle pluginBundle] imageForResource:@"Tabbar-TimeLine-Selected"] onStateAlternateImage:[[NSBundle pluginBundle] imageForResource:@"Tabbar-TimeLine-Selected-HI"] offStateImage:[[NSBundle pluginBundle] imageForResource:@"Tabbar-TimeLine"] offStateAlternateImage:[[NSBundle pluginBundle] imageForResource:@"Tabbar-TimeLine-HI"]];
40 | [timeLineMainVC setTabbarItem:tabBarItem];
41 |
42 | NSMutableArray *viewControllers = [vcs mutableCopy];
43 | [viewControllers addObject:timeLineMainVC];
44 | [self cb_setViewControllers:[viewControllers copy]];
45 |
46 | }
47 |
48 | -(void)cb_mmDidLoad{
49 | NSLog(@"\n----\n ❤️ %@ didLoad \n----\n",NSStringFromClass([self class]));
50 | }
51 | -(void)cb_preViewDidLoad{
52 |
53 | [self cb_preViewDidLoad];
54 | }
55 |
56 | -(void)cb_preshow{
57 | [self cb_preshow];
58 | }
59 |
60 | @end
61 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Category/WeChat+Hook.h:
--------------------------------------------------------------------------------
1 | //
2 | // WeChat+hook.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSObject (WeChatHook)
12 |
13 | + (void)hookWeChat;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Category/NSButton+Action.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSButton+Action.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSButton (Action)
12 | + (instancetype)tk_buttonWithTitle:(NSString *)title target:(id)target action:(SEL)action;
13 | + (instancetype)tk_checkboxWithTitle:(NSString *)title target:(id)target action:(SEL)action;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Category/NSButton+Action.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSButton+Action.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "NSButton+Action.h"
10 |
11 | @implementation NSButton (Action)
12 |
13 | + (instancetype)tk_checkboxWithTitle:(NSString *)title target:(id)target action:(SEL)action {
14 | NSButton *btn = [NSButton tk_buttonWithTitle:title target:target action:action];
15 | [btn setButtonType:NSButtonTypeSwitch];
16 |
17 | return btn;
18 | }
19 |
20 | + (instancetype)tk_buttonWithTitle:(NSString *)title target:(id)target action:(SEL)action {
21 | NSButton *btn = ({
22 | NSButton *btn = [[NSButton alloc] init];
23 | btn.title = title;
24 | btn.target = target;
25 | btn.action = action;
26 |
27 | btn;
28 | });
29 |
30 | return btn;
31 | }
32 |
33 | @end
34 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Category/NSTextField+Action.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSTextField+Action.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSTextField (Action)
12 |
13 | + (instancetype)tk_labelWithString:(NSString *)stringValue;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Category/NSTextField+Action.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSTextField+Action.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "NSTextField+Action.h"
10 |
11 | @implementation NSTextField (Action)
12 |
13 | + (instancetype)tk_labelWithString:(NSString *)stringValue {
14 | NSTextField *textField = ({
15 | NSTextField *textField = [[NSTextField alloc] initWithFrame:NSMakeRect(10, 10, 200, 17)];
16 | [textField setStringValue:stringValue];
17 | [textField setBezeled:NO];
18 | [textField setDrawsBackground:NO];
19 | [textField setEditable:NO];
20 | [textField setSelectable:NO];
21 |
22 | textField;
23 | });
24 |
25 | return textField;
26 | }
27 |
28 | @end
29 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Category/NSView+Action.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSView+Action.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/20.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSView (Action)
12 |
13 | - (void)addSubviews:(NSArray *)subViews;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Category/NSView+Action.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSView+Action.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/20.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "NSView+Action.h"
10 |
11 | @implementation NSView (Action)
12 |
13 | - (void)addSubviews:(NSArray *)subViews {
14 | for (NSView *v in subViews) {
15 | NSAssert([v isKindOfClass:[NSView class]], @"the elements must be a view!");
16 | [self addSubview:v];
17 | }
18 | }
19 |
20 | @end
21 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/Color.h:
--------------------------------------------------------------------------------
1 | //
2 | // Color.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/20.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #ifndef Color_h
10 | #define Color_h
11 |
12 | #define TK_RGBA(r, g, b, a) [NSColor colorWithRed:(r) / 255.0 \
13 | green:(g) / 255.0 \
14 | blue:(b) / 255.0 \
15 | alpha:(a)]
16 |
17 | #define TK_RGB(r, g, b) TK_RGBA(r, g, b, 1.0)
18 | #define TK_GRAYA(c, a) TK_RGBA(c, c, c, a)
19 | #define TK_GRAY(c) TK_GRAYA(c, 1.0)
20 |
21 | #define kBG1 TK_GRAY(0xec)
22 | #define kBG2 TK_GRAY(0xe3)
23 | #define kBG3 TK_GRAYA(0x2a, 0.5)
24 | #define kBG4 TK_GRAYA(0x7a, 0.5)
25 |
26 | #endif /* Color_h */
27 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Common/TKPrefixHeader.pch:
--------------------------------------------------------------------------------
1 | //
2 | // TKPrefixHeader.pch
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/20.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #ifndef TKPrefixHeader_pch
10 | #define TKPrefixHeader_pch
11 |
12 | #ifdef __OBJC__
13 | #import "Color.h"
14 | #import "NSView+Action.h"
15 | #import "NSButton+Action.h"
16 | #import "NSTextField+Action.h"
17 | #import
18 | #import
19 | #import "WeChatPlugin.h"
20 | #import "MMStatus.h"
21 | #import "MMStatusMediaObject.h"
22 | #import "MMStatusImageMediaObject.h"
23 | #import "MMStatusLinkMediaObject.h"
24 | #endif
25 |
26 | #define CBGetClass(classname) objc_getClass(#classname)
27 | #define CBRegisterClass(superclassname, subclassname) { Class class = objc_allocateClassPair(CBGetClass(superclassname), #subclassname, 0);objc_registerClassPair(class); }
28 |
29 |
30 | #endif /* TKPrefixHeader_pch */
31 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Config/TKWeChatPluginConfig.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKWeChatPluginConfig.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 |
10 | #import
11 |
12 | @interface TKWeChatPluginConfig : NSObject
13 |
14 | @property (nonatomic, assign) BOOL preventRevokeEnable; /**< 是否开启防撤回 */
15 | @property (nonatomic, assign) BOOL autoAuthEnable; /**< 是否免认证登录 */
16 | @property (nonatomic, assign) BOOL autoLoginEnable; /**< 是否自动登录 */
17 | @property (nonatomic, assign) BOOL onTop; /**< 是否要置顶微信 */
18 | @property (nonatomic, assign) BOOL multipleSelectionEnable; /**< 是否要进行多选 */
19 | @property (nonatomic, copy) NSMutableArray *autoReplyModels; /**< 自动回复的数组 */
20 | @property (nonatomic, copy) NSMutableArray *remoteControlModels; /**< 远程控制的数组 */
21 | @property (nonatomic, copy) NSMutableArray *ignoreSessionModels; /**< 聊天置底的数组 */
22 | @property (nonatomic, copy) NSMutableArray *selectSessions; /**< 已经选中的会话 */
23 | @property (nonatomic, copy) NSMutableSet *revokeMsgSet; /**< 撤回的消息集合 */
24 | @property (nonatomic, copy) NSString *currentUserName; /**< 当前用户的id */
25 |
26 | - (void)saveAutoReplyModels;
27 | - (void)saveRemoteControlModels;
28 | - (void)saveIgnoreSessionModels;
29 |
30 | + (instancetype)sharedConfig;
31 |
32 | @end
33 |
34 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Config/TKWeChatPluginConfig.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKWeChatPluginConfig.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKWeChatPluginConfig.h"
10 | #import "TKRemoteControlModel.h"
11 | #import "TKAutoReplyModel.h"
12 | #import "TKIgnoreSessonModel.h"
13 |
14 | static NSString * const kTKPreventRevokeEnableKey = @"kTKPreventRevokeEnableKey";
15 | static NSString * const kTKAutoAuthEnableKey = @"kTKAutoAuthEnableKey";
16 | static NSString * const kTKAutoLoginEnableKey = @"kTKAutoLoginEnableKey";
17 | static NSString * const kTKOnTopKey = @"kTKOnTopKey";
18 | static NSString * const kTKWeChatResourcesPath = @"/Applications/WeChat.app/Contents/MacOS/WeChatPlugin.framework/Resources/";
19 |
20 | @interface TKWeChatPluginConfig ()
21 |
22 | @property (nonatomic, copy) NSString *remoteControlPlistFilePath;
23 | @property (nonatomic, copy) NSString *autoReplyPlistFilePath;
24 | @property (nonatomic, copy) NSString *ignoreSessionPlistFilePath;
25 |
26 | @end
27 |
28 | @implementation TKWeChatPluginConfig
29 |
30 | + (instancetype)sharedConfig {
31 | static TKWeChatPluginConfig *config = nil;
32 | static dispatch_once_t onceToken;
33 | dispatch_once(&onceToken, ^{
34 | config = [[TKWeChatPluginConfig alloc] init];
35 | });
36 | return config;
37 | }
38 |
39 | - (instancetype)init {
40 | self = [super init];
41 | if (self) {
42 | _preventRevokeEnable = [[NSUserDefaults standardUserDefaults] boolForKey:kTKPreventRevokeEnableKey];
43 | _autoAuthEnable = [[NSUserDefaults standardUserDefaults] boolForKey:kTKAutoAuthEnableKey];
44 | _autoLoginEnable = [[NSUserDefaults standardUserDefaults] boolForKey:kTKAutoLoginEnableKey];
45 | _onTop = [[NSUserDefaults standardUserDefaults] boolForKey:kTKOnTopKey];
46 | }
47 | return self;
48 | }
49 |
50 | - (void)setPreventRevokeEnable:(BOOL)preventRevokeEnable {
51 | _preventRevokeEnable = preventRevokeEnable;
52 | [[NSUserDefaults standardUserDefaults] setBool:preventRevokeEnable forKey:kTKPreventRevokeEnableKey];
53 | [[NSUserDefaults standardUserDefaults] synchronize];
54 | }
55 |
56 | - (void)setAutoAuthEnable:(BOOL)autoAuthEnable {
57 | _autoAuthEnable = autoAuthEnable;
58 | [[NSUserDefaults standardUserDefaults] setBool:autoAuthEnable forKey:kTKAutoAuthEnableKey];
59 | [[NSUserDefaults standardUserDefaults] synchronize];
60 | }
61 |
62 | - (void)setAutoLoginEnable:(BOOL)autoLoginEnable {
63 | _autoLoginEnable = autoLoginEnable;
64 | [[NSUserDefaults standardUserDefaults] setBool:autoLoginEnable forKey:kTKAutoLoginEnableKey];
65 | [[NSUserDefaults standardUserDefaults] synchronize];
66 | }
67 |
68 | - (void)setOnTop:(BOOL)onTop {
69 | _onTop = onTop;
70 | [[NSUserDefaults standardUserDefaults] setBool:_onTop forKey:kTKOnTopKey];
71 | [[NSUserDefaults standardUserDefaults] synchronize];
72 | }
73 |
74 | #pragma mark - 自动回复
75 | - (NSArray *)autoReplyModels {
76 | if (!_autoReplyModels) {
77 | _autoReplyModels = [self getModelsWithClass:[TKAutoReplyModel class] filePath:self.autoReplyPlistFilePath];
78 | }
79 | return _autoReplyModels;
80 | }
81 |
82 | - (void)saveAutoReplyModels {
83 | NSMutableArray *needSaveModels = [NSMutableArray array];
84 | [_autoReplyModels enumerateObjectsUsingBlock:^(TKAutoReplyModel *model, NSUInteger idx, BOOL * _Nonnull stop) {
85 | if (model.hasEmptyKeywordOrReplyContent) {
86 | model.enable = NO;
87 | model.enableGroupReply = NO;
88 | }
89 | model.replyContent = model.replyContent == nil ? @"" : model.replyContent;
90 | model.keyword = model.keyword == nil ? @"" : model.keyword;
91 | [needSaveModels addObject:model.dictionary];
92 | }];
93 | [needSaveModels writeToFile:self.autoReplyPlistFilePath atomically:YES];
94 | }
95 |
96 | #pragma mark - 远程控制
97 | - (NSArray *)remoteControlModels {
98 | if (!_remoteControlModels) {
99 | _remoteControlModels = ({
100 | NSArray *originModels = [NSArray arrayWithContentsOfFile:self.remoteControlPlistFilePath];
101 | NSMutableArray *newRemoteControlModels = [NSMutableArray array];
102 | [originModels enumerateObjectsUsingBlock:^(NSArray *subModels, NSUInteger idx, BOOL * _Nonnull stop) {
103 | NSMutableArray *newSubModels = [NSMutableArray array];
104 | [subModels enumerateObjectsUsingBlock:^(id _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
105 | TKRemoteControlModel *model = [[TKRemoteControlModel alloc] initWithDict:obj];
106 | [newSubModels addObject:model];
107 | }];
108 | [newRemoteControlModels addObject:newSubModels];
109 | }];
110 | newRemoteControlModels;
111 | });
112 | }
113 | return _remoteControlModels;
114 | }
115 |
116 | - (void)saveRemoteControlModels {
117 | NSMutableArray *needSaveModels = [NSMutableArray array];
118 | [_remoteControlModels enumerateObjectsUsingBlock:^(NSArray *subModels, NSUInteger idx, BOOL * _Nonnull stop) {
119 | NSMutableArray *newSubModels = [NSMutableArray array];
120 | [subModels enumerateObjectsUsingBlock:^(TKRemoteControlModel *obj, NSUInteger idx, BOOL * _Nonnull stop) {
121 | [newSubModels addObject:obj.dictionary];
122 | }];
123 | [needSaveModels addObject:newSubModels];
124 | }];
125 | [needSaveModels writeToFile:self.remoteControlPlistFilePath atomically:YES];
126 | }
127 |
128 | #pragma mark - 置底
129 | - (NSArray *)ignoreSessionModels {
130 | if (!_ignoreSessionModels) {
131 | _ignoreSessionModels = [self getModelsWithClass:[TKIgnoreSessonModel class] filePath:self.ignoreSessionPlistFilePath];
132 | }
133 | return _ignoreSessionModels;
134 | }
135 |
136 | - (void)saveIgnoreSessionModels {
137 | NSMutableArray *needSaveArray = [NSMutableArray array];
138 | [self.ignoreSessionModels enumerateObjectsUsingBlock:^(TKBaseModel *obj, NSUInteger idx, BOOL * _Nonnull stop) {
139 | [needSaveArray addObject:obj.dictionary];
140 | }];
141 |
142 | [needSaveArray writeToFile:self.ignoreSessionPlistFilePath atomically:YES];
143 |
144 | }
145 |
146 | #pragma mark - 选中的会话
147 | - (NSMutableArray *)selectSessions {
148 | if (!_selectSessions) {
149 | _selectSessions = [NSMutableArray array];
150 | }
151 | return _selectSessions;
152 | }
153 |
154 | #pragma mark - 选中的会话
155 | - (NSMutableSet *)revokeMsgSet {
156 | if (!_revokeMsgSet) {
157 | _revokeMsgSet = [NSMutableSet set];
158 | }
159 | return _revokeMsgSet;
160 | }
161 |
162 | #pragma mark - 获取沙盒上的 plist 文件,包括:远程控制,自动回复,置底列表。
163 | - (NSString *)remoteControlPlistFilePath {
164 | if (!_remoteControlPlistFilePath) {
165 | _remoteControlPlistFilePath = [self getSandboxFilePathWithPlistName:@"TKRemoteControlCommands.plist"];
166 | }
167 | return _remoteControlPlistFilePath;
168 | }
169 |
170 | - (NSString *)autoReplyPlistFilePath {
171 | if (!_autoReplyPlistFilePath) {
172 | _autoReplyPlistFilePath = [self getSandboxFilePathWithPlistName:@"TKAutoReplyModels.plist"];
173 | }
174 | return _autoReplyPlistFilePath;
175 | }
176 |
177 | - (NSString *)ignoreSessionPlistFilePath {
178 | if (!_ignoreSessionPlistFilePath) {
179 | _ignoreSessionPlistFilePath = [self getSandboxFilePathWithPlistName:@"TKIgnoreSessons.plist"];
180 | }
181 | return _ignoreSessionPlistFilePath;
182 | }
183 |
184 | #pragma mark - common
185 | - (NSMutableArray *)getModelsWithClass:(Class)class filePath:(NSString *)filePath {
186 | NSArray *originModels = [NSArray arrayWithContentsOfFile:filePath];
187 | NSMutableArray *newModels = [NSMutableArray array];
188 |
189 | __weak Class weakClass = class;
190 | [originModels enumerateObjectsUsingBlock:^(NSDictionary *obj, NSUInteger idx, BOOL * _Nonnull stop) {
191 | TKIgnoreSessonModel *model = [[weakClass alloc] initWithDict:obj];
192 | [newModels addObject:model];
193 | }];
194 | return newModels;
195 | }
196 |
197 | - (NSString *)getSandboxFilePathWithPlistName:(NSString *)plistName {
198 | NSFileManager *manager = [NSFileManager defaultManager];
199 | NSString *wechatPluginDirectory = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) firstObject] stringByAppendingPathComponent:@"TKWeChatPlugin"];
200 | NSString *plistFilePath = [wechatPluginDirectory stringByAppendingPathComponent:plistName];
201 | if ([manager fileExistsAtPath:plistFilePath]) {
202 | return plistFilePath;
203 | }
204 |
205 | [manager createDirectoryAtPath:wechatPluginDirectory withIntermediateDirectories:YES attributes:nil error:nil];
206 | NSString *resourcesFilePath = [kTKWeChatResourcesPath stringByAppendingString:plistName];
207 | if (![manager fileExistsAtPath:resourcesFilePath]) {
208 | return plistFilePath;
209 | }
210 |
211 | NSError *error = nil;
212 | [manager copyItemAtPath:resourcesFilePath toPath:plistFilePath error:&error];
213 | if (!error) {
214 | return plistFilePath;
215 | }
216 |
217 | return resourcesFilePath;
218 | }
219 |
220 | @end
221 |
222 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Controllers/TKRemoteControlController.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlController.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface TKRemoteControlController : NSObject
12 |
13 | + (void)executeRemoteControlCommandWithMsg:(NSString *)msg;
14 | + (void)executeShellCommand:(NSString *)msg;
15 | + (NSString *)remoteControlCommandsString;
16 |
17 | @end
18 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Controllers/TKRemoteControlController.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlController.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKRemoteControlController.h"
10 | #import "TKWeChatPluginConfig.h"
11 | #import "TKRemoteControlModel.h"
12 | #import "WeChatPlugin.h"
13 |
14 | // 执行 AppleScript
15 | static NSString * const kRemoteControlAppleScript = @"osascript /Applications/WeChat.app/Contents/MacOS/WeChatPlugin.framework/Resources/TKRemoteControlScript.scpt";
16 |
17 | @implementation TKRemoteControlController
18 |
19 | + (void)executeRemoteControlCommandWithMsg:(NSString *)msg {
20 | NSArray *remoteControlModels = [TKWeChatPluginConfig sharedConfig].remoteControlModels;
21 | [remoteControlModels enumerateObjectsUsingBlock:^(NSArray *subModels, NSUInteger index, BOOL * _Nonnull stop) {
22 | [subModels enumerateObjectsUsingBlock:^(TKRemoteControlModel *model, NSUInteger idx, BOOL * _Nonnull stop) {
23 | if (model.enable && ![model.keyword isEqualToString:@""] && ([msg isEqualToString:model.keyword] || [msg isEqualToString:model.command])) {
24 | if ([model.function isEqualToString:@"屏幕保护"] || [model.function isEqualToString:@"锁屏"]) {
25 | // 屏幕保护 & 锁屏 通过 Shell 命令来执行即可
26 | [self executeShellCommand:model.executeCommand];
27 | } else {
28 | // 拼接相关参数,执行 AppleScript
29 | NSString *command = [NSString stringWithFormat:@"%@ %@",kRemoteControlAppleScript, model.executeCommand];
30 | [self executeShellCommand:command];
31 | // bug: 有些程序在第一次时会无法关闭,需要再次关闭
32 | dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
33 | if ([model.function isEqualToString:@"退出所有程序"]) {
34 | NSString *command = [NSString stringWithFormat:@"%@ %@",kRemoteControlAppleScript, model.executeCommand];
35 | [self executeShellCommand:command];
36 | }
37 | });
38 | }
39 | if (![msg hasPrefix:@"#remote."]) {
40 | NSString *currentUserName = [objc_getClass("CUtility") GetCurrentUserName];
41 | NSString *callBack = [NSString stringWithFormat:@"小助手收到一条指令:%@",model.function];
42 | MessageService *service = [[objc_getClass("MMServiceCenter") defaultCenter] getService:objc_getClass("MessageService")];
43 | [service SendTextMessage:currentUserName toUsrName:currentUserName msgText:callBack atUserList:nil];
44 | }
45 | }
46 | }];
47 | }];
48 | }
49 |
50 | /**
51 | 通过 NSTask 执行 Shell 命令
52 |
53 | @param cmd Terminal命令
54 | */
55 | + (void)executeShellCommand:(NSString *)cmd {
56 | NSTask *task = [[NSTask alloc] init];
57 | [task setLaunchPath:@"/bin/bash"];
58 | [task setArguments:@[@"-c", cmd]];
59 | [task launch];
60 | }
61 |
62 | + (NSString *)remoteControlCommandsString {
63 | NSMutableString *replyContent = [NSMutableString stringWithFormat:@"远程控制指令:\n(功能-指令-是否开启)\n\n"];
64 |
65 | NSArray *remoteControlModels = [TKWeChatPluginConfig sharedConfig].remoteControlModels;
66 | [remoteControlModels enumerateObjectsUsingBlock:^(NSArray *subModels, NSUInteger index, BOOL * _Nonnull stop) {
67 | switch (index) {
68 | case 0:
69 | [replyContent appendString:@"macbook控制:\n"];
70 | break;
71 | case 1:
72 | [replyContent appendString:@"app控制:\n"];
73 | break;
74 | case 2:
75 | [replyContent appendString:@"网易云音乐控制:\n"];
76 | break;
77 | default:
78 | break;
79 | }
80 | [subModels enumerateObjectsUsingBlock:^(TKRemoteControlModel *model, NSUInteger idx, BOOL * _Nonnull stop) {
81 | [replyContent appendFormat:@"%@-%@-%@\n", model.function, model.keyword, model.enable ? @"开启":@"关闭"];
82 | }];
83 | [replyContent appendString:@"\n"];
84 | }];
85 | return replyContent;
86 | }
87 |
88 | @end
89 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/Tabbar-TimeLine-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/Tabbar-TimeLine-HI@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/Tabbar-TimeLine-Selected-HI@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/Tabbar-TimeLine-Selected-HI@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/Tabbar-TimeLine-Selected@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/Tabbar-TimeLine-Selected@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/Tabbar-TimeLine@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/Tabbar-TimeLine@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/comment_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/comment_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/comment_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/comment_icon_normal@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/like_icon_highlighted@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/like_icon_highlighted@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/like_icon_normal@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/like_icon_normal@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/link_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/link_icon@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Image/time_icon@2x.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Image/time_icon@2x.png
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/JRSwizzle/JRSwizzle.h:
--------------------------------------------------------------------------------
1 | // JRSwizzle.h semver:1.0
2 | // Copyright (c) 2007-2011 Jonathan 'Wolf' Rentzsch: http://rentzsch.com
3 | // Some rights reserved: http://opensource.org/licenses/MIT
4 | // https://github.com/rentzsch/jrswizzle
5 |
6 | #import
7 |
8 | @interface NSObject (JRSwizzle)
9 |
10 | + (BOOL)jr_swizzleMethod:(SEL)origSel_ withMethod:(SEL)altSel_ error:(NSError**)error_;
11 | + (BOOL)jr_swizzleClassMethod:(SEL)origSel_ withClassMethod:(SEL)altSel_ error:(NSError**)error_;
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/JRSwizzle/JRSwizzle.m:
--------------------------------------------------------------------------------
1 | // JRSwizzle.m semver:1.0
2 | // Copyright (c) 2007-2011 Jonathan 'Wolf' Rentzsch: http://rentzsch.com
3 | // Some rights reserved: http://opensource.org/licenses/MIT
4 | // https://github.com/rentzsch/jrswizzle
5 |
6 | #import "JRSwizzle.h"
7 |
8 | #if TARGET_OS_IPHONE
9 | #import
10 | #import
11 | #else
12 | #import
13 | #endif
14 |
15 | #define SetNSErrorFor(FUNC, ERROR_VAR, FORMAT,...) \
16 | if (ERROR_VAR) { \
17 | NSString *errStr = [NSString stringWithFormat:@"%s: " FORMAT,FUNC,##__VA_ARGS__]; \
18 | *ERROR_VAR = [NSError errorWithDomain:@"NSCocoaErrorDomain" \
19 | code:-1 \
20 | userInfo:[NSDictionary dictionaryWithObject:errStr forKey:NSLocalizedDescriptionKey]]; \
21 | }
22 | #define SetNSError(ERROR_VAR, FORMAT,...) SetNSErrorFor(__func__, ERROR_VAR, FORMAT, ##__VA_ARGS__)
23 |
24 | #if OBJC_API_VERSION >= 2
25 | #define GetClass(obj) object_getClass(obj)
26 | #else
27 | #define GetClass(obj) (obj ? obj->isa : Nil)
28 | #endif
29 |
30 | @implementation NSObject (JRSwizzle)
31 |
32 | + (BOOL)jr_swizzleMethod:(SEL)origSel_ withMethod:(SEL)altSel_ error:(NSError**)error_ {
33 | #if OBJC_API_VERSION >= 2
34 | Method origMethod = class_getInstanceMethod(self, origSel_);
35 | if (!origMethod) {
36 | #if TARGET_OS_IPHONE
37 | SetNSError(error_, @"original method %@ not found for class %@", NSStringFromSelector(origSel_), [self class]);
38 | #else
39 | SetNSError(error_, @"original method %@ not found for class %@", NSStringFromSelector(origSel_), [self className]);
40 | #endif
41 | return NO;
42 | }
43 |
44 | Method altMethod = class_getInstanceMethod(self, altSel_);
45 | if (!altMethod) {
46 | #if TARGET_OS_IPHONE
47 | SetNSError(error_, @"alternate method %@ not found for class %@", NSStringFromSelector(altSel_), [self class]);
48 | #else
49 | SetNSError(error_, @"alternate method %@ not found for class %@", NSStringFromSelector(altSel_), [self className]);
50 | #endif
51 | return NO;
52 | }
53 |
54 | class_addMethod(self,
55 | origSel_,
56 | class_getMethodImplementation(self, origSel_),
57 | method_getTypeEncoding(origMethod));
58 | class_addMethod(self,
59 | altSel_,
60 | class_getMethodImplementation(self, altSel_),
61 | method_getTypeEncoding(altMethod));
62 |
63 | method_exchangeImplementations(class_getInstanceMethod(self, origSel_), class_getInstanceMethod(self, altSel_));
64 | return YES;
65 | #else
66 | // Scan for non-inherited methods.
67 | Method directOriginalMethod = NULL, directAlternateMethod = NULL;
68 |
69 | void *iterator = NULL;
70 | struct objc_method_list *mlist = class_nextMethodList(self, &iterator);
71 | while (mlist) {
72 | int method_index = 0;
73 | for (; method_index < mlist->method_count; method_index++) {
74 | if (mlist->method_list[method_index].method_name == origSel_) {
75 | assert(!directOriginalMethod);
76 | directOriginalMethod = &mlist->method_list[method_index];
77 | }
78 | if (mlist->method_list[method_index].method_name == altSel_) {
79 | assert(!directAlternateMethod);
80 | directAlternateMethod = &mlist->method_list[method_index];
81 | }
82 | }
83 | mlist = class_nextMethodList(self, &iterator);
84 | }
85 |
86 | // If either method is inherited, copy it up to the target class to make it non-inherited.
87 | if (!directOriginalMethod || !directAlternateMethod) {
88 | Method inheritedOriginalMethod = NULL, inheritedAlternateMethod = NULL;
89 | if (!directOriginalMethod) {
90 | inheritedOriginalMethod = class_getInstanceMethod(self, origSel_);
91 | if (!inheritedOriginalMethod) {
92 | SetNSError(error_, @"original method %@ not found for class %@", NSStringFromSelector(origSel_), [self className]);
93 | return NO;
94 | }
95 | }
96 | if (!directAlternateMethod) {
97 | inheritedAlternateMethod = class_getInstanceMethod(self, altSel_);
98 | if (!inheritedAlternateMethod) {
99 | SetNSError(error_, @"alternate method %@ not found for class %@", NSStringFromSelector(altSel_), [self className]);
100 | return NO;
101 | }
102 | }
103 |
104 | int hoisted_method_count = !directOriginalMethod && !directAlternateMethod ? 2 : 1;
105 | struct objc_method_list *hoisted_method_list = malloc(sizeof(struct objc_method_list) + (sizeof(struct objc_method)*(hoisted_method_count-1)));
106 | hoisted_method_list->obsolete = NULL; // soothe valgrind - apparently ObjC runtime accesses this value and it shows as uninitialized in valgrind
107 | hoisted_method_list->method_count = hoisted_method_count;
108 | Method hoisted_method = hoisted_method_list->method_list;
109 |
110 | if (!directOriginalMethod) {
111 | bcopy(inheritedOriginalMethod, hoisted_method, sizeof(struct objc_method));
112 | directOriginalMethod = hoisted_method++;
113 | }
114 | if (!directAlternateMethod) {
115 | bcopy(inheritedAlternateMethod, hoisted_method, sizeof(struct objc_method));
116 | directAlternateMethod = hoisted_method;
117 | }
118 | class_addMethods(self, hoisted_method_list);
119 | }
120 |
121 | // Swizzle.
122 | IMP temp = directOriginalMethod->method_imp;
123 | directOriginalMethod->method_imp = directAlternateMethod->method_imp;
124 | directAlternateMethod->method_imp = temp;
125 |
126 | return YES;
127 | #endif
128 | }
129 |
130 | + (BOOL)jr_swizzleClassMethod:(SEL)origSel_ withClassMethod:(SEL)altSel_ error:(NSError**)error_ {
131 | return [GetClass((id)self) jr_swizzleMethod:origSel_ withMethod:altSel_ error:error_];
132 | }
133 |
134 | @end
135 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKAutoReplyModel.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyModel.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/18.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKBaseModel.h"
10 |
11 | @interface TKAutoReplyModel : TKBaseModel
12 |
13 | @property (nonatomic, assign) BOOL enable; /**< 是否开启自动回复 */
14 | @property (nonatomic, copy) NSString *keyword; /**< 自动回复关键字 */
15 | @property (nonatomic, copy) NSString *replyContent; /**< 自动回复的内容 */
16 | @property (nonatomic, assign) BOOL enableGroupReply; /**< 是否开启群聊自动回复 */
17 | @property (nonatomic, assign) BOOL enableSingleReply; /**< 是否开启私聊自动回复 */
18 | @property (nonatomic, assign) BOOL enableRegex; /**< 是否开启正则匹配 */
19 |
20 | - (BOOL)hasEmptyKeywordOrReplyContent;
21 |
22 | @end
23 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKAutoReplyModel.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyModel.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/18.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKAutoReplyModel.h"
10 |
11 | @implementation TKAutoReplyModel
12 |
13 | - (instancetype)initWithDict:(NSDictionary *)dict {
14 | self = [super init];
15 | if (self) {
16 | self.enable = [dict[@"enable"] boolValue];
17 | self.keyword = dict[@"keyword"];
18 | self.replyContent = dict[@"replyContent"];
19 | self.enableGroupReply = [dict[@"enableGroupReply"] boolValue];
20 | self.enableSingleReply = [dict[@"enableSingleReply"] boolValue];
21 | self.enableRegex = [dict[@"enableRegex"] boolValue];
22 | }
23 | return self;
24 | }
25 |
26 | - (NSDictionary *)dictionary {
27 | return @{@"enable": @(self.enable),
28 | @"keyword": self.keyword,
29 | @"replyContent": self.replyContent,
30 | @"enableGroupReply": @(self.enableGroupReply),
31 | @"enableSingleReply": @(self.enableSingleReply),
32 | @"enableRegex": @(self.enableRegex)};
33 | }
34 |
35 | - (BOOL)hasEmptyKeywordOrReplyContent {
36 | return (self.keyword == nil || self.replyContent == nil || [self.keyword isEqualToString:@""] || [self.replyContent isEqualToString:@""]);
37 | }
38 |
39 | @end
40 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKBaseModel.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKBaseModel.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/17.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface TKBaseModel : NSObject
12 |
13 | - (instancetype)initWithDict:(NSDictionary *)dict;
14 | - (NSDictionary *)dictionary;
15 |
16 | @end
17 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKBaseModel.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKBaseModel.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/17.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKBaseModel.h"
10 |
11 | @implementation TKBaseModel
12 |
13 | - (instancetype)initWithDict:(NSDictionary *)dict {
14 | NSAssert(NO, @"the mothed initWithDict: must be override by subclass");
15 | return nil;
16 | }
17 |
18 | - (NSDictionary *)dictionary {
19 | NSAssert(NO, @"the mothed dictionary must be override by subclass");
20 | return nil;
21 | }
22 | @end
23 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKIgnoreSessonModel.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKIgnoreSessonModel.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/15.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKBaseModel.h"
10 |
11 | @interface TKIgnoreSessonModel : TKBaseModel
12 |
13 | @property (nonatomic, copy) NSString *selfContact;
14 | @property (nonatomic, copy) NSString *userName;
15 | @property (nonatomic, assign) BOOL ignore;
16 |
17 | @end
18 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKIgnoreSessonModel.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKIgnoreSessonModel.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/9/15.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKIgnoreSessonModel.h"
10 |
11 | @implementation TKIgnoreSessonModel
12 |
13 | - (instancetype)initWithDict:(NSDictionary *)dict {
14 | self = [super init];
15 | if (self) {
16 | self.selfContact = dict[@"selfContact"];
17 | self.userName = dict[@"userName"];
18 | self.ignore = [dict[@"ignore"] boolValue];
19 | }
20 | return self;
21 | }
22 |
23 | - (NSDictionary *)dictionary {
24 | return @{@"selfContact": self.selfContact,
25 | @"userName": self.userName,
26 | @"ignore": @(self.ignore)};
27 | }
28 |
29 | @end
30 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKRemoteControlModel.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlModel.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKBaseModel.h"
10 |
11 | @interface TKRemoteControlModel : TKBaseModel
12 |
13 | @property (nonatomic, assign) BOOL enable;
14 | @property (nonatomic, copy) NSString *keyword;
15 | @property (nonatomic, copy) NSString *function;
16 | @property (nonatomic, copy) NSString *executeCommand;
17 | @property (nonatomic, copy) NSString *command;
18 |
19 | @end
20 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Models/TKRemoteControlModel.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlModel.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKRemoteControlModel.h"
10 |
11 | @implementation TKRemoteControlModel
12 |
13 | - (instancetype)initWithDict:(NSDictionary *)dict {
14 | self = [super init];
15 | if (self) {
16 | self.enable = [dict[@"enable"] boolValue];
17 | self.keyword = dict[@"keyword"];
18 | self.function = dict[@"function"];
19 | self.executeCommand = dict[@"executeCommand"];
20 | self.command = dict[@"command"];
21 | }
22 | return self;
23 | }
24 |
25 | - (NSDictionary *)dictionary {
26 | return @{@"enable": @(self.enable),
27 | @"keyword": self.keyword,
28 | @"function": self.function,
29 | @"executeCommand": self.executeCommand,
30 | @"command": self.command};
31 | }
32 |
33 | @end
34 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Status/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Status/Model/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatus.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatus.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | typedef NS_ENUM(NSUInteger, MMStatusMediaObjectType) {
12 | MMStatusMediaObjectTypeNone,
13 | MMStatusMediaObjectTypeImage,
14 | MMStatusMediaObjectTypeLink,
15 | };
16 |
17 | @class MMStatusMediaObject;
18 |
19 | @interface MMStatus : NSObject
20 |
21 | @property (nonatomic, assign) NSUInteger statusId;
22 | @property (nonatomic, strong) NSString *profileImageURLString;
23 | @property (nonatomic, strong) NSImage *profileImage;
24 | @property (nonatomic, strong) NSString *nameString;
25 | @property (nonatomic, strong) NSString *timeString;
26 | @property (nonatomic, strong) NSString *sourceString;
27 | @property (nonatomic, strong) NSAttributedString *contentAttributedString;
28 | @property (nonatomic, assign) MMStatusMediaObjectType mediaType;
29 | @property (nonatomic, strong) MMStatusMediaObject *mediaObject;
30 |
31 | - (void)updateWithSnsObject:(SnsObject *)snsObject;
32 |
33 | -(void)valiateData;
34 |
35 | - (BOOL)hasSource;
36 | - (BOOL)hasContent;
37 | - (BOOL)hasMediaObject;
38 |
39 | @end
40 |
41 |
42 |
43 | @interface MMStatusSimple : NSObject
44 |
45 | @property (nonatomic, assign) NSUInteger statusId;
46 | @property (nonatomic, strong) NSString *profileImageURLString;
47 | @property (nonatomic, strong) NSString *nameString;
48 | @property (nonatomic, strong) NSString *timeString;
49 | @property (nonatomic, strong) NSString *sourceString;
50 | @property (nonatomic, strong) NSString * contentstring;
51 | @property (nonatomic, assign) MMStatusMediaObjectType mediaType;
52 | @property (nonatomic, strong) MMStatusMediaObject *mediaObject;
53 |
54 | - (void)updateWithSnsObject:(SnsObject *)snsObject;
55 |
56 |
57 | @end
58 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatus.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatus.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/3/24.
6 | // Copyright © 2017年 nato. All rights reserved.
7 | //
8 |
9 | #import "MMStatus.h"
10 | #import "NSDate+StatusTimeDescription.h"
11 | #import "NSString+XMLDictionary.h"
12 |
13 | @implementation MMStatus
14 |
15 | - (void)updateWithSnsObject:(SnsObject *)snsObject {
16 | _statusId = snsObject.id;
17 | WCContactData *contact = [[[CBGetClass(MMServiceCenter) defaultCenter] getService:CBGetClass(ContactStorage)] GetContact:snsObject.username];
18 | _profileImageURLString = contact.m_nsHeadImgUrl;
19 | _nameString = contact.m_nsRemark.length ? contact.m_nsRemark : contact.m_nsNickName;
20 | _timeString = [[NSDate dateWithTimeIntervalSince1970:snsObject.createTime] statusTimeDescription];
21 |
22 | NSString *timeLineObj = [[NSString alloc] initWithData:snsObject.objectDesc.buffer encoding:NSUTF8StringEncoding];
23 | timeLineObj = [timeLineObj stringByReplacingOccurrencesOfString:@"
" withString:@"\n"];
24 |
25 | NSDictionary *timeLineObjDic = [timeLineObj xmlDictionary][@"TimelineObject"];
26 | NSLog(@"%@", timeLineObjDic);
27 |
28 | NSDictionary *contentObjDic = timeLineObjDic[@"ContentObject"];
29 |
30 | NSString *content = timeLineObjDic[@"contentDesc"];
31 | NSMutableAttributedString *contentAttributedString = [NSMutableAttributedString new];
32 |
33 | if ([content isKindOfClass:[NSString class]] && content.length) {
34 | [contentAttributedString appendAttributedString:[[NSAttributedString alloc] initWithString:content attributes:@{NSFontAttributeName: [NSFont systemFontOfSize:13]}]];
35 | }
36 | self.contentAttributedString = contentAttributedString;
37 |
38 | NSString *appName = timeLineObjDic[@"appInfo"][@"appName"];
39 | if ([appName isKindOfClass:[NSString class]] && appName.length) {
40 | _sourceString = appName;
41 | }
42 |
43 | NSString *contentStyle = contentObjDic[@"contentStyle"];
44 | contentStyle = [contentStyle stringByReplacingOccurrencesOfString:@"![CDATA[" withString:@""];
45 | contentStyle = [contentStyle stringByReplacingOccurrencesOfString:@"]" withString:@""];
46 | NSInteger mediaStyle = [contentStyle integerValue];
47 | NSArray *mediaList = contentObjDic[@"mediaList"][@"media"];
48 | if ([mediaList isKindOfClass:[NSDictionary class]]) {
49 | if (mediaList.count) {
50 | mediaList = @[mediaList];
51 | }
52 | else {
53 | mediaList = nil;
54 | }
55 | }
56 |
57 | if (mediaStyle == 1) {
58 | self.mediaType = MMStatusMediaObjectTypeImage;
59 | MMStatusImageMediaObject *mediaObject = [MMStatusImageMediaObject new];
60 | NSMutableArray *imageInfos = [NSMutableArray new];
61 | for (NSDictionary *media in mediaList) {
62 | MMStatusImageInfo *image = [MMStatusImageInfo new];
63 | image.imageURLString = media[@"url"];
64 | image.imageWidth = [media[@"size"][@"width"] doubleValue];
65 | image.imageHeight = [media[@"size"][@"height"] doubleValue];
66 | [imageInfos addObject:image];
67 | }
68 | mediaObject.imageInfos = imageInfos.copy;
69 | self.mediaObject = mediaObject;
70 | }
71 | else if (mediaStyle == 3 || mediaStyle == 4 || mediaStyle == 5) {
72 | self.mediaType = MMStatusMediaObjectTypeLink;
73 | NSDictionary *media = mediaList.firstObject;
74 | NSString *title = contentObjDic[@"title"];
75 | if (![title isKindOfClass:[NSString class]]) {
76 | title = media[@"title"];
77 | }
78 | MMStatusLinkMediaObject *mediaObject = [MMStatusLinkMediaObject new];
79 | mediaObject.linkURLString = contentObjDic[@"contentUrl"];
80 | mediaObject.title = title;
81 | mediaObject.imageURLString = media[@"thumb"];
82 | self.mediaObject = mediaObject;
83 | }
84 | }
85 | -(void)valiateData{
86 | _sourceString = _sourceString?_sourceString:@"";
87 | _profileImageURLString = _profileImageURLString?_profileImageURLString:@"";
88 | _nameString = _nameString?_nameString:@"";
89 |
90 | }
91 | - (BOOL)hasSource {
92 | return self.sourceString.length;
93 | }
94 |
95 | - (BOOL)hasContent {
96 | return self.contentAttributedString.length;
97 | }
98 |
99 | - (BOOL)hasMediaObject {
100 | return self.mediaType != MMStatusMediaObjectTypeNone;
101 | }
102 |
103 | @end
104 |
105 |
106 |
107 |
108 |
109 | @implementation MMStatusSimple
110 |
111 | - (void)updateWithSnsObject:(SnsObject *)snsObject {
112 | _statusId = snsObject.id;
113 | WCContactData *contact = [[[CBGetClass(MMServiceCenter) defaultCenter] getService:CBGetClass(ContactStorage)] GetContact:snsObject.username];
114 | _profileImageURLString = contact.m_nsHeadImgUrl;
115 | _nameString = contact.m_nsRemark.length ? contact.m_nsRemark : contact.m_nsNickName;
116 | _timeString = [[NSDate dateWithTimeIntervalSince1970:snsObject.createTime] statusTimeDescription];
117 |
118 | NSString *timeLineObj = [[NSString alloc] initWithData:snsObject.objectDesc.buffer encoding:NSUTF8StringEncoding];
119 | timeLineObj = [timeLineObj stringByReplacingOccurrencesOfString:@"
" withString:@"\n"];
120 |
121 | NSDictionary *timeLineObjDic = [timeLineObj xmlDictionary][@"TimelineObject"];
122 | NSLog(@"%@", timeLineObjDic);
123 |
124 | NSDictionary *contentObjDic = timeLineObjDic[@"ContentObject"];
125 |
126 | NSString *content = timeLineObjDic[@"contentDesc"];
127 | // NSMutableAttributedString *contentAttributedString = [NSMutableAttributedString new];
128 | //
129 | // if ([content isKindOfClass:[NSString class]] && content.length) {
130 | // [contentAttributedString appendAttributedString:[[NSAttributedString alloc] initWithString:content attributes:@{NSFontAttributeName: [NSFont systemFontOfSize:13]}]];
131 | // }
132 | self.contentstring = content;
133 |
134 | NSString *appName = timeLineObjDic[@"appInfo"][@"appName"];
135 | if ([appName isKindOfClass:[NSString class]] && appName.length) {
136 | _sourceString = appName;
137 | }
138 |
139 | NSString *contentStyle = contentObjDic[@"contentStyle"];
140 | contentStyle = [contentStyle stringByReplacingOccurrencesOfString:@"![CDATA[" withString:@""];
141 | contentStyle = [contentStyle stringByReplacingOccurrencesOfString:@"]" withString:@""];
142 | NSInteger mediaStyle = [contentStyle integerValue];
143 | NSArray *mediaList = contentObjDic[@"mediaList"][@"media"];
144 | if ([mediaList isKindOfClass:[NSDictionary class]]) {
145 | if (mediaList.count) {
146 | mediaList = @[mediaList];
147 | }
148 | else {
149 | mediaList = nil;
150 | }
151 | }
152 |
153 | if (mediaStyle == 1) {
154 | self.mediaType = MMStatusMediaObjectTypeImage;
155 | MMStatusImageMediaObject *mediaObject = [MMStatusImageMediaObject new];
156 | NSMutableArray *imageInfos = [NSMutableArray new];
157 | for (NSDictionary *media in mediaList) {
158 | MMStatusImageInfo *image = [MMStatusImageInfo new];
159 | image.imageURLString = media[@"url"];
160 | image.imageWidth = [media[@"size"][@"width"] doubleValue];
161 | image.imageHeight = [media[@"size"][@"height"] doubleValue];
162 | [imageInfos addObject:image];
163 | }
164 | mediaObject.imageInfos = imageInfos.copy;
165 | self.mediaObject = mediaObject;
166 | }
167 | else if (mediaStyle == 3 || mediaStyle == 4 || mediaStyle == 5) {
168 | self.mediaType = MMStatusMediaObjectTypeLink;
169 | NSDictionary *media = mediaList.firstObject;
170 | NSString *title = contentObjDic[@"title"];
171 | if (![title isKindOfClass:[NSString class]]) {
172 | title = media[@"title"];
173 | }
174 | MMStatusLinkMediaObject *mediaObject = [MMStatusLinkMediaObject new];
175 | mediaObject.linkURLString = contentObjDic[@"contentUrl"];
176 | mediaObject.title = title;
177 | mediaObject.imageURLString = media[@"thumb"];
178 | self.mediaObject = mediaObject;
179 | }
180 | }
181 | @end
182 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatusImageMediaObject.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusImageMediaObject.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusMediaObject.h"
10 |
11 | @interface MMStatusImageInfo : NSObject
12 |
13 | @property (nonatomic, strong) NSString *imageURLString;
14 | @property (nonatomic, strong) NSImage *image;
15 | @property (nonatomic, assign) CGFloat imageWidth;
16 | @property (nonatomic, assign) CGFloat imageHeight;
17 |
18 | @end
19 |
20 | @interface MMStatusImageMediaObject : MMStatusMediaObject
21 |
22 | @property (nonatomic, strong) NSArray *imageInfos;
23 |
24 | @end
25 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatusImageMediaObject.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusImageMediaObject.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusImageMediaObject.h"
10 |
11 | @implementation MMStatusImageInfo
12 |
13 | @end
14 | @implementation MMStatusImageMediaObject
15 |
16 | @end
17 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatusLinkMediaObject.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusLinkMediaObject.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusMediaObject.h"
10 |
11 | @interface MMStatusLinkMediaObject : MMStatusMediaObject
12 |
13 | @property (nonatomic, strong) NSString *imageURLString;
14 | @property (nonatomic, strong) NSImage *image;
15 | @property (nonatomic, strong) NSString *title;
16 | @property (nonatomic, strong) NSString *linkURLString;
17 |
18 | @end
19 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatusLinkMediaObject.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusLinkMediaObject.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusLinkMediaObject.h"
10 |
11 | @implementation MMStatusLinkMediaObject
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatusMediaObject.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusMediaObject.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface MMStatusMediaObject : NSObject
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/Model/MMStatusMediaObject.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusMediaObject.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusMediaObject.h"
10 |
11 | @implementation MMStatusMediaObject
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Status/View/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusCell.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusCell.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "MMStatusCellDelegate.h"
11 |
12 | @class MMStatusMediaView;
13 | @class MMStatus;
14 |
15 | @interface MMStatusCell : NSTableCellView
16 |
17 | @property (weak) IBOutlet NSImageView *profileImageView;
18 | @property (weak) IBOutlet NSTextField *nameTextField;
19 | @property (weak) IBOutlet NSTextField *tagTextField;
20 | @property (weak) IBOutlet NSTextField *contentTextField;
21 | @property (weak) IBOutlet MMStatusMediaView *mediaView;
22 | @property (weak) MMStatusMediaView *mediaRealView;
23 |
24 | @property (nonatomic, strong, readonly) MMStatus *status;
25 | @property (nonatomic, weak) id delegate;
26 |
27 | @property (strong) IBOutlet NSLayoutConstraint *toTagTextFieldLayoutConstraint;
28 | @property (strong) IBOutlet NSLayoutConstraint *toContentTextFieldLayoutConstraint;
29 |
30 | - (void)updateMediaView:(MMStatusMediaView *)mediaView;
31 | - (void)updateViewWithStatus:(MMStatus *)status;
32 |
33 | + (CGFloat)calculateHeightForStatus:(MMStatus *)status inTableView:(NSTableView *)tableView;
34 |
35 | @end
36 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusCell.xib:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusCellDelegate.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusCellDelegate.h
3 | // WeChatPlugin
4 | //
5 | // Created by nato on 2017/3/25.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @class MMStatusCell;
12 | @class MMStatusImageInfo;
13 | @protocol MMStatusCellDelegate
14 |
15 | @optional
16 | - (void)cell:(MMStatusCell *)cell didClickMediaLink:(NSString *)url;
17 | - (void)cell:(MMStatusCell *)cell didClickMediaImage:(MMStatusImageInfo *)imageInfo;
18 |
19 | @end
20 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusImageMediaView.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusImageMediaView.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusMediaView.h"
10 |
11 | @interface MMStatusImageMediaView : MMStatusMediaView
12 |
13 | @property (weak) IBOutlet NSImageView *imageView0;
14 | @property (weak) IBOutlet NSImageView *imageView1;
15 | @property (weak) IBOutlet NSImageView *imageView2;
16 | @property (weak) IBOutlet NSImageView *imageView3;
17 | @property (weak) IBOutlet NSImageView *imageView4;
18 | @property (weak) IBOutlet NSImageView *imageView5;
19 | @property (weak) IBOutlet NSImageView *imageView6;
20 | @property (weak) IBOutlet NSImageView *imageView7;
21 | @property (weak) IBOutlet NSImageView *imageView8;
22 |
23 | @property (nonatomic, strong, readonly) NSArray *imageViews;
24 |
25 | @end
26 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusImageMediaView.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusImageMediaView.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusImageMediaView.h"
10 |
11 | @implementation MMStatusImageMediaView
12 |
13 | - (void)awakeFromNib {
14 | [super awakeFromNib];
15 | _imageViews = @[self.imageView0, self.imageView1, self.imageView2, self.imageView3, self.imageView4, self.imageView5, self.imageView6, self.imageView7, self.imageView8];
16 | for (NSImageView *imageView in _imageViews) {
17 | imageView.imageAlignment = NSImageAlignTopLeft;
18 | imageView.wantsLayer = true;
19 | imageView.layer.borderColor = [NSColor whiteColor].CGColor;
20 | imageView.layer.borderWidth = 1;
21 | }
22 | }
23 |
24 | @end
25 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusImagePreviewView.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusImagePreviewView.h
3 | // WeChatPlugin
4 | //
5 | // Created by Loveletter on 26/02/2018.
6 | // Copyright © 2018 CodeTips. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface MMStatusImagePreviewView : NSImageView
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusImagePreviewView.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusImagePreviewView.m
3 | // WeChatPlugin
4 | //
5 | // Created by Loveletter on 26/02/2018.
6 | // Copyright © 2018 CodeTips. All rights reserved.
7 | //
8 |
9 | #import "MMStatusImagePreviewView.h"
10 |
11 | @implementation MMStatusImagePreviewView
12 |
13 | - (void) mouseDown:(NSEvent *)theEvent
14 | {
15 | [self removeFromSuperview];
16 | }
17 |
18 | @end
19 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusLinkMediaView.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusLinkMediaView.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusMediaView.h"
10 |
11 | @interface MMStatusLinkMediaView : MMStatusMediaView
12 |
13 | @property (weak) IBOutlet NSImageView *iconImageView;
14 | @property (weak) IBOutlet NSTextField *titleTextField;
15 |
16 | @end
17 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusLinkMediaView.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusLinkMediaView.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusLinkMediaView.h"
10 |
11 | @implementation MMStatusLinkMediaView
12 |
13 | - (void)awakeFromNib {
14 | [super awakeFromNib];
15 | self.wantsLayer = true;
16 | self.layer.backgroundColor = [NSColor colorWithWhite:0.9 alpha:1.0].CGColor;
17 | self.iconImageView.wantsLayer = true;
18 | self.iconImageView.layer.backgroundColor = [NSColor colorWithWhite:0.9 alpha:1.0].CGColor;
19 | }
20 |
21 | - (void)drawRect:(NSRect)dirtyRect {
22 | [super drawRect:dirtyRect];
23 | }
24 |
25 | @end
26 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusLinkMediaView.xib:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusMediaView.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusMediaView.h
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface MMStatusMediaView : NSTableCellView
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Status/View/MMStatusMediaView.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMStatusMediaView.m
3 | // WeChatTimeLine
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMStatusMediaView.h"
10 |
11 | @implementation MMStatusMediaView
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/TimeLine/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Controller/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/TimeLine/Controller/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Controller/MMTimeLineMainViewController.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMTimeLineMainViewController.h
3 | // MacWeChatTimeLinePlugin
4 | //
5 | // Created by nato on 16/8/16.
6 | // Copyright © 2016年 nato. All rights reserved.
7 | //
8 |
9 | #import "WeChatPlugin.h"
10 |
11 | @interface MMTimeLineMainViewController : MMContactsViewController
12 |
13 | - (void)tableView:(MMTableView *)arg1 rowGotMouseDown:(long long)arg2;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Controller/MMTimeLineViewController.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMTimeLineViewController.h
3 | // WeChatPlugin
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface MMTimeLineViewController : NSViewController
12 |
13 | @property (weak) IBOutlet NSTableView *tableView;
14 | @property (weak) IBOutlet NSView *line;
15 |
16 | @end
17 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Mgr/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/TimeLine/Mgr/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Mgr/MMTimeLineMgr.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMTimeLineMgr.h
3 | // WeChatPlugin
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "MMTimeLineMgrDelegate.h"
11 |
12 | @class MMStatus;
13 |
14 | @interface MMTimeLineMgr : NSObject
15 |
16 | @property (nonatomic, weak) id delegate;
17 |
18 | - (void)updateTimeLineHead;
19 | - (void)updateTimeLineTail;
20 |
21 | - (NSUInteger)getTimeLineStatusCount;
22 | - (MMStatus *)getTimeLineStatusAtIndex:(NSUInteger)index;
23 |
24 | @property (nonatomic, strong) NSMutableArray * jsonlist;
25 |
26 |
27 | @end
28 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Mgr/MMTimeLineMgr.m:
--------------------------------------------------------------------------------
1 | //
2 | // MMTimeLineMgr.m
3 | // WeChatPlugin
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import "MMTimeLineMgr.h"
10 | #import "NSObject+ObjectMap.h"
11 | @interface MMTimeLineMgr ()
12 |
13 | @property (nonatomic, assign, getter=isRequesting) BOOL requesting;
14 | @property (nonatomic, strong) NSString *firstPageMd5;
15 | @property (nonatomic, strong) SKBuiltinBuffer_t *session;
16 | @property (nonatomic, strong) NSMutableArray *statuses;
17 |
18 | @end
19 |
20 | @implementation MMTimeLineMgr
21 |
22 | #pragma mark - Network
23 |
24 | - (void)updateTimeLineHead {
25 | [self requestTimeLineDataAfterItemID:0];
26 | }
27 |
28 | - (void)updateTimeLineTail {
29 | MMStatus *status = [self.statuses lastObject];
30 | [self requestTimeLineDataAfterItemID:status.statusId];
31 | }
32 |
33 | - (void)requestTimeLineDataAfterItemID:(unsigned long long)itemID {
34 | if (self.isRequesting) {
35 | return;
36 | }
37 | self.requesting = true;
38 | SnsTimeLineRequest *request = [[CBGetClass(SnsTimeLineRequest) alloc] init];
39 | request.baseRequest = [CBGetClass(MMCGIRequestUtil) InitBaseRequestWithScene:0];
40 | request.clientLatestId = 0;
41 | request.firstPageMd5 = itemID == 0 ? self.firstPageMd5 : @"";
42 | request.lastRequestTime = 0;
43 | request.maxId = itemID;
44 | request.minFilterId = 0;
45 | request.session = self.session;
46 | MMCGIWrap *cgiWrap = [[CBGetClass(MMCGIWrap) alloc] init];
47 | cgiWrap.m_requestPb = request;
48 | cgiWrap.m_functionId = kMMCGIWrapTimeLineFunctionId;
49 |
50 | MMCGIService *cgiService = [[CBGetClass(MMServiceCenter) defaultCenter] getService:CBGetClass(MMCGIService)];
51 | [cgiService RequestCGI:cgiWrap delegate:self];
52 |
53 | }
54 |
55 | - (NSMutableArray *)jsonlist {
56 | if (!_jsonlist) {
57 | _jsonlist = [[NSMutableArray alloc] init];
58 | }
59 | return _jsonlist;
60 | }
61 | #pragma mark - MMCGIDelegate
62 |
63 | - (void)OnResponseCGI:(BOOL)arg1 sessionId:(unsigned int)arg2 cgiWrap:(MMCGIWrap *)cgiWrap {
64 | NSLog(@"%d %d %@", arg1, arg2, cgiWrap);
65 | SnsTimeLineRequest *request = (SnsTimeLineRequest *)cgiWrap.m_requestPb;
66 | SnsTimeLineResponse *response = (SnsTimeLineResponse *)cgiWrap.m_responsePb;
67 |
68 | self.session = response.session;
69 | NSMutableArray *statuses = [NSMutableArray new];
70 | NSString * jsonstr = @"";
71 | for (SnsObject *snsObject in response.objectList) {
72 | MMStatus *status = [MMStatus new];
73 | [status updateWithSnsObject:snsObject];
74 | [statuses addObject:status];
75 |
76 | MMStatusSimple *st = [MMStatusSimple new];
77 | [st updateWithSnsObject:snsObject];
78 | NSString * stajson = [st JSONString];
79 | jsonstr = [jsonstr stringByAppendingFormat:@"%@,",stajson];
80 | }
81 | jsonstr = [jsonstr stringByAppendingFormat:@""];
82 | NSLog(@"\n\njson:\n%@\n\n",jsonstr);
83 |
84 | dispatch_async(dispatch_get_main_queue(), ^{
85 | BOOL isRefresh = request.maxId == 0;
86 | if (isRefresh) {
87 | self.firstPageMd5 = response.firstPageMd5;
88 | if (statuses.count) {
89 | self.statuses = statuses;
90 | }
91 | self.jsonlist = [@[jsonstr] mutableCopy];
92 | }
93 | else {
94 | [self.statuses addObjectsFromArray:statuses];
95 | [self.jsonlist addObject:jsonstr];
96 | }
97 | self.requesting = false;
98 | if (self.delegate && [self.delegate respondsToSelector:@selector(onTimeLineStatusChange)]) {
99 | [self.delegate onTimeLineStatusChange];
100 | }
101 | });
102 | }
103 |
104 | #pragma mark -
105 |
106 | - (NSUInteger)getTimeLineStatusCount {
107 | return [self.statuses count];
108 | }
109 |
110 | - (MMStatus *)getTimeLineStatusAtIndex:(NSUInteger)index {
111 | if (index >= self.statuses.count) {
112 | return nil;
113 | }
114 | else {
115 | return self.statuses[index];
116 | }
117 | }
118 |
119 | @end
120 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/Mgr/MMTimeLineMgrDelegate.h:
--------------------------------------------------------------------------------
1 | //
2 | // MMTimeLineMgrDelegate.h
3 | // WeChatPlugin
4 | //
5 | // Created by nato on 2017/1/22.
6 | // Copyright © 2017年 github:natoto. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @protocol MMTimeLineMgrDelegate
12 |
13 | - (void)onTimeLineStatusChange;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/View/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/TimeLine/View/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/TimeLine/View/MMTimeLineViewController.xib:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Utils/.DS_Store:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/Sources/Utils/.DS_Store
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Utils/TKHelper.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKHelper.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 | #import
11 |
12 | @interface TKHelper : NSObject
13 |
14 | /**
15 | 替换对象方法
16 |
17 | @param originalClass 原始类
18 | @param originalSelector 原始类的方法
19 | @param swizzledClass 替换类
20 | @param swizzledSelector 替换类的方法
21 | */
22 | void tk_hookMethod(Class originalClass, SEL originalSelector, Class swizzledClass, SEL swizzledSelector);
23 |
24 | /**
25 | 替换类方法
26 |
27 | @param originalClass 原始类
28 | @param originalSelector 原始类的类方法
29 | @param swizzledClass 替换类
30 | @param swizzledSelector 替换类的类方法
31 | */
32 | void tk_hookClassMethod(Class originalClass, SEL originalSelector, Class swizzledClass, SEL swizzledSelector);
33 |
34 | void tk_addMethod(Class originalClass,Class swizzledClass, SEL swizzledSelector);
35 |
36 | @end
37 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Utils/TKHelper.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKHelper.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKHelper.h"
10 |
11 | @implementation TKHelper
12 |
13 | /**
14 | 替换对象方法
15 |
16 | @param originalClass 原始类
17 | @param originalSelector 原始类的方法
18 | @param swizzledClass 替换类
19 | @param swizzledSelector 替换类的方法
20 | */
21 | void tk_hookMethod(Class originalClass, SEL originalSelector, Class swizzledClass, SEL swizzledSelector) {
22 | Method originalMethod = class_getInstanceMethod(originalClass, originalSelector);
23 | Method swizzledMethod = class_getInstanceMethod(swizzledClass, swizzledSelector);
24 | if(originalMethod && swizzledMethod) {
25 | method_exchangeImplementations(originalMethod, swizzledMethod);
26 | }
27 | }
28 |
29 | /**
30 | 替换类方法
31 |
32 | @param originalClass 原始类
33 | @param originalSelector 原始类的类方法
34 | @param swizzledClass 替换类
35 | @param swizzledSelector 替换类的类方法
36 | */
37 | void tk_hookClassMethod(Class originalClass, SEL originalSelector, Class swizzledClass, SEL swizzledSelector) {
38 | Method originalMethod = class_getClassMethod(originalClass, originalSelector);
39 | Method swizzledMethod = class_getClassMethod(swizzledClass, swizzledSelector);
40 | if(originalMethod && swizzledMethod) {
41 | method_exchangeImplementations(originalMethod, swizzledMethod);
42 | }
43 | }
44 |
45 | void tk_addMethod(Class originalClass,Class swizzledClass, SEL swizzledSelector)
46 | {
47 | Method swizzledMethod = class_getInstanceMethod(swizzledClass, swizzledSelector);
48 | class_addMethod(originalClass,swizzledSelector,method_getImplementation(swizzledMethod),method_getTypeEncoding(swizzledMethod));
49 | }
50 |
51 | @end
52 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Utils/XMLReader.h:
--------------------------------------------------------------------------------
1 | //
2 | // XmlReader.h
3 | // XmlReader
4 | //
5 | // Created by Benoit C on 10/31/13.
6 | // Copyright (c) 2013 Benoit Caccinolo. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 |
12 | @interface XMLReader : NSObject
13 | {
14 | NSMutableArray *dictionaryStack;
15 | NSMutableString *textInProgress;
16 | // NSError **errorPointer;
17 | }
18 |
19 | + (NSDictionary *)dictionaryForXMLData:(NSData *)data error:(NSError **)errorPointer;
20 | + (NSDictionary *)dictionaryForXMLString:(NSString *)string error:(NSError **)errorPointer;
21 |
22 | @end
23 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Utils/XMLReader.m:
--------------------------------------------------------------------------------
1 | //
2 | // XmlReader.m
3 | // XmlReader
4 | //
5 | // Created by Benoit C on 10/31/13.
6 | // Copyright (c) 2013 Benoit Caccinolo. All rights reserved.
7 | //
8 |
9 | #import "XMLReader.h"
10 |
11 | NSString *const kXMLReaderTextNodeKey = @"text";
12 |
13 | @interface XMLReader (Internal)
14 |
15 | - (id)initWithError:(NSError **)error;
16 | - (NSDictionary *)objectWithData:(NSData *)data;
17 |
18 | @end
19 |
20 |
21 | @implementation XMLReader
22 |
23 | #pragma mark -
24 | #pragma mark Public methods
25 |
26 | + (NSDictionary *)dictionaryForXMLData:(NSData *)data error:(NSError **)error
27 | {
28 | XMLReader *reader = [[XMLReader alloc] initWithError:error];
29 | NSDictionary *rootDictionary = [reader objectWithData:data];
30 | // [reader release];
31 | return rootDictionary;
32 | }
33 |
34 | + (NSDictionary *)dictionaryForXMLString:(NSString *)string error:(NSError **)error
35 | {
36 | NSData *data = [string dataUsingEncoding:NSUTF8StringEncoding];
37 | return [XMLReader dictionaryForXMLData:data error:error];
38 | }
39 |
40 | #pragma mark -
41 | #pragma mark Parsing
42 |
43 | - (id)initWithError:(NSError **)error
44 | {
45 | if (self = [super init])
46 | {
47 | // errorPointer = error;
48 | }
49 | return self;
50 | }
51 |
52 | //- (void)dealloc
53 | //{
54 | // [dictionaryStack release];
55 | // [textInProgress release];
56 | // [super dealloc];
57 | //}
58 |
59 | - (NSDictionary *)objectWithData:(NSData *)data
60 | {
61 | // Clear out any old data
62 | // [dictionaryStack release];
63 | // [textInProgress release];
64 |
65 | dictionaryStack = [[NSMutableArray alloc] init];
66 | textInProgress = [[NSMutableString alloc] init];
67 |
68 | // Initialize the stack with a fresh dictionary
69 | [dictionaryStack addObject:[NSMutableDictionary dictionary]];
70 |
71 | // Parse the XML
72 | NSXMLParser *parser = [[NSXMLParser alloc] initWithData:data];
73 | parser.delegate = self;
74 | BOOL success = [parser parse];
75 |
76 | // Return the stack's root dictionary on success
77 | if (success)
78 | {
79 | NSDictionary *resultDict = [dictionaryStack objectAtIndex:0];
80 | return resultDict;
81 | }
82 |
83 | return nil;
84 | }
85 |
86 | #pragma mark -
87 | #pragma mark NSXMLParserDelegate methods
88 |
89 | - (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict
90 | {
91 | // Get the dictionary for the current level in the stack
92 | NSMutableDictionary *parentDict = [dictionaryStack lastObject];
93 |
94 | // Create the child dictionary for the new element, and initilaize it with the attributes
95 | NSMutableDictionary *childDict = [NSMutableDictionary dictionary];
96 | [childDict addEntriesFromDictionary:attributeDict];
97 |
98 | // If there's already an item for this key, it means we need to create an array
99 | id existingValue = [parentDict objectForKey:elementName];
100 | if (existingValue)
101 | {
102 | NSMutableArray *array = nil;
103 | if ([existingValue isKindOfClass:[NSMutableArray class]])
104 | {
105 | // The array exists, so use it
106 | array = (NSMutableArray *) existingValue;
107 | }
108 | else
109 | {
110 | // Create an array if it doesn't exist
111 | array = [NSMutableArray array];
112 | [array addObject:existingValue];
113 |
114 | // Replace the child dictionary with an array of children dictionaries
115 | [parentDict setObject:array forKey:elementName];
116 | }
117 |
118 | // Add the new child dictionary to the array
119 | [array addObject:childDict];
120 | }
121 | else
122 | {
123 | // No existing value, so update the dictionary
124 | [parentDict setObject:childDict forKey:elementName];
125 | }
126 |
127 | // Update the stack
128 | [dictionaryStack addObject:childDict];
129 | }
130 |
131 | - (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName
132 | {
133 | // Pop the current dict
134 | [dictionaryStack removeLastObject];
135 | // Set the text property
136 | if ([textInProgress length] > 0)
137 | {
138 |
139 | // Update the parent dict with text info
140 | NSMutableDictionary *dictInProgress = [dictionaryStack lastObject];
141 |
142 | [dictInProgress setObject:textInProgress forKey:elementName];
143 |
144 | textInProgress = [[NSMutableString alloc] init];
145 | }
146 | else {
147 |
148 | }
149 | }
150 |
151 | - (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string
152 | {
153 | // Build the text value
154 | [textInProgress appendString:string];
155 | }
156 |
157 | - (void)parser:(NSXMLParser *)parser parseErrorOccurred:(NSError *)parseError
158 | {
159 | // Set the error pointer to the parser's error object
160 | // *errorPointer = parseError;
161 | }
162 |
163 | @end
164 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Vendor/fishhook.h:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2013, Facebook, Inc.
2 | // All rights reserved.
3 | // Redistribution and use in source and binary forms, with or without
4 | // modification, are permitted provided that the following conditions are met:
5 | // * Redistributions of source code must retain the above copyright notice,
6 | // this list of conditions and the following disclaimer.
7 | // * Redistributions in binary form must reproduce the above copyright notice,
8 | // this list of conditions and the following disclaimer in the documentation
9 | // and/or other materials provided with the distribution.
10 | // * Neither the name Facebook nor the names of its contributors may be used to
11 | // endorse or promote products derived from this software without specific
12 | // prior written permission.
13 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
14 | // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15 | // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
16 | // DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
17 | // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
18 | // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
19 | // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
20 | // CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
21 | // OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
22 | // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23 |
24 | #ifndef fishhook_h
25 | #define fishhook_h
26 |
27 | #include
28 | #include
29 |
30 | #if !defined(FISHHOOK_EXPORT)
31 | #define FISHHOOK_VISIBILITY __attribute__((visibility("hidden")))
32 | #else
33 | #define FISHHOOK_VISIBILITY __attribute__((visibility("default")))
34 | #endif
35 |
36 | #ifdef __cplusplus
37 | extern "C" {
38 | #endif //__cplusplus
39 |
40 | /*
41 | * A structure representing a particular intended rebinding from a symbol
42 | * name to its replacement
43 | */
44 | struct rebinding {
45 | const char *name;
46 | void *replacement;
47 | void **replaced;
48 | };
49 |
50 | /*
51 | * For each rebinding in rebindings, rebinds references to external, indirect
52 | * symbols with the specified name to instead point at replacement for each
53 | * image in the calling process as well as for all future images that are loaded
54 | * by the process. If rebind_functions is called more than once, the symbols to
55 | * rebind are added to the existing list of rebindings, and if a given symbol
56 | * is rebound more than once, the later rebinding will take precedence.
57 | */
58 | FISHHOOK_VISIBILITY
59 | int rebind_symbols(struct rebinding rebindings[], size_t rebindings_nel);
60 |
61 | /*
62 | * Rebinds as above, but only in the specified image. The header should point
63 | * to the mach-o header, the slide should be the slide offset. Others as above.
64 | */
65 | FISHHOOK_VISIBILITY
66 | int rebind_symbols_image(void *header,
67 | intptr_t slide,
68 | struct rebinding rebindings[],
69 | size_t rebindings_nel);
70 |
71 | #ifdef __cplusplus
72 | }
73 | #endif //__cplusplus
74 |
75 | #endif //fishhook_h
76 |
77 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Views/AutoReply/TKAutoReplyCell.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyCell.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/21.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "TKAutoReplyModel.h"
11 |
12 | @interface TKAutoReplyCell : NSControl
13 |
14 | @property (nonatomic, strong) TKAutoReplyModel *model;
15 | @property (nonatomic, copy) void (^updateModel)(void);
16 |
17 | @end
18 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Views/AutoReply/TKAutoReplyCell.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyCell.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/21.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKAutoReplyCell.h"
10 |
11 | @interface TKAutoReplyCell ()
12 |
13 | @property (nonatomic, strong) NSButton *selectBtn;
14 | @property (nonatomic, strong) NSTextField *keywordLabel;
15 | @property (nonatomic, strong) NSTextField *replyContentLabel;
16 | @property (nonatomic, strong) NSBox *bottomLine;
17 |
18 | @end
19 |
20 | @implementation TKAutoReplyCell
21 |
22 | - (instancetype)init {
23 | self = [super init];
24 | if (self) {
25 | [self initSubviews];
26 | }
27 | return self;
28 | }
29 |
30 | - (void)initSubviews {
31 | self.selectBtn = ({
32 | NSButton *btn = [NSButton tk_checkboxWithTitle:@"" target:self action:@selector(clickSelectBtn:)];
33 | btn.frame = NSMakeRect(5, 15, 20, 20);
34 |
35 | btn;
36 | });
37 |
38 | self.keywordLabel = ({
39 | NSTextField *label = [NSTextField tk_labelWithString:@""];
40 | label.placeholderString = @"关键字";
41 | [[label cell] setLineBreakMode:NSLineBreakByCharWrapping];
42 | [[label cell] setTruncatesLastVisibleLine:YES];
43 | label.font = [NSFont systemFontOfSize:10];
44 | label.frame = NSMakeRect(30, 30, 160, 15);
45 |
46 | label;
47 | });
48 |
49 | self.replyContentLabel = ({
50 | NSTextField *label = [NSTextField tk_labelWithString:@""];
51 | label.placeholderString = @"回复内容";
52 | [[label cell] setLineBreakMode:NSLineBreakByCharWrapping];
53 | [[label cell] setTruncatesLastVisibleLine:YES];
54 | label.frame = NSMakeRect(30, 10, 160, 15);
55 |
56 | label;
57 | });
58 |
59 | self.bottomLine = ({
60 | NSBox *v = [[NSBox alloc] init];
61 | v.boxType = NSBoxSeparator;
62 | v.frame = NSMakeRect(0, 0, 200, 1);
63 |
64 | v;
65 | });
66 |
67 | [self addSubviews:@[self.selectBtn,
68 | self.keywordLabel,
69 | self.replyContentLabel,
70 | self.bottomLine]];
71 | }
72 |
73 | - (void)clickSelectBtn:(NSButton *)btn {
74 | self.model.enable = btn.state;
75 | if (!self.model.enableSingleReply && !self.model.enableGroupReply && btn.state == YES) {
76 | self.model.enableSingleReply = YES;
77 | if (self.updateModel) self.updateModel();
78 | }
79 | }
80 |
81 | - (void)setModel:(TKAutoReplyModel *)model {
82 | _model = model;
83 | if (model.keyword == nil && model.replyContent == nil) return;
84 |
85 | self.selectBtn.state = model.enable;
86 | self.keywordLabel.stringValue = model.keyword != nil ? model.keyword : @"";
87 | self.replyContentLabel.stringValue = model.replyContent != nil ? model.replyContent : @"";
88 | }
89 |
90 | @end
91 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Views/AutoReply/TKAutoReplyContentView.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyContentView.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/20.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "TKAutoReplyModel.h"
11 |
12 | @interface TKAutoReplyContentView : NSView
13 |
14 | @property (nonatomic, strong) TKAutoReplyModel *model;
15 | @property (nonatomic, copy) void (^endEdit)(void);
16 |
17 | @end
18 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Views/AutoReply/TKAutoReplyContentView.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyContentView.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/20.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKAutoReplyContentView.h"
10 |
11 | @interface TKAutoReplyContentView ()
12 |
13 | @property (nonatomic, strong) NSTextField *keywordLabel;
14 | @property (nonatomic, strong) NSTextField *keywordTextField;
15 | @property (nonatomic, strong) NSTextField *autoReplyLabel;
16 | @property (nonatomic, strong) NSTextField *autoReplyContentField;
17 | @property (nonatomic, strong) NSButton *enableGroupReplyBtn;
18 | @property (nonatomic, strong) NSButton *enableSingleReplyBtn;
19 | @property (nonatomic, strong) NSButton *enableRegexBtn;
20 |
21 | @end
22 |
23 | @implementation TKAutoReplyContentView
24 |
25 | - (instancetype)init {
26 | self = [super init];
27 | if (self) {
28 | [self initSubviews];
29 | }
30 | return self;
31 | }
32 |
33 | - (void)initSubviews {
34 | self.enableRegexBtn = ({
35 | NSButton *btn = [NSButton tk_checkboxWithTitle:@"开启正则匹配" target:self action:@selector(clickEnableRegexBtn:)];
36 | btn.frame = NSMakeRect(20, 15, 400, 20);
37 |
38 | btn;
39 | });
40 |
41 | self.enableGroupReplyBtn = ({
42 | NSButton *btn = [NSButton tk_checkboxWithTitle:@"开启群聊自动回复" target:self action:@selector(clickEnableGroupBtn:)];
43 | btn.frame = NSMakeRect(20, 40, 400, 20);
44 |
45 | btn;
46 | });
47 |
48 | self.enableSingleReplyBtn = ({
49 | NSButton *btn = [NSButton tk_checkboxWithTitle:@"开启私聊自动回复" target:self action:@selector(clickEnableSingleBtn:)];
50 | btn.frame = NSMakeRect(200, 40, 400, 20);
51 |
52 | btn;
53 | });
54 |
55 | self.autoReplyContentField = ({
56 | NSTextField *textField = [[NSTextField alloc] init];
57 | textField.frame = NSMakeRect(20, 70, 350, 175);
58 | textField.placeholderString = @"请输入自动回复的内容(‘|’ 为随机回复其中任一内容)";
59 | textField.delegate = self;
60 |
61 | textField;
62 | });
63 |
64 | self.autoReplyLabel = ({
65 | NSTextField *label = [NSTextField tk_labelWithString:@"自动回复:"];
66 | label.frame = NSMakeRect(20, 250, 350, 20);
67 |
68 | label;
69 | });
70 |
71 | self.keywordTextField = ({
72 | NSTextField *textField = [[NSTextField alloc] init];
73 | textField.frame = NSMakeRect(20, 290, 350, 50);
74 | textField.placeholderString = @"请输入关键字( ‘*’ 为任何消息都回复,‘|’ 为匹配多个关键字)";
75 | textField.delegate = self;
76 |
77 | textField;
78 | });
79 |
80 | self.keywordLabel = ({
81 | NSTextField *label = [NSTextField tk_labelWithString:@"关键字:"];
82 | label.frame = NSMakeRect(20, 345, 350, 20);
83 |
84 | label;
85 | });
86 |
87 | [self addSubviews:@[self.enableRegexBtn,
88 | self.enableGroupReplyBtn,
89 | self.enableSingleReplyBtn,
90 | self.autoReplyContentField,
91 | self.autoReplyLabel,
92 | self.keywordTextField,
93 | self.keywordLabel]];
94 | }
95 |
96 | - (void)clickEnableRegexBtn:(NSButton *)btn {
97 | self.model.enableRegex = btn.state;
98 | }
99 |
100 | - (void)clickEnableGroupBtn:(NSButton *)btn {
101 | self.model.enableGroupReply = btn.state;
102 | if (btn.state) {
103 | self.model.enable = YES;
104 | } else if(!self.model.enableSingleReply) {
105 | self.model.enable = NO;
106 | }
107 |
108 | if (self.endEdit) self.endEdit();
109 | }
110 |
111 | - (void)clickEnableSingleBtn:(NSButton *)btn {
112 | self.model.enableSingleReply = btn.state;
113 | if (btn.state) {
114 | self.model.enable = YES;
115 | } else if(!self.model.enableGroupReply) {
116 | self.model.enable = NO;
117 | }
118 | if (self.endEdit) self.endEdit();
119 | }
120 |
121 | - (void)viewDidMoveToSuperview {
122 | [super viewDidMoveToSuperview];
123 | self.layer.backgroundColor = [kBG2 CGColor];
124 | self.layer.borderWidth = 1;
125 | self.layer.borderColor = [TK_RGBA(0, 0, 0, 0.1) CGColor];
126 | self.layer.cornerRadius = 3;
127 | self.layer.masksToBounds = YES;
128 | [self.layer setNeedsDisplay];
129 | }
130 |
131 | - (void)setModel:(TKAutoReplyModel *)model {
132 | _model = model;
133 | self.keywordTextField.stringValue = model.keyword != nil ? model.keyword : @"";
134 | self.autoReplyContentField.stringValue = model.replyContent != nil ? model.replyContent : @"";
135 | self.enableGroupReplyBtn.state = model.enableGroupReply;
136 | self.enableSingleReplyBtn.state = model.enableSingleReply;
137 | self.enableRegexBtn.state = model.enableRegex;
138 | }
139 |
140 | - (void)controlTextDidEndEditing:(NSNotification *)notification {
141 | if (self.endEdit) self.endEdit();
142 | }
143 |
144 | - (void)controlTextDidChange:(NSNotification *)notification {
145 | NSControl *control = notification.object;
146 | if (control == self.keywordTextField) {
147 | self.model.keyword = self.keywordTextField.stringValue;
148 | } else if (control == self.autoReplyContentField) {
149 | self.model.replyContent = self.autoReplyContentField.stringValue;
150 | }
151 | }
152 |
153 | - (BOOL)control:(NSControl *)control textView:(NSTextView *)textView doCommandBySelector:(SEL)commandSelector {
154 | BOOL result = NO;
155 |
156 | if (commandSelector == @selector(insertNewline:)) {
157 | [textView insertNewlineIgnoringFieldEditor:self];
158 | result = YES;
159 | } else if (commandSelector == @selector(insertTab:)) {
160 | if (control == self.keywordTextField) {
161 | [self.autoReplyContentField becomeFirstResponder];
162 | } else if (control == self.autoReplyContentField) {
163 | [self.keywordTextField becomeFirstResponder];
164 | }
165 | }
166 |
167 | return result;
168 | }
169 |
170 | @end
171 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Views/RemoteControl/TKRemoteControlCell.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlCell.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface TKRemoteControlCell : NSView
12 |
13 | - (void)setupWithData:(id)data;
14 |
15 | @end
16 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/Views/RemoteControl/TKRemoteControlCell.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlCell.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKRemoteControlCell.h"
10 | #import "TKRemoteControlModel.h"
11 |
12 | @interface TKRemoteControlCell ()
13 |
14 | @property (nonatomic, strong) NSButton *selectBtn;
15 | @property (nonatomic, strong) NSTextField *textField;
16 | @property (nonatomic, strong) TKRemoteControlModel *model;
17 |
18 | @end
19 |
20 | @implementation TKRemoteControlCell
21 |
22 | - (instancetype)init {
23 | self = [super init];
24 | if (self) {
25 | [self initSubviews];
26 | }
27 | return self;
28 | }
29 |
30 | - (void)initSubviews {
31 | self.selectBtn = ({
32 | NSButton *btn = [NSButton tk_checkboxWithTitle:@"" target:self action:@selector(clickSelectBtn:)];
33 | btn.frame = NSMakeRect(50, 10, 150, 30);
34 |
35 | btn;
36 | });
37 |
38 | self.textField = ({
39 | NSTextField *v = [[NSTextField alloc] init];
40 | v.frame = NSMakeRect(200, 10, 250, 30);
41 | v.placeholderString = @"请输入匹配的关键词";
42 | v.layer.cornerRadius = 10;
43 | v.layer.masksToBounds = YES;
44 | [v.layer setNeedsDisplay];
45 | v.editable = YES;
46 | v.delegate = self;
47 |
48 | v;
49 | });
50 |
51 | [self addSubviews:@[self.selectBtn, self.textField]];
52 | }
53 |
54 | - (void)clickSelectBtn:(NSButton *)btn {
55 | self.model.enable = btn.state;
56 | }
57 |
58 | - (void)setupWithData:(id)data {
59 | TKRemoteControlModel *model = data;
60 | self.model = model;
61 | self.selectBtn.title = model.function;
62 | self.selectBtn.state = model.enable;
63 | self.textField.stringValue = model.keyword;
64 | }
65 |
66 | - (BOOL)control:(NSControl *)control textShouldEndEditing:(NSText *)fieldEditor {
67 | NSString *string = control.stringValue;
68 | self.model.keyword = string;
69 | return YES;
70 | }
71 |
72 | @end
73 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/WindowControllers/AutoReply/TKAutoReplyWindowController.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyWindowController.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "TKAutoReplyModel.h"
11 |
12 | @interface TKAutoReplyWindowController : NSWindowController
13 |
14 | @property (nonatomic, copy) TKAutoReplyModel *model;
15 |
16 | @end
17 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/WindowControllers/AutoReply/TKAutoReplyWindowController.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKAutoReplyWindowController.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKAutoReplyWindowController.h"
10 | #import "TKAutoReplyContentView.h"
11 | #import "WeChatPlugin.h"
12 | #import "TKAutoReplyCell.h"
13 |
14 | @interface TKAutoReplyWindowController ()
15 |
16 | @property (nonatomic, strong) NSTableView *tableView;
17 | @property (nonatomic, strong) TKAutoReplyContentView *contentView;
18 | @property (nonatomic, strong) NSButton *addButton;
19 | @property (nonatomic, strong) NSButton *reduceButton;
20 | @property (nonatomic, strong) NSAlert *alert;
21 |
22 | @property (nonatomic, strong) NSMutableArray *autoReplyModels;
23 | @property (nonatomic, assign) NSInteger lastSelectIndex;
24 |
25 | @end
26 |
27 | @implementation TKAutoReplyWindowController
28 |
29 | - (void)windowDidLoad {
30 | [super windowDidLoad];
31 |
32 | [self initSubviews];
33 | [self setup];
34 | }
35 |
36 | - (void)showWindow:(id)sender {
37 | [super showWindow:sender];
38 | [self.tableView reloadData];
39 | [self.contentView setHidden:YES];
40 | if (self.autoReplyModels && self.autoReplyModels.count == 0) {
41 | [self addModel];
42 | }
43 | if (self.autoReplyModels.count > 0 && self.tableView) {
44 | [self.tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:self.autoReplyModels.count - 1] byExtendingSelection:YES];
45 | }
46 | }
47 |
48 | - (void)initSubviews {
49 | NSScrollView *scrollView = ({
50 | NSScrollView *scrollView = [[NSScrollView alloc] init];
51 | scrollView.hasVerticalScroller = YES;
52 | scrollView.frame = NSMakeRect(30, 50, 200, 375);
53 | scrollView.autoresizingMask = NSViewWidthSizable | NSViewHeightSizable;
54 |
55 | scrollView;
56 | });
57 |
58 | self.tableView = ({
59 | NSTableView *tableView = [[NSTableView alloc] init];
60 | tableView.frame = scrollView.bounds;
61 | tableView.allowsTypeSelect = YES;
62 | tableView.delegate = self;
63 | tableView.dataSource = self;
64 | NSTableColumn *column = [[NSTableColumn alloc] init];
65 | column.title = @"自动回复列表";
66 | column.width = 200;
67 | [tableView addTableColumn:column];
68 |
69 | tableView;
70 | });
71 |
72 | self.contentView = ({
73 | TKAutoReplyContentView *contentView = [[TKAutoReplyContentView alloc] init];
74 | contentView.frame = NSMakeRect(250, 50, 400, 375);
75 | contentView.hidden = YES;
76 |
77 | contentView;
78 | });
79 |
80 | self.addButton = ({
81 | NSButton *btn = [NSButton tk_buttonWithTitle:@"+" target:self action:@selector(addModel)];
82 | btn.frame = NSMakeRect(30, 10, 40, 40);
83 | btn.bezelStyle = NSBezelStyleTexturedRounded;
84 |
85 | btn;
86 | });
87 |
88 | self.reduceButton = ({
89 | NSButton *btn = [NSButton tk_buttonWithTitle:@"-" target:self action:@selector(reduceModel)];
90 | btn.frame = NSMakeRect(80, 10, 40, 40);
91 | btn.bezelStyle = NSBezelStyleTexturedRounded;
92 | btn.enabled = NO;
93 |
94 | btn;
95 | });
96 |
97 | self.alert = ({
98 | NSAlert *alert = [[NSAlert alloc] init];
99 | [alert addButtonWithTitle:@"确定"];
100 | [alert setMessageText:@"您还有一条自动回复设置未完成"];
101 | [alert setInformativeText:@"请完善未完成的自动回复设置"];
102 |
103 | alert;
104 | });
105 |
106 | scrollView.contentView.documentView = self.tableView;
107 |
108 | [self.window.contentView addSubviews:@[scrollView,
109 | self.contentView,
110 | self.addButton,
111 | self.reduceButton]];
112 | }
113 |
114 | - (void)setup {
115 | self.window.title = @"自动回复设置";
116 | self.window.contentView.layer.backgroundColor = [kBG1 CGColor];
117 | [self.window.contentView.layer setNeedsDisplay];
118 |
119 | self.lastSelectIndex = -1;
120 | self.autoReplyModels = [[TKWeChatPluginConfig sharedConfig] autoReplyModels];
121 | [self.tableView reloadData];
122 |
123 | __weak typeof(self) weakSelf = self;
124 | self.contentView.endEdit = ^(void) {
125 | [weakSelf.tableView reloadData];
126 | if (weakSelf.lastSelectIndex != -1) {
127 | [weakSelf.tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:weakSelf.lastSelectIndex] byExtendingSelection:YES];
128 | }
129 | };
130 | }
131 |
132 | /**
133 | 关闭窗口事件
134 |
135 | */
136 | - (BOOL)windowShouldClose:(id)sender {
137 | [[TKWeChatPluginConfig sharedConfig] saveAutoReplyModels];
138 | return YES;
139 | }
140 |
141 | #pragma mark - addButton & reduceButton ClickAction
142 | - (void)addModel {
143 | if (self.contentView.hidden) {
144 | self.contentView.hidden = NO;
145 | }
146 | __block NSInteger emptyModelIndex = -1;
147 | [self.autoReplyModels enumerateObjectsUsingBlock:^(TKAutoReplyModel *model, NSUInteger idx, BOOL * _Nonnull stop) {
148 | if (model.hasEmptyKeywordOrReplyContent) {
149 | emptyModelIndex = idx;
150 | *stop = YES;
151 | }
152 | }];
153 |
154 | if (self.autoReplyModels.count > 0 && emptyModelIndex != -1) {
155 | [self.alert beginSheetModalForWindow:self.window completionHandler:^(NSModalResponse returnCode) {
156 | if(returnCode == NSAlertFirstButtonReturn){
157 | if (self.tableView.selectedRow != -1) {
158 | [self.tableView deselectRow:self.tableView.selectedRow];
159 | }
160 | [self.tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:emptyModelIndex] byExtendingSelection:YES];
161 | }
162 | }];
163 | return;
164 | };
165 |
166 | TKAutoReplyModel *model = [[TKAutoReplyModel alloc] init];
167 | [self.autoReplyModels addObject:model];
168 | [self.tableView reloadData];
169 | self.contentView.model = model;
170 |
171 | [self.tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:self.autoReplyModels.count - 1] byExtendingSelection:YES];
172 | }
173 |
174 | - (void)reduceModel {
175 | NSInteger index = self.tableView.selectedRow;
176 | if (index > -1) {
177 | [self.autoReplyModels removeObjectAtIndex:index];
178 | [self.tableView reloadData];
179 | if (self.autoReplyModels.count == 0) {
180 | self.contentView.hidden = YES;
181 | self.reduceButton.enabled = NO;
182 | } else {
183 | [self.tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:self.autoReplyModels.count - 1] byExtendingSelection:YES];
184 | }
185 | }
186 | }
187 |
188 | #pragma mark - NSTableViewDataSource && NSTableViewDelegate
189 | - (NSInteger)numberOfRowsInTableView:(NSTableView *)tableView {
190 | return self.autoReplyModels.count;
191 | }
192 |
193 | - (NSView *)tableView:(NSTableView *)tableView viewForTableColumn:(NSTableColumn *)tableColumn row:(NSInteger)row {
194 | TKAutoReplyCell *cell = [[TKAutoReplyCell alloc] init];
195 | cell.frame = NSMakeRect(0, 0, self.tableView.frame.size.width, 40);
196 | cell.model = self.autoReplyModels[row];
197 | __weak typeof(self) weakSelf = self;
198 | cell.updateModel = ^{
199 | weakSelf.contentView.model = weakSelf.autoReplyModels[row];
200 | };
201 | return cell;
202 | }
203 |
204 | - (CGFloat)tableView:(NSTableView *)tableView heightOfRow:(NSInteger)row {
205 | return 50;
206 | }
207 |
208 | - (void)tableViewSelectionDidChange:(NSNotification *)notification {
209 | NSTableView *tableView = notification.object;
210 | self.contentView.hidden = tableView.selectedRow == -1;
211 | self.reduceButton.enabled = tableView.selectedRow != -1;
212 |
213 | if (tableView.selectedRow != -1) {
214 | TKAutoReplyModel *model = self.autoReplyModels[tableView.selectedRow];
215 | self.contentView.model = model;
216 | self.lastSelectIndex = tableView.selectedRow;
217 | __block NSInteger emptyModelIndex = -1;
218 | [self.autoReplyModels enumerateObjectsUsingBlock:^(TKAutoReplyModel *model, NSUInteger idx, BOOL * _Nonnull stop) {
219 | if (model.hasEmptyKeywordOrReplyContent) {
220 | emptyModelIndex = idx;
221 | *stop = YES;
222 | }
223 | }];
224 |
225 | if (emptyModelIndex != -1 && tableView.selectedRow != emptyModelIndex) {
226 | [self.alert beginSheetModalForWindow:self.window completionHandler:^(NSModalResponse returnCode) {
227 | if(returnCode == NSAlertFirstButtonReturn){
228 | if (self.tableView.selectedRow != -1) {
229 | [self.tableView deselectRow:self.tableView.selectedRow];
230 | }
231 | [self.tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:emptyModelIndex] byExtendingSelection:YES];
232 | }
233 | }];
234 | }
235 | }
236 | }
237 |
238 | @end
239 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/WindowControllers/AutoReply/TKAutoReplyWindowController.xib:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/WindowControllers/RemoteControl/TKRemoteControlWindowController.h:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlWindowController.h
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface TKRemoteControlWindowController : NSWindowController
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/WindowControllers/RemoteControl/TKRemoteControlWindowController.m:
--------------------------------------------------------------------------------
1 | //
2 | // TKRemoteControlWindowController.m
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/8/8.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import "TKRemoteControlWindowController.h"
10 | #import "TKRemoteControlModel.h"
11 | #import "TKWeChatPluginConfig.h"
12 | #import "TKRemoteControlCell.h"
13 |
14 | @interface TKRemoteControlWindowController ()
15 |
16 | @property (nonatomic, weak) IBOutlet NSTabView *tabView;
17 | @property (nonatomic, strong) NSTableView *tableView;
18 | @property (nonatomic, strong) NSArray *remoteControlModels;
19 |
20 | @end
21 |
22 | @implementation TKRemoteControlWindowController
23 |
24 | - (void)windowDidLoad {
25 | [super windowDidLoad];
26 |
27 | [self setup];
28 | [self initSubviews];
29 | }
30 |
31 | - (void)initSubviews {
32 |
33 | CGFloat tabViewWidth = self.tabView.frame.size.width;
34 | CGFloat tabViewHeight = self.tabView.frame.size.height;
35 |
36 | self.tableView = ({
37 | NSTableView *tableView = [[NSTableView alloc] init];
38 | tableView.frame = NSMakeRect(50, 50, tabViewWidth, tabViewHeight);
39 | tableView.delegate = self;
40 | tableView.dataSource = self;
41 | NSTableColumn *column = [[NSTableColumn alloc] init];
42 | column.width = tabViewWidth - 100;
43 | [tableView addTableColumn:column];
44 | tableView.selectionHighlightStyle = NSTableViewSelectionHighlightStyleNone;
45 | tableView.backgroundColor = [NSColor clearColor];
46 |
47 | tableView;
48 | });
49 |
50 | [self.tabView addSubview:self.tableView];
51 | }
52 |
53 | - (void)setup {
54 | self.window.contentView.layer.backgroundColor = [NSColor whiteColor].CGColor;
55 | [self.window.contentView.layer setNeedsDisplay];
56 | self.remoteControlModels = [[TKWeChatPluginConfig sharedConfig] remoteControlModels][0];
57 | }
58 |
59 | /**
60 | 关闭窗口事件
61 |
62 | */
63 | - (BOOL)windowShouldClose:(id)sender {
64 | [[TKWeChatPluginConfig sharedConfig] saveRemoteControlModels];
65 | return YES;
66 | }
67 |
68 | #pragma mark - NSTableViewDataSource && NSTableViewDelegate
69 | - (NSInteger)numberOfRowsInTableView:(NSTableView *)tableView{
70 | return self.remoteControlModels.count;
71 | }
72 |
73 | - (NSView *)tableView:(NSTableView *)tableView viewForTableColumn:(NSTableColumn *)tableColumn row:(NSInteger)row{
74 | TKRemoteControlCell *cell = [[TKRemoteControlCell alloc] init];
75 | cell.frame = NSMakeRect(0, 0, self.tabView.frame.size.width, 40);
76 | [cell setupWithData:self.remoteControlModels[row]];
77 |
78 | return cell;
79 | }
80 |
81 | - (CGFloat)tableView:(NSTableView *)tableView heightOfRow:(NSInteger)row{
82 | return 50;
83 | }
84 |
85 | #pragma mark - NSTabViewDelegate
86 | - (void)tabView:(NSTabView *)tabView didSelectTabViewItem:(NSTabViewItem *)tabViewItem {
87 | NSInteger selectTabIndex = [tabViewItem.identifier integerValue];
88 | self.remoteControlModels = [[TKWeChatPluginConfig sharedConfig] remoteControlModels][selectTabIndex];
89 | [self.tableView reloadData];
90 | }
91 |
92 | @end
93 |
--------------------------------------------------------------------------------
/WeChatPlugin/Sources/WindowControllers/RemoteControl/TKRemoteControlWindowController.xib:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
--------------------------------------------------------------------------------
/WeChatPlugin/TKRemoteControlCommands.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | executeCommand
8 | open /System/Library/Frameworks/ScreenSaver.framework/Versions/A/Resources/ScreenSaverEngine.app || open /System/Library/CoreServices/ScreenSaverEngine.app
9 | keyword
10 | ScreenSave
11 | function
12 | 屏幕保护
13 | enable
14 |
15 | command
16 | #remote.screensaver
17 |
18 |
19 | executeCommand
20 | /System/Library/CoreServices/Menu\ Extras/User.menu/Contents/Resources/CGSession -suspend
21 | keyword
22 | LockScreen
23 | function
24 | 锁屏
25 | enable
26 |
27 | command
28 | #remote.lockscreen
29 |
30 |
31 | executeCommand
32 | sleep
33 | keyword
34 | Sleep
35 | function
36 | 休眠
37 | enable
38 |
39 | command
40 | #remote.sleep
41 |
42 |
43 | executeCommand
44 | shutdown
45 | keyword
46 | Shutdown
47 | function
48 | 关机
49 | enable
50 |
51 | command
52 | #remote.shutdown
53 |
54 |
55 | executeCommand
56 | restart
57 | keyword
58 | Restart
59 | function
60 | 重启
61 | enable
62 |
63 | command
64 | #remote.restart
65 |
66 |
67 | executeCommand
68 | empty
69 | keyword
70 | EmptyTrash
71 | function
72 | 清空废纸篓
73 | enable
74 |
75 | command
76 | #remote.emptytrash
77 |
78 |
79 |
80 |
81 | executeCommand
82 | killQQ
83 | keyword
84 | KillQQ
85 | function
86 | 退出 QQ
87 | enable
88 |
89 |
90 |
91 | executeCommand
92 | killWeChat
93 | keyword
94 | KillWeChat
95 | function
96 | 退出 WeChat
97 | enable
98 |
99 |
100 |
101 | executeCommand
102 | killChrome
103 | keyword
104 | KillChrome
105 | function
106 | 退出 Chrome
107 | enable
108 |
109 |
110 |
111 | executeCommand
112 | killSafari
113 | keyword
114 | KillSafari
115 | function
116 | 退出 Safari
117 | enable
118 |
119 |
120 |
121 | executeCommand
122 | killAll
123 | keyword
124 | KillAll
125 | function
126 | 退出所有程序
127 | enable
128 |
129 |
130 |
131 |
132 |
133 | executeCommand
134 | musicToggle
135 | keyword
136 | Toggle
137 | function
138 | 播放/暂停
139 | enable
140 |
141 |
142 |
143 | executeCommand
144 | musicNext
145 | keyword
146 | Next
147 | function
148 | 下一首
149 | enable
150 |
151 |
152 |
153 | executeCommand
154 | musicPrevious
155 | keyword
156 | Previous
157 | function
158 | 上一首
159 | enable
160 |
161 |
162 |
163 | executeCommand
164 | musicVolumeUp
165 | keyword
166 | VolumeUp
167 | function
168 | 增大音量
169 | enable
170 |
171 |
172 |
173 | executeCommand
174 | musicVolumeDown
175 | keyword
176 | VolumeDown
177 | function
178 | 减小音量
179 | enable
180 |
181 |
182 |
183 | executeCommand
184 | musicLike
185 | keyword
186 | LikeChange
187 | function
188 | 喜欢/取消喜欢
189 | enable
190 |
191 |
192 |
193 |
194 |
195 |
--------------------------------------------------------------------------------
/WeChatPlugin/TKRemoteControlScript.scpt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/CodeTips/WeChatPlugin-macOS/35938a151a013ae7e4f782bd05c0839e3ac29bd3/WeChatPlugin/TKRemoteControlScript.scpt
--------------------------------------------------------------------------------
/WeChatPlugin/en.lproj/Localizable.strings:
--------------------------------------------------------------------------------
1 | /*
2 | Localizable.strings
3 | WeChatPlugin
4 |
5 | Created by Loveletter on 28/02/2018.
6 | Copyright © 2018 CodeTips. All rights reserved.
7 | */
8 | "PreventRevoke" = "Prevent Revoke";
9 | "AutoReply" = "Auto Reply";
10 | "NewWeChat" = "New WeChat";
11 | "RemoteControl" = "Remote Control";
12 | "WeChatOnTop" = "WeChat Stick";
13 | "AutoAuthLogin" = "AutoAuth Login";
14 | "Plugin" = "Plugin";
15 |
--------------------------------------------------------------------------------
/WeChatPlugin/main.mm:
--------------------------------------------------------------------------------
1 | //
2 | // main.c
3 | // WeChatPlugin
4 | //
5 | // Created by TK on 2017/4/19.
6 | // Copyright © 2017年 tk. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "WeChat+hook.h"
11 | #import "MMChatsTableCellView+hook.h"
12 | #import "NSViewController+Hook.h"
13 |
14 | static void __attribute__((constructor)) initialize(void) {
15 | NSLog(@"++++++++ WeChatPlugin loaded ++++++++");
16 | [NSObject hookWeChat];
17 | [NSObject hookMMChatsTableCellView];
18 | [NSObject hookNSViewController];
19 | }
20 |
--------------------------------------------------------------------------------
/WeChatPlugin/zh-Hans.lproj/Localizable.strings:
--------------------------------------------------------------------------------
1 | /*
2 | Localizable.strings
3 | WeChatPlugin
4 |
5 | Created by Loveletter on 28/02/2018.
6 | Copyright © 2018 CodeTips. All rights reserved.
7 | */
8 | "PreventRevoke" = "消息防撤回";
9 | "AutoReply" = "自动回复设置";
10 | "NewWeChat" = "登录新微信";
11 | "RemoteControl" = "远程控制MacOS";
12 | "WeChatOnTop" = "微信窗口置顶";
13 | "AutoAuthLogin" = "免认证登录";
14 | "Plugin" = "小助手";
15 |
--------------------------------------------------------------------------------