├── ChatClient
├── ChatClient.pro
├── ChatClient.pro.user
├── Makefile
├── chatLog.txt
├── chatconnection.cpp
├── chatconnection.h
├── chatdialog.cpp
├── chatdialog.h
├── chatserver.cpp
├── chatserver.h
├── debug.log
├── header.h
├── images
│ ├── chatroom.ico
│ └── icon.rc
├── logindialog.cpp
├── logindialog.h
├── main.cpp
├── mainwindow.cpp
├── mainwindow.h
├── peerinfo.cpp
├── peerinfo.h
├── registerconnection.cpp
└── registerconnection.h
├── LICENSE
├── Material
├── P2P聊天软件设计文档.pdf
├── chat_dialog.jpg
├── chat_dialog2.jpg
├── client_gui.jpg
├── client_gui2.jpg
├── register_gui.jpg
└── register_server_gui.jpg
├── README.md
└── RegisterServer
├── Makefile
├── RegisterServer.pro
├── RegisterServer.pro.user
├── debug.log
├── header.h
├── images
├── icon.rc
└── server.ico
├── main.cpp
├── peerinfo.cpp
├── peerinfo.h
├── registerLog.txt
├── registerconnection.cpp
├── registerconnection.h
├── registerserver.cpp
├── registerserver.h
├── window.cpp
└── window.h
/ChatClient/ChatClient.pro:
--------------------------------------------------------------------------------
1 | #-------------------------------------------------
2 | #
3 | # Project created by QtCreator 2015-10-13T22:07:38
4 | #
5 | #-------------------------------------------------
6 |
7 | QT += core gui network sql
8 |
9 | greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
10 |
11 | TARGET = ChatClient
12 | TEMPLATE = app
13 |
14 |
15 | SOURCES += main.cpp\
16 | mainwindow.cpp \
17 | chatconnection.cpp \
18 | chatdialog.cpp \
19 | chatserver.cpp \
20 | logindialog.cpp \
21 | registerconnection.cpp \
22 | peerinfo.cpp
23 |
24 | HEADERS += mainwindow.h \
25 | chatconnection.h \
26 | chatdialog.h \
27 | chatserver.h \
28 | header.h \
29 | logindialog.h \
30 | registerconnection.h \
31 | peerinfo.h
32 |
33 | RC_FILE = images/icon.rc
34 |
35 | OTHER_FILES += \
36 | images/icon.rc \
37 | images/chatroom.ico
38 |
--------------------------------------------------------------------------------
/ChatClient/ChatClient.pro.user:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | EnvironmentId
7 | {1f2d4bf0-dd7c-4612-97c0-0e08f39cb8c2}
8 |
9 |
10 | ProjectExplorer.Project.ActiveTarget
11 | 0
12 |
13 |
14 | ProjectExplorer.Project.EditorSettings
15 |
16 | true
17 | false
18 | true
19 |
20 | Cpp
21 |
22 | CppGlobal
23 |
24 |
25 |
26 | QmlJS
27 |
28 | QmlJSGlobal
29 |
30 |
31 | 2
32 | UTF-8
33 | false
34 | 4
35 | false
36 | 80
37 | true
38 | true
39 | 1
40 | true
41 | false
42 | 0
43 | true
44 | 0
45 | 8
46 | true
47 | 1
48 | true
49 | true
50 | true
51 | false
52 |
53 |
54 |
55 | ProjectExplorer.Project.PluginSettings
56 |
57 |
58 |
59 | ProjectExplorer.Project.Target.0
60 |
61 | Desktop Qt 5.6.0 MinGW 32bit
62 | Desktop Qt 5.6.0 MinGW 32bit
63 | qt.56.win32_mingw49_kit
64 | 0
65 | 0
66 | 0
67 |
68 | C:/Users/Adoryn/P2PChatRoom/ChatClient
69 |
70 |
71 | true
72 | qmake
73 |
74 | QtProjectManager.QMakeBuildStep
75 | true
76 |
77 | false
78 | false
79 | false
80 |
81 |
82 | true
83 | Make
84 |
85 | Qt4ProjectManager.MakeStep
86 |
87 | false
88 |
89 |
90 |
91 | 2
92 | 构建
93 |
94 | ProjectExplorer.BuildSteps.Build
95 |
96 |
97 |
98 | true
99 | Make
100 |
101 | Qt4ProjectManager.MakeStep
102 |
103 | true
104 | clean
105 |
106 |
107 | 1
108 | 清理
109 |
110 | ProjectExplorer.BuildSteps.Clean
111 |
112 | 2
113 | false
114 |
115 | Debug
116 |
117 | Qt4ProjectManager.Qt4BuildConfiguration
118 | 2
119 | true
120 |
121 |
122 | D:/CoreShare/Work/研究生作业/QtProjects/HomeWork/P2PChatRoom/build-ChatClient-Desktop_Qt_5_6_0_MinGW_32bit-Release
123 |
124 |
125 | true
126 | qmake
127 |
128 | QtProjectManager.QMakeBuildStep
129 | false
130 |
131 | false
132 | false
133 | false
134 |
135 |
136 | true
137 | Make
138 |
139 | Qt4ProjectManager.MakeStep
140 |
141 | false
142 |
143 |
144 |
145 | 2
146 | 构建
147 |
148 | ProjectExplorer.BuildSteps.Build
149 |
150 |
151 |
152 | true
153 | Make
154 |
155 | Qt4ProjectManager.MakeStep
156 |
157 | true
158 | clean
159 |
160 |
161 | 1
162 | 清理
163 |
164 | ProjectExplorer.BuildSteps.Clean
165 |
166 | 2
167 | false
168 |
169 | Release
170 |
171 | Qt4ProjectManager.Qt4BuildConfiguration
172 | 0
173 | true
174 |
175 |
176 | D:/CoreShare/Work/研究生作业/QtProjects/HomeWork/P2PChatRoom/build-ChatClient-Desktop_Qt_5_6_0_MinGW_32bit-Profile
177 |
178 |
179 | true
180 | qmake
181 |
182 | QtProjectManager.QMakeBuildStep
183 | true
184 |
185 | false
186 | true
187 | false
188 |
189 |
190 | true
191 | Make
192 |
193 | Qt4ProjectManager.MakeStep
194 |
195 | false
196 |
197 |
198 |
199 | 2
200 | 构建
201 |
202 | ProjectExplorer.BuildSteps.Build
203 |
204 |
205 |
206 | true
207 | Make
208 |
209 | Qt4ProjectManager.MakeStep
210 |
211 | true
212 | clean
213 |
214 |
215 | 1
216 | 清理
217 |
218 | ProjectExplorer.BuildSteps.Clean
219 |
220 | 2
221 | false
222 |
223 | Profile
224 |
225 | Qt4ProjectManager.Qt4BuildConfiguration
226 | 0
227 | true
228 |
229 | 3
230 |
231 |
232 | 0
233 | 部署
234 |
235 | ProjectExplorer.BuildSteps.Deploy
236 |
237 | 1
238 | 在本地部署
239 |
240 | ProjectExplorer.DefaultDeployConfiguration
241 |
242 | 1
243 |
244 |
245 | false
246 | 1000
247 |
248 | true
249 |
250 | false
251 | false
252 | false
253 | false
254 | true
255 | 0.01
256 | 10
257 | true
258 | 1
259 | 25
260 |
261 | 1
262 | true
263 | false
264 | true
265 | valgrind
266 |
267 | 0
268 | 1
269 | 2
270 | 3
271 | 4
272 | 5
273 | 6
274 | 7
275 | 8
276 | 9
277 | 10
278 | 11
279 | 12
280 | 13
281 | 14
282 |
283 | 2
284 |
285 | ChatClient
286 | ChatClient2
287 | Qt4ProjectManager.Qt4RunConfiguration:C:/Users/Adoryn/P2PChatRoom/ChatClient/ChatClient.pro
288 | true
289 |
290 | ChatClient.pro
291 | false
292 | false
293 |
294 | 3768
295 | false
296 | true
297 | false
298 | false
299 | true
300 |
301 | 1
302 |
303 |
304 |
305 | ProjectExplorer.Project.TargetCount
306 | 1
307 |
308 |
309 | ProjectExplorer.Project.Updater.FileVersion
310 | 18
311 |
312 |
313 | Version
314 | 18
315 |
316 |
317 |
--------------------------------------------------------------------------------
/ChatClient/Makefile:
--------------------------------------------------------------------------------
1 | #############################################################################
2 | # Makefile for building: ChatClient
3 | # Generated by qmake (3.0) (Qt 5.6.0)
4 | # Project: ChatClient.pro
5 | # Template: app
6 | # Command: C:\Qt\Qt5.6.0\5.6\mingw49_32\bin\qmake.exe -spec win32-g++ "CONFIG+=debug" "CONFIG+=qml_debug" -o Makefile ChatClient.pro
7 | #############################################################################
8 |
9 | MAKEFILE = Makefile
10 |
11 | first: debug
12 | install: debug-install
13 | uninstall: debug-uninstall
14 | QMAKE = C:\Qt\Qt5.6.0\5.6\mingw49_32\bin\qmake.exe
15 | DEL_FILE = del
16 | CHK_DIR_EXISTS= if not exist
17 | MKDIR = mkdir
18 | COPY = copy /y
19 | COPY_FILE = copy /y
20 | COPY_DIR = xcopy /s /q /y /i
21 | INSTALL_FILE = copy /y
22 | INSTALL_PROGRAM = copy /y
23 | INSTALL_DIR = xcopy /s /q /y /i
24 | DEL_FILE = del
25 | SYMLINK = $(QMAKE) -install ln -f -s
26 | DEL_DIR = rmdir
27 | MOVE = move
28 | SUBTARGETS = \
29 | debug \
30 | release
31 |
32 |
33 | debug: FORCE
34 | $(MAKE) -f $(MAKEFILE).Debug
35 | debug-make_first: FORCE
36 | $(MAKE) -f $(MAKEFILE).Debug
37 | debug-all: FORCE
38 | $(MAKE) -f $(MAKEFILE).Debug all
39 | debug-clean: FORCE
40 | $(MAKE) -f $(MAKEFILE).Debug clean
41 | debug-distclean: FORCE
42 | $(MAKE) -f $(MAKEFILE).Debug distclean
43 | debug-install: FORCE
44 | $(MAKE) -f $(MAKEFILE).Debug install
45 | debug-uninstall: FORCE
46 | $(MAKE) -f $(MAKEFILE).Debug uninstall
47 | release: FORCE
48 | $(MAKE) -f $(MAKEFILE).Release
49 | release-make_first: FORCE
50 | $(MAKE) -f $(MAKEFILE).Release
51 | release-all: FORCE
52 | $(MAKE) -f $(MAKEFILE).Release all
53 | release-clean: FORCE
54 | $(MAKE) -f $(MAKEFILE).Release clean
55 | release-distclean: FORCE
56 | $(MAKE) -f $(MAKEFILE).Release distclean
57 | release-install: FORCE
58 | $(MAKE) -f $(MAKEFILE).Release install
59 | release-uninstall: FORCE
60 | $(MAKE) -f $(MAKEFILE).Release uninstall
61 |
62 | Makefile: ChatClient.pro ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/win32-g++/qmake.conf ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_pre.prf \
63 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qdevice.pri \
64 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/device_config.prf \
65 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/common/angle.conf \
66 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qconfig.pri \
67 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore.pri \
68 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore_private.pri \
69 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput.pri \
70 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput_private.pri \
71 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic.pri \
72 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic_private.pri \
73 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick.pri \
74 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick_private.pri \
75 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput.pri \
76 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput_private.pri \
77 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender.pri \
78 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender_private.pri \
79 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender.pri \
80 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender_private.pri \
81 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase.pri \
82 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase_private.pri \
83 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer.pri \
84 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer_private.pri \
85 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver.pri \
86 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver_private.pri \
87 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth.pri \
88 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth_private.pri \
89 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bootstrap_private.pri \
90 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_clucene_private.pri \
91 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent.pri \
92 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent_private.pri \
93 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core.pri \
94 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core_private.pri \
95 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus.pri \
96 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus_private.pri \
97 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer.pri \
98 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer_private.pri \
99 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designercomponents_private.pri \
100 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui.pri \
101 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui_private.pri \
102 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help.pri \
103 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help_private.pri \
104 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labscontrols_private.pri \
105 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labstemplates_private.pri \
106 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location.pri \
107 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location_private.pri \
108 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia.pri \
109 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia_private.pri \
110 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets.pri \
111 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets_private.pri \
112 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network.pri \
113 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network_private.pri \
114 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc.pri \
115 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc_private.pri \
116 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl.pri \
117 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl_private.pri \
118 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions.pri \
119 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions_private.pri \
120 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_platformsupport_private.pri \
121 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning.pri \
122 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning_private.pri \
123 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport.pri \
124 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport_private.pri \
125 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml.pri \
126 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml_private.pri \
127 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmldevtools_private.pri \
128 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest.pri \
129 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest_private.pri \
130 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qtmultimediaquicktools_private.pri \
131 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick.pri \
132 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick_private.pri \
133 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickparticles_private.pri \
134 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets.pri \
135 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets_private.pri \
136 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script.pri \
137 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script_private.pri \
138 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools.pri \
139 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools_private.pri \
140 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors.pri \
141 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors_private.pri \
142 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus.pri \
143 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus_private.pri \
144 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport.pri \
145 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport_private.pri \
146 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql.pri \
147 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql_private.pri \
148 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg.pri \
149 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg_private.pri \
150 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib.pri \
151 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib_private.pri \
152 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uiplugin.pri \
153 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools.pri \
154 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools_private.pri \
155 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel.pri \
156 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel_private.pri \
157 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets.pri \
158 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets_private.pri \
159 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets.pri \
160 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets_private.pri \
161 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras.pri \
162 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras_private.pri \
163 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml.pri \
164 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml_private.pri \
165 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns.pri \
166 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns_private.pri \
167 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_functions.prf \
168 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_config.prf \
169 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/qt_config.prf \
170 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/win32-g++/qmake.conf \
171 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_post.prf \
172 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds.prf \
173 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_pre.prf \
174 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/default_pre.prf \
175 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resolve_config.prf \
176 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds_post.prf \
177 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_post.prf \
178 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qml_debug.prf \
179 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/rtti.prf \
180 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/precompile_header.prf \
181 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/warn_on.prf \
182 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt.prf \
183 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resources.prf \
184 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/moc.prf \
185 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/opengl.prf \
186 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/uic.prf \
187 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/windows.prf \
188 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/testcase_targets.prf \
189 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exceptions.prf \
190 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/yacc.prf \
191 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/lex.prf \
192 | ChatClient.pro \
193 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/qtmaind.prl \
194 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Widgets.prl \
195 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Gui.prl \
196 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Network.prl \
197 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Sql.prl \
198 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Core.prl
199 | $(QMAKE) -spec win32-g++ "CONFIG+=debug" "CONFIG+=qml_debug" -o Makefile ChatClient.pro
200 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_pre.prf:
201 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qdevice.pri:
202 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/device_config.prf:
203 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/common/angle.conf:
204 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qconfig.pri:
205 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore.pri:
206 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore_private.pri:
207 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput.pri:
208 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput_private.pri:
209 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic.pri:
210 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic_private.pri:
211 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick.pri:
212 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick_private.pri:
213 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput.pri:
214 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput_private.pri:
215 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender.pri:
216 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender_private.pri:
217 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender.pri:
218 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender_private.pri:
219 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase.pri:
220 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase_private.pri:
221 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer.pri:
222 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer_private.pri:
223 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver.pri:
224 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver_private.pri:
225 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth.pri:
226 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth_private.pri:
227 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bootstrap_private.pri:
228 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_clucene_private.pri:
229 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent.pri:
230 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent_private.pri:
231 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core.pri:
232 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core_private.pri:
233 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus.pri:
234 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus_private.pri:
235 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer.pri:
236 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer_private.pri:
237 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designercomponents_private.pri:
238 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui.pri:
239 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui_private.pri:
240 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help.pri:
241 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help_private.pri:
242 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labscontrols_private.pri:
243 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labstemplates_private.pri:
244 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location.pri:
245 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location_private.pri:
246 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia.pri:
247 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia_private.pri:
248 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets.pri:
249 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets_private.pri:
250 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network.pri:
251 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network_private.pri:
252 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc.pri:
253 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc_private.pri:
254 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl.pri:
255 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl_private.pri:
256 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions.pri:
257 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions_private.pri:
258 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_platformsupport_private.pri:
259 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning.pri:
260 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning_private.pri:
261 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport.pri:
262 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport_private.pri:
263 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml.pri:
264 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml_private.pri:
265 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmldevtools_private.pri:
266 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest.pri:
267 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest_private.pri:
268 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qtmultimediaquicktools_private.pri:
269 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick.pri:
270 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick_private.pri:
271 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickparticles_private.pri:
272 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets.pri:
273 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets_private.pri:
274 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script.pri:
275 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script_private.pri:
276 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools.pri:
277 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools_private.pri:
278 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors.pri:
279 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors_private.pri:
280 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus.pri:
281 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus_private.pri:
282 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport.pri:
283 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport_private.pri:
284 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql.pri:
285 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql_private.pri:
286 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg.pri:
287 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg_private.pri:
288 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib.pri:
289 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib_private.pri:
290 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uiplugin.pri:
291 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools.pri:
292 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools_private.pri:
293 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel.pri:
294 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel_private.pri:
295 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets.pri:
296 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets_private.pri:
297 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets.pri:
298 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets_private.pri:
299 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras.pri:
300 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras_private.pri:
301 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml.pri:
302 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml_private.pri:
303 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns.pri:
304 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns_private.pri:
305 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_functions.prf:
306 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_config.prf:
307 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/qt_config.prf:
308 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/win32-g++/qmake.conf:
309 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_post.prf:
310 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds.prf:
311 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_pre.prf:
312 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/default_pre.prf:
313 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resolve_config.prf:
314 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds_post.prf:
315 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_post.prf:
316 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qml_debug.prf:
317 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/rtti.prf:
318 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/precompile_header.prf:
319 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/warn_on.prf:
320 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt.prf:
321 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resources.prf:
322 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/moc.prf:
323 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/opengl.prf:
324 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/uic.prf:
325 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/windows.prf:
326 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/testcase_targets.prf:
327 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exceptions.prf:
328 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/yacc.prf:
329 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/lex.prf:
330 | ChatClient.pro:
331 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/qtmaind.prl:
332 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Widgets.prl:
333 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Gui.prl:
334 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Network.prl:
335 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Sql.prl:
336 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Core.prl:
337 | qmake: FORCE
338 | @$(QMAKE) -spec win32-g++ "CONFIG+=debug" "CONFIG+=qml_debug" -o Makefile ChatClient.pro
339 |
340 | qmake_all: FORCE
341 |
342 | make_first: debug-make_first release-make_first FORCE
343 | all: debug-all release-all FORCE
344 | clean: debug-clean release-clean FORCE
345 | distclean: debug-distclean release-distclean FORCE
346 | -$(DEL_FILE) Makefile
347 |
348 | debug-mocclean:
349 | $(MAKE) -f $(MAKEFILE).Debug mocclean
350 | release-mocclean:
351 | $(MAKE) -f $(MAKEFILE).Release mocclean
352 | mocclean: debug-mocclean release-mocclean
353 |
354 | debug-mocables:
355 | $(MAKE) -f $(MAKEFILE).Debug mocables
356 | release-mocables:
357 | $(MAKE) -f $(MAKEFILE).Release mocables
358 | mocables: debug-mocables release-mocables
359 |
360 | check: first
361 | FORCE:
362 |
363 | $(MAKEFILE).Debug: Makefile
364 | $(MAKEFILE).Release: Makefile
365 |
--------------------------------------------------------------------------------
/ChatClient/chatLog.txt:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/ChatClient/chatLog.txt
--------------------------------------------------------------------------------
/ChatClient/chatconnection.cpp:
--------------------------------------------------------------------------------
1 | #include "chatconnection.h"
2 |
3 | static const int TransferTimeout = 30 * 1000;
4 | static const char SeparatorToken = ' ';
5 |
6 | // ChatConnection初始化和信号槽连接
7 | ChatConnection::ChatConnection(QObject *parent) :
8 | QTcpSocket(parent)
9 | {
10 | this->greetingMessage = QObject::tr("undefined");
11 | this->userName = QObject::tr("unknown");
12 | this->state = WaitingForGreeting;
13 | this->currentDataType = UNDEFINED;
14 | this->numBytesForCurrentDataType = -1;
15 | this->transferTimerId = 0;
16 | this->isGreetingMessageSent = false;
17 |
18 | connect(this, SIGNAL(readyRead()), this, SLOT(processReadyRead()));
19 | connect(this, SIGNAL(connected()), this, SLOT(sendGreetingMessage()));
20 | connect(this, SIGNAL(disconnected()), this, SLOT(handleDisconnected()));
21 | connect(this, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(handleSocketError(QAbstractSocket::SocketError)));
22 |
23 | }
24 |
25 | // 获取ChatConnection对端的名字
26 | QString ChatConnection::getPeerName()
27 | {
28 | return this->userName;
29 | }
30 |
31 | // 获取ChatConnection对端的IP地址
32 | QString ChatConnection::getPeerIP()
33 | {
34 | return this->ip.toString();
35 | }
36 |
37 | // 获取ChatConnection对端的端口号
38 | int ChatConnection::getPeerPort()
39 | {
40 | return this->port;
41 | }
42 |
43 | void ChatConnection::handleSocketError(QAbstractSocket::SocketError error)
44 | {
45 | emit this->socketError(this, error);
46 | }
47 |
48 | void ChatConnection::handleDisconnected()
49 | {
50 | emit this->disconnectedChat(this);
51 | }
52 |
53 | // 设置greeting消息
54 | void ChatConnection::setGreetingMessage(QString greet)
55 | {
56 | this->greetingMessage = greet;
57 | }
58 |
59 | // 定时器事件处理,此事件主要处理接收超时的问题(超时则关闭连接)
60 | void ChatConnection::timerEvent(QTimerEvent *timerEvent)
61 | {
62 | if(timerEvent->timerId() == this->transferTimerId)
63 | {
64 | this->abort();
65 | this->killTimer(transferTimerId);
66 | transferTimerId = 0;
67 | }
68 | }
69 |
70 | // 发送message消息
71 | bool ChatConnection::sendMessage(const QString message)
72 | {
73 | if(message.isEmpty())
74 | return false;
75 |
76 | QByteArray msg = message.toUtf8();
77 | QByteArray data = "MESSAGE " + QByteArray::number(msg.size()) + ' ' + msg;
78 | return this->write(data) == data.size();
79 | }
80 |
81 | // 发送greeting消息
82 | void ChatConnection::sendGreetingMessage()
83 | {
84 | QByteArray greeting = this->greetingMessage.toUtf8();
85 | QByteArray data = "GREETING " + QByteArray::number(greeting.size()) + ' ' + greeting;
86 | if( this->write(data) == data.size() )
87 | isGreetingMessageSent = true;
88 | }
89 |
90 | // 读取数据到buffer中,主要用于解析消息类型和消息长度
91 | int ChatConnection::readDataIntoBuffer(int maxSize)
92 | {
93 | if(maxSize > MaxBufferSize)
94 | return 0;
95 |
96 | int numBytesBeforeRead = this->buffer.size();
97 |
98 | if(numBytesBeforeRead == MaxBufferSize)
99 | {
100 | this->abort();
101 | return 0;
102 | }
103 |
104 | while(bytesAvailable() > 0 && buffer.size() < maxSize)
105 | {
106 | buffer.append(this->read(1));
107 | if(buffer.endsWith(SeparatorToken))
108 | break;
109 | }
110 |
111 | return buffer.size() - numBytesBeforeRead;
112 | }
113 |
114 | // 获取当前消息的消息长度
115 | int ChatConnection::dataLengthForCurrentDataType()
116 | {
117 | if(this->bytesAvailable() <= 0 || readDataIntoBuffer(MaxBufferSize) <= 0 || !buffer.endsWith(SeparatorToken))
118 | return 0;
119 |
120 | this->buffer.chop(1);
121 | int length = buffer.toInt();
122 | this->buffer.clear();
123 | return length;
124 | }
125 |
126 | // 解析消息的头部信息,包括消息类型和消息长度
127 | bool ChatConnection::readProtocolHeader()
128 | {
129 | if(this->transferTimerId != 0)
130 | {
131 | this->killTimer(this->transferTimerId);
132 | this->transferTimerId = 0;
133 | }
134 |
135 | if(this->readDataIntoBuffer() <= 0)
136 | {
137 | this->transferTimerId = this->startTimer(TransferTimeout);
138 | return false;
139 | }
140 |
141 | if(buffer == "MESSAGE ")
142 | this->currentDataType = MESSAGE;
143 | else if(buffer == "GREETING ")
144 | this->currentDataType = GREETING;
145 | else
146 | {
147 | this->currentDataType = UNDEFINED;
148 | this->abort();
149 | return false;
150 | }
151 |
152 | buffer.clear();
153 | this->numBytesForCurrentDataType = this->dataLengthForCurrentDataType();
154 | return true;
155 | }
156 |
157 | bool ChatConnection::hasEnoughData()
158 | {
159 | if(this->transferTimerId)
160 | {
161 | this->killTimer(transferTimerId);
162 | transferTimerId = 0;
163 | }
164 |
165 | if (numBytesForCurrentDataType <= 0)
166 | numBytesForCurrentDataType = this->dataLengthForCurrentDataType();
167 |
168 | if (bytesAvailable() < numBytesForCurrentDataType
169 | || numBytesForCurrentDataType <= 0)
170 | {
171 | this->transferTimerId = this->startTimer(TransferTimeout);
172 | return false;
173 | }
174 |
175 | return true;
176 | }
177 |
178 | // 处理socket接收消息的核心函数,根据连接状态进行不同的操作
179 | void ChatConnection::processReadyRead()
180 | {
181 | if(this->state == WaitingForGreeting)
182 | {
183 | if(!this->readProtocolHeader())
184 | return;
185 | if(this->currentDataType != GREETING)
186 | {
187 | this->abort();
188 | return;
189 | }
190 | this->state = ReadingGreeting;
191 | }
192 |
193 | if(this->state == ReadingGreeting)
194 | {
195 | if(!this->hasEnoughData())
196 | return;
197 |
198 | this->buffer = read(this->numBytesForCurrentDataType);
199 | if(buffer.size() != this->numBytesForCurrentDataType)
200 | {
201 | this->abort();
202 | return;
203 | }
204 |
205 | QString greeting = QString::fromUtf8(this->buffer);
206 |
207 | if(DEBUG)
208 | qDebug() << "Get greeting message: " << greeting;
209 |
210 | QStringList addrList = greeting.split(":");
211 | this->userName = addrList.at(0);
212 | QString ipStr = addrList.at(1);
213 | QString portStr = addrList.at(2);
214 | this->ip = QHostAddress(ipStr);
215 | this->port = portStr.toInt();
216 |
217 | this->currentDataType = UNDEFINED;
218 | this->numBytesForCurrentDataType = 0;
219 | this->buffer.clear();
220 |
221 | if(!this->isValid())
222 | {
223 | this->abort();
224 | return;
225 | }
226 |
227 | if(!this->isGreetingMessageSent)
228 | this->sendGreetingMessage();
229 |
230 | this->state = ReadyForUse;
231 | emit this->endGreeting(this);
232 | }
233 |
234 | do
235 | {
236 | if(this->currentDataType == UNDEFINED)
237 | {
238 | if(!readProtocolHeader())
239 | return;
240 | }
241 | if(!this->hasEnoughData())
242 | return;
243 | this->processData();
244 | }while(this->bytesAvailable() > 0);
245 | }
246 |
247 | // 该函数用于解析接收到的消息的内容部分
248 | void ChatConnection::processData()
249 | {
250 | this->buffer = this->read(this->numBytesForCurrentDataType);
251 | if(buffer.size() != this->numBytesForCurrentDataType)
252 | {
253 | this->abort();
254 | return;
255 | }
256 |
257 | switch (currentDataType) {
258 | case MESSAGE:
259 | emit newMessage(this->userName, QString::fromUtf8(buffer));
260 | break;
261 | default:
262 | break;
263 | }
264 |
265 | this->currentDataType = UNDEFINED;
266 | this->numBytesForCurrentDataType = -1;
267 | this->buffer.clear();
268 | }
269 |
270 |
--------------------------------------------------------------------------------
/ChatClient/chatconnection.h:
--------------------------------------------------------------------------------
1 | /* 说明:
2 | * 对于整个ChatConnection来说,其主要功能是提供用于建立聊天连接和进行聊天交互的信息接收与发送过程
3 | * 有几个设计性说明:
4 | * (1) ChatConnectionState 标识当前连接的状态,分别为等待greeting、读取greeting和读取聊天信息
5 | * (2) DataType 标识接收信息的类型,主要有greeting信息和message信息以及未定义的信息(错误)
6 | * 对于其结构来说,主要分为下面几个方面:
7 | * 1. 我们设置Greeting信息用于最初的连接建立时的连通性检测
8 | * peerHost <--->Greeting<---> peerHost
9 | * 当连接建立成功之后(发送connected信号),便发送greeting消息;同时,连接建立成功之后,连接工作在等待greeting的状态
10 | * 2. 对于消息的传递,我们设置了"消息类型 消息长度 消息内容"的传输格式,通过空格键相隔离
11 | * 因此,当我们解析消息时,首先应该去解析消息类型,然后读取消息长度,最后根据消息长度读取消息的内容
12 | * 3. 另外,对于ChatConnection,我们通过peer端的userName去标识该连接
13 | */
14 |
15 | #ifndef CHATCONNECTION_H
16 | #define CHATCONNECTION_H
17 |
18 | #include "header.h"
19 | #include
20 |
21 | class ChatConnection : public QTcpSocket
22 | {
23 | Q_OBJECT
24 | public:
25 | explicit ChatConnection(QObject *parent = 0);
26 |
27 | enum ChatConnectionState{
28 | WaitingForGreeting,
29 | ReadingGreeting,
30 | ReadyForUse
31 | };
32 |
33 | enum DataType{
34 | MESSAGE,
35 | GREETING,
36 | UNDEFINED
37 | };
38 |
39 | QString getPeerName();
40 | QString getPeerIP();
41 | int getPeerPort();
42 | void setGreetingMessage(QString message);
43 | bool sendMessage(QString message);
44 |
45 | signals:
46 | void endGreeting(ChatConnection *);
47 | void newMessage(QString from, QString message);
48 | void disconnectedChat(ChatConnection *);
49 | void socketError(ChatConnection *, QAbstractSocket::SocketError);
50 |
51 | protected:
52 | void timerEvent(QTimerEvent *);
53 |
54 | private slots:
55 | void processReadyRead();
56 | void sendGreetingMessage();
57 | void handleDisconnected();
58 | void handleSocketError(QAbstractSocket::SocketError);
59 |
60 | private:
61 | int readDataIntoBuffer(int maxSize = MaxBufferSize);
62 | int dataLengthForCurrentDataType();
63 | bool readProtocolHeader();
64 | bool hasEnoughData();
65 | void processData();
66 |
67 | QString userName; //通过远端的信息来标识该连接
68 | QHostAddress ip;
69 | int port;
70 | QString greetingMessage;
71 | QByteArray buffer;
72 | enum ChatConnectionState state;
73 | enum DataType currentDataType;
74 | int numBytesForCurrentDataType;
75 | int transferTimerId;
76 | bool isGreetingMessageSent;
77 | };
78 |
79 | #endif // CHATCONNECTION_H
80 |
--------------------------------------------------------------------------------
/ChatClient/chatdialog.cpp:
--------------------------------------------------------------------------------
1 | #include "chatdialog.h"
2 |
3 | ChatDialog::ChatDialog(QWidget *parent, QString username, QString peername, QString peeraddr, ChatConnection *connection) :
4 | QDialog(parent)
5 | {
6 | this->userName = username;
7 | this->chatSession = connection;
8 |
9 | if(DEBUG)
10 | qDebug() << "Peer addr string is: " << peeraddr;
11 |
12 | //this->iconLabel = new QLabel(QObject::tr("XXXXX\nXXXXX\nXXXXX"), this);
13 | //this->iconLabel->setAlignment(Qt::AlignCenter);
14 | this->peerName = new QLabel(this);
15 | this->peerAddress = new QLabel(this);
16 | this->logChat = new QTextEdit();
17 | this->msgSend = new QLineEdit();
18 | this->sendButton = new QPushButton(QObject::tr("Send"), this);
19 | this->msgSend->setFocusPolicy(Qt::StrongFocus);
20 | this->logChat->setFocusPolicy(Qt::NoFocus);
21 | this->logChat->setReadOnly(true);
22 |
23 | this->peerName->setText("Username: " + peername);
24 | this->peerAddress->setText("Address: " + peeraddr);
25 | this->setWindowTitle(peername + "@" + peeraddr);
26 | this->initLayout();
27 | this->resize(QSize(480, 360));
28 |
29 | connect(sendButton, SIGNAL(clicked()), this, SLOT(handleToSendMessage()));
30 | connect(msgSend, SIGNAL(returnPressed()), this, SLOT(handleToSendMessage()));
31 |
32 | connect(chatSession, SIGNAL(newMessage(QString, QString)), this, SLOT(handleReceivedMssage(QString, QString)));
33 | connect(chatSession, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(handleConnectionError(QAbstractSocket::SocketError)));
34 | connect(this, SIGNAL(rejected()), this, SLOT(handleRejected()));
35 | }
36 |
37 | ChatDialog::~ChatDialog()
38 | {
39 |
40 | }
41 |
42 | void ChatDialog::initLayout()
43 | {
44 | QVBoxLayout *infoLayout = new QVBoxLayout;
45 | infoLayout->addWidget(peerName);
46 | infoLayout->addWidget(peerAddress);
47 |
48 | /****************************************
49 | QHBoxLayout *peerLayout = new QHBoxLayout;
50 | peerLayout->addWidget(iconLabel);
51 | peerLayout->addLayout(infoLayout);
52 | peerLayout->setStretch(0, 1);
53 | peerLayout->setStretch(1, 6);
54 | ****************************************/
55 |
56 | QHBoxLayout *sendLayout = new QHBoxLayout;
57 | sendLayout->addWidget(msgSend);
58 | sendLayout->addWidget(sendButton);
59 | sendLayout->setStretch(0, 5);
60 | sendLayout->setStretch(1, 1);
61 |
62 | QVBoxLayout *dialogLayout = new QVBoxLayout;
63 | //dialogLayout->addLayout(peerLayout);
64 | dialogLayout->addLayout(infoLayout);
65 | dialogLayout->addWidget(logChat);
66 | dialogLayout->addLayout(sendLayout);
67 | dialogLayout->setStretch(0, 1);
68 | dialogLayout->setStretch(1, 8);
69 | dialogLayout->setStretch(2, 2);
70 |
71 | this->setLayout(dialogLayout);
72 | }
73 |
74 | void ChatDialog::handleReceivedMssage(QString from, QString message)
75 | {
76 | if (from.isEmpty() || message.isEmpty())
77 | return;
78 |
79 | QDateTime time = QDateTime::currentDateTime();
80 | QString timeString = time.toString("hh:mm:ss MM-dd");
81 | QString infoString = from + "(" + timeString + "): ";
82 | QColor color = this->logChat->textColor();
83 | this->logChat->setTextColor(Qt::blue);
84 | this->logChat->append(infoString);
85 | this->logChat->append(message + "\n");
86 | this->logChat->setTextColor(color);
87 | QScrollBar *bar = logChat->verticalScrollBar();
88 | bar->setValue(bar->maximum());
89 | }
90 |
91 | void ChatDialog::readAndDisplayHistory(QList strList)
92 | {
93 | QColor color = this->logChat->textColor();
94 | this->logChat->setTextColor(Qt::blue);
95 | foreach(QString s, strList)
96 | this->logChat->append(s);
97 | this->logChat->setTextColor(color);
98 | QScrollBar *bar = logChat->verticalScrollBar();
99 | bar->setValue(bar->maximum());
100 | }
101 |
102 | void ChatDialog::handleToSendMessage()
103 | {
104 | QString text = this->msgSend->text();
105 | if (text.isEmpty())
106 | return;
107 |
108 | QColor color = logChat->textColor();
109 | if (text.startsWith(QChar('/'))) {
110 | this->logChat->setTextColor(Qt::black);
111 | this->logChat->append(tr("Unknown command: %1")
112 | .arg(text.left(text.indexOf(' '))));
113 | }
114 | else
115 | {
116 | if(!chatSession->sendMessage(text))
117 | {
118 | this->logChat->setTextColor(Qt::red);
119 | this->logChat->append("Transfer Error: cannot send message: " + text);
120 | this->msgSend->clear();
121 | this->logChat->setTextColor(color);
122 | QScrollBar *bar = logChat->verticalScrollBar();
123 | bar->setValue(bar->maximum());
124 |
125 | if(DEBUG)
126 | qDebug() << "Error send message.";
127 | return;
128 | }
129 |
130 | QDateTime time = QDateTime::currentDateTime();
131 | QString timeString = time.toString("hh:mm:ss MM-dd");
132 | QString infoString = this->userName + "(" + timeString + ") : ";
133 |
134 | QColor color = this->logChat->textColor();
135 | this->logChat->setTextColor(Qt::black);
136 | this->logChat->append(infoString);
137 | this->logChat->append(text + "\n");
138 | this->logChat->setTextColor(color);
139 |
140 | QScrollBar *bar = logChat->verticalScrollBar();
141 | bar->setValue(bar->maximum());
142 | }
143 |
144 | this->msgSend->clear();
145 | this->logChat->setTextColor(color);
146 |
147 | if(DEBUG)
148 | qDebug() << "Send Message Success" << endl;
149 | }
150 |
151 | void ChatDialog::handleConnectionError(QAbstractSocket::SocketError error)
152 | {
153 | this->chatSession->close();
154 | QString errorString;
155 | switch(error)
156 | {
157 | case QAbstractSocket::ConnectionRefusedError:
158 | errorString = "Connection refused!";
159 | break;
160 | case QAbstractSocket::RemoteHostClosedError:
161 | errorString = "Remote host closed.";
162 | break;
163 | case QAbstractSocket::HostNotFoundError:
164 | errorString = "Host not found!";
165 | break;
166 | case QAbstractSocket::NetworkError:
167 | errorString = "Network error!";
168 | break;
169 | case QAbstractSocket::AddressInUseError:
170 | errorString = "Address already in use!";
171 | break;
172 | case QAbstractSocket::UnknownSocketError:
173 | default:
174 | errorString = "Unknown socket error!";
175 | break;
176 | }
177 | QColor color = this->logChat->textColor();
178 | this->logChat->setTextColor(Qt::red);
179 | this->logChat->append("Connection Error:" + errorString);
180 | this->logChat->setTextColor(color);
181 | }
182 |
183 | void ChatDialog::handleRejected()
184 | {
185 | emit this->dialogExit(this->chatSession);
186 | this->chatSession->close();
187 | }
188 |
--------------------------------------------------------------------------------
/ChatClient/chatdialog.h:
--------------------------------------------------------------------------------
1 | #ifndef CHATDIALOG_H
2 | #define CHATDIALOG_H
3 |
4 | #include "header.h"
5 | #include "chatconnection.h"
6 | #include
7 |
8 | class ChatDialog : public QDialog
9 | {
10 | Q_OBJECT
11 |
12 | public:
13 | explicit ChatDialog(QWidget *parent = 0, QString username = "localhost", QString peername = "unknown", QString peeraddr = "null", ChatConnection *connection = NULL);
14 | ~ChatDialog();
15 |
16 | void readAndDisplayHistory(QList);
17 |
18 | signals:
19 | void dialogExit(ChatConnection *);
20 |
21 | public slots:
22 | void handleReceivedMssage(QString from, QString message);
23 | void handleToSendMessage();
24 | void handleConnectionError(QAbstractSocket::SocketError);
25 | void handleRejected();
26 |
27 | private:
28 | // private functions
29 | void initLayout();
30 |
31 | /*Qt Widgets*/
32 | //QLabel *iconLabel;
33 | QLabel *peerName;
34 | QLabel *peerAddress;
35 | QTextEdit *logChat;
36 | QLineEdit *msgSend;
37 | QPushButton *sendButton;
38 |
39 | // Connection part
40 | QString userName;
41 | ChatConnection *chatSession;
42 | };
43 |
44 | #endif // CHATDIALOG_H
45 |
--------------------------------------------------------------------------------
/ChatClient/chatserver.cpp:
--------------------------------------------------------------------------------
1 | #include "chatserver.h"
2 |
3 | ChatServer::ChatServer(QObject *parent) :
4 | QTcpServer(parent)
5 | {
6 | this->myIp = QHostAddress::AnyIPv4;
7 | this->myPort = 9001;
8 | }
9 |
10 | void ChatServer::setChatServerInfo(QHostAddress &ip, int &port)
11 | {
12 | this->myIp = ip;
13 | this->myPort = port;
14 | }
15 |
16 | bool ChatServer::startServer()
17 | {
18 | return this->listen(this->myIp, this->myPort);
19 | }
20 |
21 | void ChatServer::incomingConnection(qintptr socketDescriptor)
22 | {
23 | ChatConnection *connection = new ChatConnection(this);
24 | connection->setSocketDescriptor(socketDescriptor);
25 | emit newChatConnection(connection);
26 | }
27 |
28 |
--------------------------------------------------------------------------------
/ChatClient/chatserver.h:
--------------------------------------------------------------------------------
1 | #ifndef CHATSERVER_H
2 | #define CHATSERVER_H
3 |
4 | #include "header.h"
5 | #include "chatconnection.h"
6 | #include
7 |
8 | class ChatServer : public QTcpServer
9 | {
10 | Q_OBJECT
11 | public:
12 | explicit ChatServer(QObject *parent = 0);
13 |
14 | void setChatServerInfo(QHostAddress &ip, int &port);
15 | bool startServer();
16 |
17 | signals:
18 | void newChatConnection(ChatConnection *connection);
19 |
20 | protected:
21 | void incomingConnection(qintptr socketDescriptor);
22 |
23 | private:
24 | QHostAddress myIp;
25 | int myPort;
26 | };
27 |
28 | #endif // CHATSERVER_H
29 |
--------------------------------------------------------------------------------
/ChatClient/debug.log:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/ChatClient/debug.log
--------------------------------------------------------------------------------
/ChatClient/header.h:
--------------------------------------------------------------------------------
1 | #ifndef HEADER_H
2 | #define HEADER_H
3 |
4 | // General Methods
5 | #include
6 | #include
7 | #include
8 | #include
9 | #include
10 | #include
11 | #include
12 | #include
13 | #include
14 | #include
15 | #include
16 | #include
17 | #include
18 | #include
19 |
20 | // Widgets
21 | #include
22 | #include
23 | #include
24 | #include
25 | #include
26 | #include
27 | #include
28 | #include
29 | #include
30 | #include
31 | #include
32 | #include
33 | #include
34 | #include
35 | #include
36 | #include
37 |
38 | // Notification Methods
39 | #include
40 |
41 | // Qt Network
42 | #include
43 | #include
44 | #include
45 | #include
46 | #include
47 | #include
48 |
49 | // Related to Qt Mysql operations
50 | #include
51 | #include
52 | #include
53 | #include
54 |
55 | // Related to Json File operations
56 | #include
57 | #include
58 | #include
59 | #include
60 |
61 | #define MaxBufferSize 1024000
62 | #define DEBUG 0
63 |
64 | #endif // HEADER_H
65 |
--------------------------------------------------------------------------------
/ChatClient/images/chatroom.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/ChatClient/images/chatroom.ico
--------------------------------------------------------------------------------
/ChatClient/images/icon.rc:
--------------------------------------------------------------------------------
1 | IDI_ICON1 ICON DISCARDABLE "chatroom.ico"
--------------------------------------------------------------------------------
/ChatClient/logindialog.cpp:
--------------------------------------------------------------------------------
1 | #include "logindialog.h"
2 |
3 | LoginDialog::LoginDialog(QWidget *parent)
4 | : QDialog(parent)
5 | {
6 | // Initialization Parts
7 | this->loginLogo = new QLabel(QObject::tr("Register client"), this);
8 | this->loginLogo->setAlignment(Qt::AlignCenter);
9 |
10 | this->loginUsername = new QLabel(QObject::tr("Username:"), this);
11 | this->editUsername = new QLineEdit(this);
12 | this->localIPAddress = new QLabel(QObject::tr("Local IP:"), this);
13 | this->localIPAddressBox = new QComboBox(this);
14 | this->localPort = new QLabel(QObject::tr("Local Port:"), this);
15 | this->localPortBox = new QSpinBox(this);
16 | this->registerIpLabel = new QLabel(QObject::tr("Server IP:"), this);
17 | this->registerIpEdit = new QLineEdit(this);
18 | this->registerPortLabel = new QLabel(QObject::tr("Server Port"), this);
19 | this->registerPortBox = new QSpinBox(this);
20 | this->registerIpLabel->setBuddy(this->registerIpEdit);
21 | this->registerPortLabel->setBuddy(this->registerPortBox);
22 | this->loginUsername->setBuddy(this->editUsername);
23 | this->localIPAddress->setBuddy(this->localIPAddressBox);
24 | this->localPort->setBuddy(this->localPortBox);
25 |
26 | this->networkInterfacesCombo();
27 | this->localPortBox->setRange(1024, 65535);
28 | this->localPortBox->setValue(9001);
29 | this->registerPortBox->setRange(1024, 65535);
30 | this->registerPortBox->setValue(10001);
31 | this->editUsername->setText("unknown");
32 | this->registerIpEdit->setText("192.168.1.106");
33 |
34 | // Button Settings
35 | this->doneButton = new QPushButton(QObject::tr("Register"), this);
36 | this->cancelButton = new QPushButton(QObject::tr("Cancel"), this);
37 | this->doneButton->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
38 | this->cancelButton->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
39 |
40 | this->initLayout();
41 | this->resize(QSize(300, 220));
42 | this->setMinimumSize(QSize(250, 180));
43 | this->setWindowTitle(QObject::tr("Client Register"));
44 |
45 | connect(doneButton, SIGNAL(clicked()), this, SLOT(on_doneButton_clicked()));
46 | connect(cancelButton, SIGNAL(clicked()), this, SLOT(on_cancelButton_clicked()));
47 | }
48 |
49 | LoginDialog::~LoginDialog()
50 | {
51 | }
52 |
53 | void LoginDialog::networkInterfacesCombo()
54 | {
55 | QList list = QNetworkInterface::allAddresses();
56 | foreach( QHostAddress address, list )
57 | {
58 | if(address.protocol() == QAbstractSocket::IPv4Protocol)
59 | this->localIPAddressBox->addItem(address.toString());
60 | }
61 | }
62 |
63 | void LoginDialog::initLayout()
64 | {
65 | // Layout Manager
66 | QHBoxLayout *userLayout = new QHBoxLayout;
67 | userLayout->addWidget(this->loginUsername);
68 | userLayout->addWidget(this->editUsername);
69 | userLayout->setStretch(0, 1);
70 | userLayout->setStretch(1, 3);
71 |
72 | QHBoxLayout *ipLayout = new QHBoxLayout;
73 | ipLayout->addWidget(this->localIPAddress);
74 | ipLayout->addWidget(this->localIPAddressBox);
75 | ipLayout->setStretch(0, 1);
76 | ipLayout->setStretch(1, 3);
77 |
78 | QHBoxLayout *portLayout = new QHBoxLayout;
79 | portLayout->addWidget(this->localPort);
80 | portLayout->addWidget(this->localPortBox);
81 | portLayout->setStretch(0, 1);
82 | portLayout->setStretch(1, 3);
83 |
84 | QHBoxLayout *ripLayout = new QHBoxLayout;
85 | ripLayout->addWidget(this->registerIpLabel);
86 | ripLayout->addWidget(this->registerIpEdit);
87 | ripLayout->setStretch(0, 1);
88 | ripLayout->setStretch(1, 3);
89 |
90 | QHBoxLayout *rportLayout = new QHBoxLayout;
91 | rportLayout->addWidget(this->registerPortLabel);
92 | rportLayout->addWidget(this->registerPortBox);
93 | rportLayout->setStretch(0, 1);
94 | rportLayout->setStretch(1, 3);
95 |
96 | QHBoxLayout *buttonLayout = new QHBoxLayout;
97 | buttonLayout->addStretch();
98 | buttonLayout->addWidget(this->doneButton);
99 | buttonLayout->addStretch();
100 | buttonLayout->addWidget(this->cancelButton);
101 | buttonLayout->addStretch();
102 |
103 | QVBoxLayout *mainLayout = new QVBoxLayout;
104 | mainLayout->addWidget(this->loginLogo);
105 | mainLayout->addLayout(userLayout);
106 | mainLayout->addLayout(ipLayout);
107 | mainLayout->addLayout(portLayout);
108 | mainLayout->addLayout(ripLayout);
109 | mainLayout->addLayout(rportLayout);
110 | mainLayout->addStretch();
111 | mainLayout->addLayout(buttonLayout);
112 | mainLayout->setStretch(0, 2);
113 | mainLayout->setStretch(1, 1);
114 | mainLayout->setStretch(2, 1);
115 | mainLayout->setStretch(3, 1);
116 | mainLayout->setStretch(4, 1);
117 | mainLayout->setStretch(5, 1);
118 | mainLayout->setStretch(6, 1);
119 |
120 | this->setLayout(mainLayout);
121 | }
122 |
123 |
124 | QString LoginDialog::getUsername()
125 | {
126 | QString username = this->editUsername->text();
127 | if(username.isEmpty())
128 | username = "unknown";
129 |
130 | return username;
131 | }
132 |
133 | QString LoginDialog::getLocalServerIP()
134 | {
135 | QString ipAddress = this->localIPAddressBox->currentText();
136 | if(ipAddress.isEmpty())
137 | ipAddress = "localhost";
138 |
139 | return ipAddress;
140 | }
141 |
142 | int LoginDialog::getLocalServerPort()
143 | {
144 | return this->localPortBox->value();
145 | }
146 |
147 | QString LoginDialog::getRegisterServerIP()
148 | {
149 | QString serverIp = this->registerIpEdit->text();
150 | if(serverIp.isEmpty())
151 | serverIp = "192.168.1.106";
152 |
153 | return serverIp;
154 | }
155 |
156 | int LoginDialog::getRegisterServerPort()
157 | {
158 | return this->registerPortBox->value();
159 | }
160 |
161 | void LoginDialog::on_doneButton_clicked()
162 | {
163 | this->accept();
164 | }
165 |
166 | void LoginDialog::on_cancelButton_clicked()
167 | {
168 | this->reject();
169 | }
170 |
--------------------------------------------------------------------------------
/ChatClient/logindialog.h:
--------------------------------------------------------------------------------
1 | #ifndef LOGINDIALOG_H
2 | #define LOGINDIALOG_H
3 |
4 | #include "header.h"
5 | #include
6 |
7 |
8 | class LoginDialog : public QDialog
9 | {
10 | Q_OBJECT
11 |
12 | public:
13 | LoginDialog(QWidget *parent = 0);
14 | ~LoginDialog();
15 |
16 | QString getUsername();
17 | QString getLocalServerIP();
18 | int getLocalServerPort();
19 | QString getRegisterServerIP();
20 | int getRegisterServerPort();
21 |
22 | signals:
23 |
24 |
25 | public slots:
26 | void on_doneButton_clicked();
27 | void on_cancelButton_clicked();
28 |
29 | private:
30 | // private functions
31 | void networkInterfacesCombo();
32 | void initLayout();
33 |
34 | // login information
35 | QLabel *loginLogo;
36 | QLabel *loginUsername;
37 | QLineEdit *editUsername;
38 | QLabel *localIPAddress;
39 | QComboBox *localIPAddressBox;
40 | QLabel *localPort;
41 | QSpinBox *localPortBox;
42 | QLabel *registerIpLabel;
43 | QLineEdit *registerIpEdit;
44 | QLabel *registerPortLabel;
45 | QSpinBox *registerPortBox;
46 | QPushButton *doneButton;
47 | QPushButton *cancelButton;
48 |
49 | };
50 |
51 | #endif // LOGINDIALOG_H
52 |
--------------------------------------------------------------------------------
/ChatClient/main.cpp:
--------------------------------------------------------------------------------
1 | #include "logindialog.h"
2 | #include "mainwindow.h"
3 | #include "chatdialog.h"
4 | #include
5 |
6 | void outputMessage(QtMsgType type, const QMessageLogContext &context, const QString &msg);
7 | void clearLogFile();
8 |
9 | int main(int argc, char *argv[])
10 | {
11 | clearLogFile();
12 | qInstallMessageHandler(outputMessage);
13 | QApplication a(argc, argv);
14 | MainWindow w;
15 | w.show();
16 | return a.exec();
17 | }
18 |
19 | void clearLogFile()
20 | {
21 | QFile file("chatLog.txt");
22 | file.open(QIODevice::WriteOnly | QIODevice::Append);
23 | file.resize(0);
24 | file.flush();
25 | file.close();
26 | }
27 |
28 | void outputMessage(QtMsgType type, const QMessageLogContext &context, const QString &msg)
29 | {
30 | static QMutex mutex;
31 |
32 | QString text;
33 | switch(type)
34 | {
35 | case QtDebugMsg:
36 | text = QString("Debug:");
37 | break;
38 |
39 | case QtWarningMsg:
40 | text = QString("Warning:");
41 | break;
42 |
43 | case QtCriticalMsg:
44 | text = QString("Critical:");
45 | break;
46 |
47 | case QtFatalMsg:
48 | text = QString("Fatal:");
49 | break;
50 |
51 | default:
52 | break;
53 | }
54 |
55 | QString context_info = QString("(%1:%2)").arg(QString(context.file)).arg(context.line);
56 | QString message = QString("%1 %2\r\n %3").arg(text).arg(context_info).arg(msg);
57 |
58 | mutex.lock();
59 |
60 | QFile file("chatLog.txt");
61 | file.open(QIODevice::WriteOnly | QIODevice::Append);
62 | QTextStream text_stream(&file);
63 | text_stream << message << "\r\n";
64 | file.flush();
65 | file.close();
66 |
67 | mutex.unlock();
68 | }
69 |
--------------------------------------------------------------------------------
/ChatClient/mainwindow.cpp:
--------------------------------------------------------------------------------
1 | #include "mainwindow.h"
2 |
3 | MainWindow::MainWindow(QWidget *parent) :
4 | QMainWindow(parent)
5 | {
6 | this->myName = new QLabel(QObject::tr("Username: none"), this);
7 | this->myAddress = new QLabel(QObject::tr("Address: client unregistered."), this);
8 | //this->myIcon = new QLabel(QObject::tr("XXXXX\nXXXXX\nXXXXX"), this);
9 | //this->myIcon->setAlignment(Qt::AlignCenter);
10 | this->infoLabel = new QLabel(QObject::tr("Active peer list:"), this);
11 | this->peerListWidget = new QListWidget();
12 | this->chatButton = new QPushButton(QObject::tr("New Chat"), this);
13 | this->registerButton = new QPushButton(QObject::tr("Register"), this);
14 | this->checkButton = new QPushButton(QObject::tr("Recv Chat"), this);
15 | this->remoteServerLabel = new QLabel("Not set register server info.");
16 | this->server = new ChatServer(this);
17 | this->registConnection = new RegisterConnection(this);
18 | this->initLayout();
19 | this->setWindowTitle(QObject::tr("Chat Room"));
20 | this->resize(QSize(340, 500));
21 | this->setMinimumSize(QSize(280, 320));
22 |
23 | connect(this->chatButton, SIGNAL(clicked()), this, SLOT(handleActiveConnection()));
24 | connect(this->registerButton, SIGNAL(clicked()), this, SLOT(handleRegisterAction()));
25 | connect(this->checkButton, SIGNAL(clicked()), this, SLOT(handleCheckDialog()));
26 | }
27 |
28 | MainWindow::~MainWindow()
29 | {
30 | this->server->close();
31 | this->registConnection->close();
32 | }
33 |
34 | void MainWindow::initLayout()
35 | {
36 | QVBoxLayout *myTextLayout = new QVBoxLayout;
37 | myTextLayout->addWidget(myName);
38 | myTextLayout->addWidget(myAddress);
39 |
40 | /******************************************
41 | QHBoxLayout *myInfoLayout = new QHBoxLayout;
42 | myInfoLayout->addWidget(myIcon);
43 | myInfoLayout->addLayout(myTextLayout);
44 | myInfoLayout->setStretch(0, 1);
45 | myInfoLayout->setStretch(1, 5);
46 | *******************************************/
47 |
48 | QHBoxLayout *chatLayout = new QHBoxLayout;
49 | chatLayout->addWidget(registerButton);
50 | chatLayout->addStretch();
51 | chatLayout->addWidget(checkButton);
52 | chatLayout->addWidget(chatButton);
53 |
54 | QVBoxLayout *mainLayout = new QVBoxLayout;
55 | //mainLayout->addLayout(myInfoLayout);
56 | mainLayout->addLayout(myTextLayout);
57 | mainLayout->addWidget(infoLabel);
58 | mainLayout->addWidget(peerListWidget);
59 | mainLayout->addLayout(chatLayout);
60 | mainLayout->addWidget(remoteServerLabel);
61 |
62 | QWidget *widget = new QWidget(this);
63 | widget->setLayout(mainLayout);
64 |
65 | this->setCentralWidget(widget);
66 | }
67 |
68 | // 网络模块启动部分,包括启动本地的聊天服务器,以及连接至注册服务器
69 | void MainWindow::initNetwork()
70 | {
71 | // 启动ChatServer
72 | if(DEBUG)
73 | {
74 | qDebug() << "Local server ip address: " << this->localServerIP.toString();
75 | qDebug() << "Local server port: " << this->localServerPort;
76 | }
77 |
78 | this->server->setChatServerInfo(this->localServerIP, this->localServerPort);
79 | if(this->server->startServer())
80 | {
81 | QString address = this->localServerIP.toString() + ":" + QString::number(this->localServerPort);
82 | this->myName->setText("Username: " + this->userName);
83 | this->myAddress->setText("Address: " + address);
84 |
85 | QString remoteAddress = QString("Register Server Info: ") + this->remoteServerIP.toString() + ":" + QString::number(this->remoteServerPort);
86 | this->remoteServerLabel->setText(remoteAddress);
87 |
88 | this->registerButton->setEnabled(false);
89 | if(DEBUG)
90 | qDebug() << "Local chat server started.";
91 | }
92 | else
93 | {
94 | this->remoteServerLabel->setText("Cannot start local chat server.");
95 | this->registerButton->setEnabled(true);
96 | QMessageBox::warning(this, tr("Error"), tr("Cannot start local chat server!"));
97 | if(DEBUG)
98 | qDebug() << "Cannot start local chat server.";
99 | return;
100 | }
101 | connect(server, SIGNAL(newChatConnection(ChatConnection*)), this, SLOT(handlePassiveConnection(ChatConnection*)));
102 |
103 | // 连接至中心注册服务器
104 | if(DEBUG)
105 | qDebug() << "Connect to register server.";
106 | this->registConnection->setLocalServerInfo(this->userName, this->localServerIP, this->localServerPort);
107 | this->registConnection->connectToHost(this->remoteServerIP, this->remoteServerPort);
108 | if(DEBUG)
109 | qDebug() << "Connected to register server.";
110 | connect(registConnection, SIGNAL(newPeerList(QString&)), this, SLOT(handleNewPeerList(QString&)));
111 | connect(registConnection, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(handleRegisterError(QAbstractSocket::SocketError)));
112 | }
113 |
114 | void MainWindow::handleRegisterAction()
115 | {
116 | LoginDialog *ld = new LoginDialog(this);
117 | if (ld->exec() != QDialog::Accepted)
118 | {
119 | QMessageBox::warning(this, tr("Warning"), tr("Client Register Canceled!"));
120 | return;
121 | }
122 |
123 | this->userName = ld->getUsername();
124 | this->localServerIP = ld->getLocalServerIP();
125 | this->localServerPort = ld->getLocalServerPort();
126 | this->remoteServerIP = ld->getRegisterServerIP();
127 | this->remoteServerPort = ld->getRegisterServerPort();
128 |
129 | if(DEBUG)
130 | {
131 | qDebug() << "Register client configuration done!";
132 | qDebug() << "Local server name: " << this->userName;
133 | qDebug() << "Local server ip address: " << this->localServerIP;
134 | qDebug() << "Local server port: " << this->localServerPort;
135 | }
136 |
137 | this->initNetwork();
138 | }
139 |
140 | void MainWindow::updateListWidget()
141 | {
142 | this->peerListWidget->clear();
143 | for(int i = 0; i < this->peerList.size(); i++)
144 | {
145 | QString comment = "";
146 | PeerInfo *pi = this->peerList.at(i);
147 | QString name = pi->getPeerName();
148 | if(name == this->userName)
149 | comment = " ( local )";
150 | if(this->tempMsgs.contains(name))
151 | comment = " ( new message: " + QString::number(this->tempMsgs[name].size()) + " )";
152 | QString itemString = pi->getPeerName() + "@" + pi->getPeerIP() + ":" + QString::number(pi->getPeerPort()) + comment;
153 | this->peerListWidget->addItem(new QListWidgetItem(itemString));
154 | }
155 | }
156 |
157 | void MainWindow::handleNewPeerList(QString &peerListString)
158 | {
159 | this->peerList.clear();
160 | if(peerListString.isEmpty())
161 | return;
162 |
163 | QString username, comment;
164 | QHostAddress ip;
165 | int port;
166 | QStringList peerInfoList = peerListString.split(";");
167 | foreach(QString peerInfo, peerInfoList)
168 | {
169 | comment = QString("");
170 | QStringList items = peerInfo.split("@");
171 | username = items.at(0);
172 | QString addr = items.at(1);
173 | QStringList addrList = addr.split(":");
174 | QString ipString = addrList.at(0);
175 | ip = QHostAddress(ipString);
176 | QString portString = addrList.at(1);
177 | port = portString.toInt();
178 | PeerInfo *pinfo = new PeerInfo(this, username, ip, port);
179 | this->peerList.push_back(pinfo);
180 | }
181 |
182 | this->updateListWidget();
183 | }
184 |
185 | void MainWindow::handlePassiveConnection(ChatConnection *connection)
186 | {
187 | if(DEBUG)
188 | qDebug() << "New passive chat connection.";
189 |
190 | QString greeting = this->userName + ":" + this->localServerIP.toString() + ":" + QString::number(this->localServerPort);
191 | connection->setGreetingMessage(greeting);
192 |
193 | this->addChatConnection(connection);
194 |
195 | connect(connection, SIGNAL(socketError(ChatConnection*,QAbstractSocket::SocketError)),
196 | this, SLOT(handleChatConnectionError(ChatConnection*,QAbstractSocket::SocketError)));
197 | connect(connection, SIGNAL(endGreeting(ChatConnection*)), this, SLOT(handlePassiveNewChat(ChatConnection*)));
198 | }
199 |
200 | void MainWindow::handleActiveConnection()
201 | {
202 | if(DEBUG)
203 | qDebug() << "New active chat connection.";
204 |
205 | QListWidgetItem *item = this->peerListWidget->currentItem();
206 | if(!item)
207 | {
208 | QMessageBox::warning(this, tr("Warning"), tr("Please select one peer."));
209 |
210 | if(DEBUG)
211 | qDebug() << "Select no peer to connect.";
212 | return;
213 | }
214 |
215 | QString connInfo = item->text();
216 | QStringList strList = connInfo.split("@");
217 | QString name = strList.at(0);
218 | QString addr = strList.at(1);
219 | QStringList addrList = addr.split(":");
220 | QString ipStr = addrList.at(0);
221 | QString portExtStr = addrList.at(1);
222 | QHostAddress ip = QHostAddress(ipStr);
223 | QStringList eList = portExtStr.split(" ");
224 | QString portStr = eList.at(0);
225 | int port = portStr.toInt();
226 |
227 | if(name == this->userName && ipStr == this->localServerIP.toString() && port == this->localServerPort)
228 | {
229 | QMessageBox::warning(this, tr("Warning"), tr("Cannot select local server."));
230 |
231 | if(DEBUG)
232 | qDebug() << "Select local server to connect.";
233 |
234 | return;
235 | }
236 |
237 | ChatConnection *cp = this->findChatConnection(name, ipStr);
238 | if(cp)
239 | {
240 | QMessageBox::warning(this, tr("Warning"), tr("Connection already established."));
241 |
242 | if(DEBUG)
243 | qDebug() << "New error: Connection already established.";
244 | return;
245 | }
246 |
247 | if(DEBUG)
248 | {
249 | qDebug() << "Establish chat connection to selected peer.";
250 | qDebug() << "Remote peer ip: " << ip.toString();
251 | qDebug() << "Remote peer port: " << port;
252 | }
253 |
254 | ChatConnection *newConnection = new ChatConnection(this);
255 | QString greeting = this->userName + ":" + this->localServerIP.toString() + ":" + QString::number(this->localServerPort);
256 | newConnection->setGreetingMessage(greeting);
257 | newConnection->connectToHost(ip, port);
258 | this->addChatConnection(newConnection);
259 | connect(newConnection, SIGNAL(socketError(ChatConnection*, QAbstractSocket::SocketError)),
260 | this, SLOT(handleChatConnectionError(ChatConnection*, QAbstractSocket::SocketError)));
261 | connect(newConnection, SIGNAL(endGreeting(ChatConnection*)), this, SLOT(handleNewChatDialog(ChatConnection*)));
262 |
263 | if(DEBUG)
264 | qDebug() << "Open new chat dialog to display chat process.";
265 | }
266 |
267 | void MainWindow::handleNewChatDialog(ChatConnection *connection)
268 | {
269 | QString peerName = connection->getPeerName();
270 | QString peerAddr = connection->getPeerIP() + ":" + QString::number(connection->getPeerPort());
271 |
272 | ChatDialog *newChat = new ChatDialog(this, this->userName, peerName, peerAddr, connection);
273 | connect(newChat, SIGNAL(dialogExit(ChatConnection*)), this, SLOT(handleDialogExit(ChatConnection*)));
274 | newChat->show();
275 | }
276 |
277 | void MainWindow::handleDialogExit(ChatConnection *connection)
278 | {
279 | this->removeChatConnection(connection);
280 | }
281 |
282 | void MainWindow::handleCheckDialog()
283 | {
284 | QListWidgetItem *item = this->peerListWidget->currentItem();
285 |
286 | if(!item)
287 | {
288 | QMessageBox::warning(this, tr("Warning"), tr("Please select one peer."));
289 |
290 | if(DEBUG)
291 | qDebug() << "Select no peer to read message.";
292 | return;
293 | }
294 |
295 | QString connInfo = item->text();
296 | QStringList strList = connInfo.split("@");
297 | QString name = strList.at(0);
298 | QString addr = strList.at(1);
299 | QStringList addrList = addr.split(":");
300 | QString ipStr = addrList.at(0);
301 |
302 | ChatConnection *cp = this->findChatConnection(name, ipStr);
303 | if(!cp)
304 | {
305 | QMessageBox::warning(this, tr("Warning"), tr("No connection or connection broked."));
306 |
307 | if(DEBUG)
308 | qDebug() << "No connection or connection broked.";
309 | return;
310 | }
311 |
312 | ChatDialog *newChat = new ChatDialog(this, this->userName, name, addr, cp);
313 | connect(newChat, SIGNAL(dialogExit(ChatConnection*)), this, SLOT(handleDialogExit(ChatConnection*)));
314 | QList hList = this->tempMsgs[name];
315 | newChat->readAndDisplayHistory(hList);
316 | this->tempMsgs.remove(name);
317 | this->updateListWidget();
318 | newChat->show();
319 | }
320 |
321 | void MainWindow::handlePassiveNewChat(ChatConnection *connection)
322 | {
323 | QList rcvInfoMsgs;
324 | QString name = connection->getPeerName();
325 | this->tempMsgs.insert(name, rcvInfoMsgs);
326 | connect(connection, SIGNAL(newMessage(QString, QString)), this, SLOT(handlePassiveMsgRecv(QString, QString)));
327 | }
328 |
329 | void MainWindow::handlePassiveMsgRecv(QString from, QString msg)
330 | {
331 | QDateTime time = QDateTime::currentDateTime();
332 | QString timeString = time.toString("hh:mm:ss MM-dd");
333 | QString infoString = from + "(" + timeString + "): \n";
334 | QString infoMsg = infoString + msg + "\n";
335 | this->tempMsgs[from].push_back(infoMsg);
336 | this->updateListWidget();
337 |
338 | if(DEBUG)
339 | qDebug() << "Handle passive received messages done.";
340 | }
341 |
342 | void MainWindow::handleChatConnectionError(ChatConnection *connection, QAbstractSocket::SocketError error)
343 | {
344 | if(DEBUG)
345 | qDebug() << "Chat connection Error.";
346 |
347 | QString errorString;
348 | switch(error)
349 | {
350 | case QAbstractSocket::ConnectionRefusedError:
351 | errorString = "Connection refused!";
352 | break;
353 | case QAbstractSocket::RemoteHostClosedError:
354 | errorString = "Remote host closed.";
355 | break;
356 | case QAbstractSocket::HostNotFoundError:
357 | errorString = "Host not found!";
358 | break;
359 | case QAbstractSocket::NetworkError:
360 | errorString = "Network error!";
361 | break;
362 | case QAbstractSocket::AddressInUseError:
363 | errorString = "Address already in use!";
364 | break;
365 | case QAbstractSocket::UnknownSocketError:
366 | default:
367 | errorString = "Unknown socket error!";
368 | break;
369 | }
370 | connection->close();
371 | this->removeChatConnection(connection);
372 |
373 | if(DEBUG)
374 | {
375 | qDebug() << "Chat connection error: " << errorString;
376 | qDebug() << "Handle chat connection error done.";
377 | }
378 | }
379 |
380 | void MainWindow::handleRegisterError(QAbstractSocket::SocketError error)
381 | {
382 | if(DEBUG)
383 | qDebug() << "Register network error.";
384 |
385 | QString errorString;
386 | switch(error)
387 | {
388 | case QAbstractSocket::ConnectionRefusedError:
389 | errorString = "Connection refused!";
390 | break;
391 | case QAbstractSocket::RemoteHostClosedError:
392 | errorString = "Remote host closed.";
393 | break;
394 | case QAbstractSocket::HostNotFoundError:
395 | errorString = "Host not found!";
396 | break;
397 | case QAbstractSocket::NetworkError:
398 | errorString = "Network error!";
399 | break;
400 | case QAbstractSocket::AddressInUseError:
401 | errorString = "Address already in use!";
402 | break;
403 | case QAbstractSocket::UnknownSocketError:
404 | default:
405 | errorString = "Unknown socket error!";
406 | break;
407 | }
408 | this->server->close();
409 | this->registConnection->close();
410 | this->peerList.clear();
411 | this->peerListWidget->clear();
412 | this->registerButton->setEnabled(true);
413 | this->remoteServerLabel->setText("Not set register server info.");
414 |
415 | QMessageBox::warning(this, tr("Register Error"), errorString);
416 |
417 | if(DEBUG)
418 | qDebug() << "Handle register network error done.";
419 | }
420 |
421 | void MainWindow::addChatConnection(ChatConnection *connection)
422 | {
423 | this->connList.push_back(connection);
424 |
425 | if(DEBUG)
426 | qDebug() << "Add new chat connection to connection list.";
427 | }
428 |
429 | void MainWindow::removeChatConnection(ChatConnection *connection)
430 | {
431 | this->connList.removeOne(connection);
432 |
433 | if(DEBUG)
434 | qDebug() << "Remove chat connection from connection list";
435 | }
436 |
437 | ChatConnection * MainWindow::findChatConnection(QString name, QString ip)
438 | {
439 | for(int i = 0; i < this->connList.size(); i++)
440 | {
441 | ChatConnection *cp = this->connList.at(i);
442 | qDebug() << "cp name: " << cp->getPeerName();
443 | qDebug() << "cp ip: " << cp->getPeerIP();
444 | qDebug() << "cp port" << cp->getPeerPort();
445 | if((cp->getPeerName() == name) &&
446 | (cp->getPeerIP() == ip))
447 | return cp;
448 | }
449 |
450 | return NULL;
451 | }
452 |
--------------------------------------------------------------------------------
/ChatClient/mainwindow.h:
--------------------------------------------------------------------------------
1 | #ifndef MAINWINDOW_H
2 | #define MAINWINDOW_H
3 |
4 | #include "header.h"
5 | #include "chatconnection.h"
6 | #include "registerconnection.h"
7 | #include "chatserver.h"
8 | #include "logindialog.h"
9 | #include "chatdialog.h"
10 | #include "peerinfo.h"
11 | #include
12 |
13 | class MainWindow : public QMainWindow
14 | {
15 | Q_OBJECT
16 | public:
17 | explicit MainWindow(QWidget *parent = 0);
18 | ~MainWindow();
19 |
20 | signals:
21 |
22 | public slots:
23 | void handleRegisterAction();
24 | void handleNewPeerList(QString &);
25 | void handleActiveConnection();
26 | void handleCheckDialog();
27 | void handlePassiveConnection(ChatConnection *);
28 | void handleChatConnectionError(ChatConnection *, QAbstractSocket::SocketError);
29 | void handleRegisterError(QAbstractSocket::SocketError);
30 | void handleNewChatDialog(ChatConnection *);
31 | void handlePassiveMsgRecv(QString, QString);
32 | void handlePassiveNewChat(ChatConnection *);
33 | void handleDialogExit(ChatConnection *);
34 |
35 | private:
36 | // private functions
37 | void initLayout();
38 | void initNetwork();
39 | void updateListWidget();
40 |
41 | // connections
42 | void addChatConnection(ChatConnection *);
43 | void removeChatConnection(ChatConnection *);
44 | ChatConnection* findChatConnection(QString name, QString ip);
45 |
46 | // gui widgets
47 | QLabel *myName;
48 | QLabel *myAddress;
49 | //QLabel *myIcon;
50 | QLabel *infoLabel;
51 | QListWidget *peerListWidget;
52 | QPushButton *chatButton;
53 | QPushButton *registerButton;
54 | QPushButton *checkButton;
55 | QLabel *remoteServerLabel;
56 |
57 | // Variables
58 | QString userName; // Local Server UserName
59 | QHostAddress localServerIP;
60 | int localServerPort;
61 | QHostAddress remoteServerIP;
62 | int remoteServerPort;
63 |
64 | // connections
65 | QMap> tempMsgs; //记录被动连接的接收信息
66 | QMap chatMap; //记录已打开的ChatDialog
67 | QList peerList; // 记录活跃的远端主机
68 | QList connList; // 用于管理所有聊天连接
69 | ChatServer *server; // 本地聊天连接监听服务器
70 | RegisterConnection *registConnection; // 与中心服务器相连接
71 | };
72 |
73 | #endif // MAINWINDOW_H
74 |
--------------------------------------------------------------------------------
/ChatClient/peerinfo.cpp:
--------------------------------------------------------------------------------
1 | #include "peerinfo.h"
2 |
3 | static const int TimeOut = 22 * 1000;
4 |
5 | PeerInfo::PeerInfo(QObject *parent, QString peername, QHostAddress ip, int port) :
6 | QObject(parent)
7 | {
8 | this->setPeerInfo(peername, ip, port);
9 | }
10 |
11 | PeerInfo::~PeerInfo()
12 | {
13 | }
14 |
15 | QString PeerInfo::getPeerName()
16 | {
17 | return this->peerName;
18 | }
19 |
20 | QString PeerInfo::getPeerIP()
21 | {
22 | return this->peerIP.toString();
23 | }
24 |
25 | int PeerInfo::getPeerPort()
26 | {
27 | return this->peerPort;
28 | }
29 |
30 | void PeerInfo::setPeerInfo(QString peername, QHostAddress ip, int port)
31 | {
32 | this->peerName = peername;
33 | this->peerIP = ip;
34 | this->peerPort = port;
35 | }
36 |
37 | void PeerInfo::clear()
38 | {
39 |
40 | }
41 |
--------------------------------------------------------------------------------
/ChatClient/peerinfo.h:
--------------------------------------------------------------------------------
1 | #ifndef PEERINFO_H
2 | #define PEERINFO_H
3 |
4 | #include "header.h"
5 | #include
6 |
7 | class PeerInfo : public QObject
8 | {
9 | Q_OBJECT
10 | public:
11 | explicit PeerInfo(QObject *parent = 0, QString peername = "unknown", QHostAddress ip = QHostAddress("127.0.0.1"), int port = 0);
12 | ~PeerInfo();
13 |
14 | QString getPeerName();
15 | QString getPeerIP();
16 | int getPeerPort();
17 | void setPeerInfo(QString, QHostAddress, int);
18 | void clear();
19 |
20 | private:
21 | QString peerName;
22 | QHostAddress peerIP;
23 | int peerPort;
24 | };
25 |
26 | #endif // PEERINFO_H
27 |
--------------------------------------------------------------------------------
/ChatClient/registerconnection.cpp:
--------------------------------------------------------------------------------
1 | #include "registerconnection.h"
2 |
3 | static const int TransferTimeout = 40 * 1000;
4 | static const int PeriodicInterval = 15 * 1000;
5 | static const char SeparateToken = ' ';
6 |
7 | RegisterConnection::RegisterConnection(QObject *parent) :
8 | QTcpSocket(parent)
9 | {
10 | this->greetingMessage = QObject::tr("Register Validation");
11 | this->registerMessage = QObject::tr(" ");
12 | this->state = WaitingForGreeting;
13 | this->currentDataType = UNDEFINED;
14 | this->isGreetingMessageSent = false;
15 | this->numBytesForCurrentDataType = -1;
16 | this->transferTimerId = 0;
17 | this->periodicTimer.setInterval(PeriodicInterval);
18 |
19 | connect(this, SIGNAL(readyRead()), this, SLOT(processReadyRead()));
20 | connect(&periodicTimer, SIGNAL(timeout()), this, SLOT(sendPeriodicRegisterMessage()));
21 | connect(this, SIGNAL(connected()), this, SLOT(sendGreetingMessage()));
22 | }
23 |
24 | void RegisterConnection::setLocalServerInfo(QString &name, QHostAddress &ip, int &port)
25 | {
26 | this->localUserName = name;
27 | this->localServerIP = ip;
28 | this->localServerPort = port;
29 | this->registerMessage = this->localUserName + '@' +
30 | this->localServerIP.toString() + ':' +
31 | QString::number(this->localServerPort);
32 | this->greetingMessage = this->localUserName + ':' +
33 | this->localServerIP.toString() + ':' +
34 | QString::number(this->localServerPort);
35 | }
36 |
37 | void RegisterConnection::timerEvent(QTimerEvent *timerEvent)
38 | {
39 | if(timerEvent->timerId() == this->transferTimerId)
40 | {
41 | this->abort();
42 | this->killTimer(transferTimerId);
43 | transferTimerId = 0;
44 | }
45 | }
46 |
47 | void RegisterConnection::sendGreetingMessage()
48 | {
49 | QByteArray greet = this->greetingMessage.toUtf8();
50 | QByteArray msg = "GREETING " + QByteArray::number(greet.size()) + ' ' + greet;
51 | if(this->write(msg) == msg.size())
52 | {
53 | if(DEBUG)
54 | qDebug() << "Send greeting message!";
55 | this->isGreetingMessageSent = 1;
56 |
57 | this->sendPeriodicRegisterMessage();
58 | this->periodicTimer.start();
59 | if(DEBUG)
60 | qDebug() << "Send register message!";
61 | }
62 | }
63 |
64 | bool RegisterConnection::sendPeriodicRegisterMessage()
65 | {
66 | QByteArray regist = this->registerMessage.toUtf8();
67 | QByteArray msg = "REGISTER " + QByteArray::number(regist.size()) + ' ' + regist;
68 | return this->write(msg) == msg.size();
69 | }
70 |
71 | int RegisterConnection::readDataIntoBuffer(int maxSize)
72 | {
73 | if(maxSize > MaxBufferSize)
74 | return 0;
75 |
76 | int numBytesBeforeRead = this->buffer.size();
77 | if(numBytesBeforeRead >= MaxBufferSize)
78 | {
79 | this->abort();
80 | return 0;
81 | }
82 |
83 | while(this->bytesAvailable() > 0 && buffer.size() <= maxSize)
84 | {
85 | this->buffer.append(this->read(1));
86 | if(buffer.endsWith(SeparateToken))
87 | break;
88 | }
89 |
90 | return buffer.size() - numBytesBeforeRead;
91 | }
92 |
93 | int RegisterConnection::dataLengthForCurrentDataType()
94 | {
95 | if(this->bytesAvailable() <=0 || this->readDataIntoBuffer() <= 0 || !this->buffer.endsWith(SeparateToken))
96 | return 0;
97 |
98 | this->buffer.chop(1);
99 | int length = this->buffer.toInt();
100 | this->buffer.clear();
101 |
102 | return length;
103 | }
104 |
105 | bool RegisterConnection::hasEnoughData()
106 | {
107 | if(this->transferTimerId != 0)
108 | {
109 | this->killTimer(this->transferTimerId);
110 | this->transferTimerId = 0;
111 | }
112 |
113 | if(this->numBytesForCurrentDataType <= 0)
114 | this->numBytesForCurrentDataType = this->dataLengthForCurrentDataType();
115 |
116 | if(bytesAvailable() < this->numBytesForCurrentDataType || this->numBytesForCurrentDataType <= 0)
117 | {
118 | this->transferTimerId = this->startTimer(TransferTimeout);
119 | return false;
120 | }
121 |
122 | return true;
123 | }
124 |
125 | void RegisterConnection::processReadyRead()
126 | {
127 | if(this->state == WaitingForGreeting)
128 | {
129 | if(!readProtocolHeader())
130 | return;
131 | if(this->currentDataType != GREETING)
132 | {
133 | this->abort();
134 | return;
135 | }
136 |
137 | this->state = ReadingGreeting;
138 | }
139 |
140 | if(this->state == ReadingGreeting)
141 | {
142 | if(!this->hasEnoughData())
143 | return;
144 |
145 | this->buffer = this->read(this->numBytesForCurrentDataType);
146 | if(this->buffer.size() != this->numBytesForCurrentDataType)
147 | {
148 | this->abort();
149 | return;
150 | }
151 |
152 | this->buffer.clear();
153 | this->numBytesForCurrentDataType = -1;
154 | this->currentDataType = UNDEFINED;
155 |
156 | if(!this->isValid())
157 | {
158 | this->abort();
159 | return;
160 | }
161 |
162 | if(!this->isGreetingMessageSent)
163 | this->sendGreetingMessage();
164 |
165 | this->state = ReadyForUse;
166 | }
167 |
168 | do
169 | {
170 | if(currentDataType == UNDEFINED)
171 | {
172 | if(!readProtocolHeader())
173 | return;
174 | }
175 |
176 | if(!this->hasEnoughData())
177 | return;
178 |
179 | this->processData();
180 | }while(this->bytesAvailable() > 0);
181 | }
182 |
183 | bool RegisterConnection::readProtocolHeader()
184 | {
185 | if(this->transferTimerId != 0)
186 | {
187 | this->killTimer(this->transferTimerId);
188 | this->transferTimerId = 0;
189 | }
190 |
191 | if(this->readDataIntoBuffer() <= 0)
192 | {
193 | this->transferTimerId = this->startTimer(TransferTimeout);
194 | return false;
195 | }
196 |
197 | if(this->buffer == "GREETING ")
198 | this->currentDataType = GREETING;
199 | else if (this->buffer == "REGISTER ")
200 | this->currentDataType = REGISTER;
201 | else if (this->buffer == "PEERLIST ")
202 | this->currentDataType = PEERLIST;
203 | else
204 | {
205 | this->currentDataType = UNDEFINED;
206 | this->abort();
207 | return false;
208 | }
209 |
210 | this->buffer.clear();
211 | this->numBytesForCurrentDataType = this->dataLengthForCurrentDataType();
212 | return true;
213 | }
214 |
215 | void RegisterConnection::processData()
216 | {
217 | this->buffer = this->read(this->numBytesForCurrentDataType);
218 | if(this->buffer.size() != this->numBytesForCurrentDataType)
219 | {
220 | this->abort();
221 | return;
222 | }
223 |
224 | switch(this->currentDataType)
225 | {
226 | case REGISTER:
227 | break;
228 | case PEERLIST:
229 | this->peerListString = QString::fromUtf8(this->buffer);
230 | emit this->newPeerList(this->peerListString);
231 | break;
232 | default:
233 | break;
234 | }
235 |
236 | this->currentDataType = UNDEFINED;
237 | this->numBytesForCurrentDataType = -1;
238 | this->buffer.clear();
239 | }
240 |
--------------------------------------------------------------------------------
/ChatClient/registerconnection.h:
--------------------------------------------------------------------------------
1 | /* 说明:
2 | * RegisterConnection用于与中心验证服务器通信,主要交换Register注册信息和PeerList活跃用户信息
3 | * 这里,我们也有几个设计说明:
4 | * (1) 我们仍然设置Greeting的过程用于初始的连接建立过程
5 | * (2) 我们设置周期定时器用于周期发送Register信息和获取最新的活跃用户信息
6 | *
7 | */
8 |
9 | #ifndef REGISTERCONNECTION_H
10 | #define REGISTERCONNECTION_H
11 |
12 | #include "header.h"
13 | #include
14 |
15 |
16 | class RegisterConnection : public QTcpSocket
17 | {
18 | Q_OBJECT
19 | public:
20 | explicit RegisterConnection(QObject *parent = 0);
21 |
22 | enum RegisterConnectionState
23 | {
24 | WaitingForGreeting,
25 | ReadingGreeting,
26 | ReadyForUse
27 | };
28 |
29 | enum DataType
30 | {
31 | GREETING,
32 | REGISTER,
33 | PEERLIST,
34 | UNDEFINED
35 | };
36 |
37 | void setLocalServerInfo(QString &name, QHostAddress &ip, int &port);
38 |
39 | signals:
40 | void newPeerList(QString &peerlist);
41 |
42 | protected:
43 | void timerEvent(QTimerEvent *);
44 |
45 | public slots:
46 | void processReadyRead();
47 | void sendGreetingMessage();
48 | bool sendPeriodicRegisterMessage();
49 |
50 | private:
51 | int readDataIntoBuffer(int maxSize = MaxBufferSize);
52 | int dataLengthForCurrentDataType();
53 | bool readProtocolHeader();
54 | bool hasEnoughData();
55 | void processData();
56 |
57 | QString localUserName;
58 | QHostAddress localServerIP;
59 | int localServerPort;
60 |
61 | QByteArray buffer;
62 | QTimer periodicTimer;
63 | QString peerListString;
64 | QString greetingMessage;
65 | QString registerMessage;
66 | enum RegisterConnectionState state;
67 | enum DataType currentDataType;
68 | int numBytesForCurrentDataType;
69 | int transferTimerId;
70 | bool isGreetingMessageSent;
71 | };
72 |
73 | #endif // REGISTERCONNECTION_H
74 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | Apache License
2 | Version 2.0, January 2004
3 | http://www.apache.org/licenses/
4 |
5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
6 |
7 | 1. Definitions.
8 |
9 | "License" shall mean the terms and conditions for use, reproduction,
10 | and distribution as defined by Sections 1 through 9 of this document.
11 |
12 | "Licensor" shall mean the copyright owner or entity authorized by
13 | the copyright owner that is granting the License.
14 |
15 | "Legal Entity" shall mean the union of the acting entity and all
16 | other entities that control, are controlled by, or are under common
17 | control with that entity. For the purposes of this definition,
18 | "control" means (i) the power, direct or indirect, to cause the
19 | direction or management of such entity, whether by contract or
20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the
21 | outstanding shares, or (iii) beneficial ownership of such entity.
22 |
23 | "You" (or "Your") shall mean an individual or Legal Entity
24 | exercising permissions granted by this License.
25 |
26 | "Source" form shall mean the preferred form for making modifications,
27 | including but not limited to software source code, documentation
28 | source, and configuration files.
29 |
30 | "Object" form shall mean any form resulting from mechanical
31 | transformation or translation of a Source form, including but
32 | not limited to compiled object code, generated documentation,
33 | and conversions to other media types.
34 |
35 | "Work" shall mean the work of authorship, whether in Source or
36 | Object form, made available under the License, as indicated by a
37 | copyright notice that is included in or attached to the work
38 | (an example is provided in the Appendix below).
39 |
40 | "Derivative Works" shall mean any work, whether in Source or Object
41 | form, that is based on (or derived from) the Work and for which the
42 | editorial revisions, annotations, elaborations, or other modifications
43 | represent, as a whole, an original work of authorship. For the purposes
44 | of this License, Derivative Works shall not include works that remain
45 | separable from, or merely link (or bind by name) to the interfaces of,
46 | the Work and Derivative Works thereof.
47 |
48 | "Contribution" shall mean any work of authorship, including
49 | the original version of the Work and any modifications or additions
50 | to that Work or Derivative Works thereof, that is intentionally
51 | submitted to Licensor for inclusion in the Work by the copyright owner
52 | or by an individual or Legal Entity authorized to submit on behalf of
53 | the copyright owner. For the purposes of this definition, "submitted"
54 | means any form of electronic, verbal, or written communication sent
55 | to the Licensor or its representatives, including but not limited to
56 | communication on electronic mailing lists, source code control systems,
57 | and issue tracking systems that are managed by, or on behalf of, the
58 | Licensor for the purpose of discussing and improving the Work, but
59 | excluding communication that is conspicuously marked or otherwise
60 | designated in writing by the copyright owner as "Not a Contribution."
61 |
62 | "Contributor" shall mean Licensor and any individual or Legal Entity
63 | on behalf of whom a Contribution has been received by Licensor and
64 | subsequently incorporated within the Work.
65 |
66 | 2. Grant of Copyright License. Subject to the terms and conditions of
67 | this License, each Contributor hereby grants to You a perpetual,
68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable
69 | copyright license to reproduce, prepare Derivative Works of,
70 | publicly display, publicly perform, sublicense, and distribute the
71 | Work and such Derivative Works in Source or Object form.
72 |
73 | 3. Grant of Patent License. Subject to the terms and conditions of
74 | this License, each Contributor hereby grants to You a perpetual,
75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable
76 | (except as stated in this section) patent license to make, have made,
77 | use, offer to sell, sell, import, and otherwise transfer the Work,
78 | where such license applies only to those patent claims licensable
79 | by such Contributor that are necessarily infringed by their
80 | Contribution(s) alone or by combination of their Contribution(s)
81 | with the Work to which such Contribution(s) was submitted. If You
82 | institute patent litigation against any entity (including a
83 | cross-claim or counterclaim in a lawsuit) alleging that the Work
84 | or a Contribution incorporated within the Work constitutes direct
85 | or contributory patent infringement, then any patent licenses
86 | granted to You under this License for that Work shall terminate
87 | as of the date such litigation is filed.
88 |
89 | 4. Redistribution. You may reproduce and distribute copies of the
90 | Work or Derivative Works thereof in any medium, with or without
91 | modifications, and in Source or Object form, provided that You
92 | meet the following conditions:
93 |
94 | (a) You must give any other recipients of the Work or
95 | Derivative Works a copy of this License; and
96 |
97 | (b) You must cause any modified files to carry prominent notices
98 | stating that You changed the files; and
99 |
100 | (c) You must retain, in the Source form of any Derivative Works
101 | that You distribute, all copyright, patent, trademark, and
102 | attribution notices from the Source form of the Work,
103 | excluding those notices that do not pertain to any part of
104 | the Derivative Works; and
105 |
106 | (d) If the Work includes a "NOTICE" text file as part of its
107 | distribution, then any Derivative Works that You distribute must
108 | include a readable copy of the attribution notices contained
109 | within such NOTICE file, excluding those notices that do not
110 | pertain to any part of the Derivative Works, in at least one
111 | of the following places: within a NOTICE text file distributed
112 | as part of the Derivative Works; within the Source form or
113 | documentation, if provided along with the Derivative Works; or,
114 | within a display generated by the Derivative Works, if and
115 | wherever such third-party notices normally appear. The contents
116 | of the NOTICE file are for informational purposes only and
117 | do not modify the License. You may add Your own attribution
118 | notices within Derivative Works that You distribute, alongside
119 | or as an addendum to the NOTICE text from the Work, provided
120 | that such additional attribution notices cannot be construed
121 | as modifying the License.
122 |
123 | You may add Your own copyright statement to Your modifications and
124 | may provide additional or different license terms and conditions
125 | for use, reproduction, or distribution of Your modifications, or
126 | for any such Derivative Works as a whole, provided Your use,
127 | reproduction, and distribution of the Work otherwise complies with
128 | the conditions stated in this License.
129 |
130 | 5. Submission of Contributions. Unless You explicitly state otherwise,
131 | any Contribution intentionally submitted for inclusion in the Work
132 | by You to the Licensor shall be under the terms and conditions of
133 | this License, without any additional terms or conditions.
134 | Notwithstanding the above, nothing herein shall supersede or modify
135 | the terms of any separate license agreement you may have executed
136 | with Licensor regarding such Contributions.
137 |
138 | 6. Trademarks. This License does not grant permission to use the trade
139 | names, trademarks, service marks, or product names of the Licensor,
140 | except as required for reasonable and customary use in describing the
141 | origin of the Work and reproducing the content of the NOTICE file.
142 |
143 | 7. Disclaimer of Warranty. Unless required by applicable law or
144 | agreed to in writing, Licensor provides the Work (and each
145 | Contributor provides its Contributions) on an "AS IS" BASIS,
146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
147 | implied, including, without limitation, any warranties or conditions
148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
149 | PARTICULAR PURPOSE. You are solely responsible for determining the
150 | appropriateness of using or redistributing the Work and assume any
151 | risks associated with Your exercise of permissions under this License.
152 |
153 | 8. Limitation of Liability. In no event and under no legal theory,
154 | whether in tort (including negligence), contract, or otherwise,
155 | unless required by applicable law (such as deliberate and grossly
156 | negligent acts) or agreed to in writing, shall any Contributor be
157 | liable to You for damages, including any direct, indirect, special,
158 | incidental, or consequential damages of any character arising as a
159 | result of this License or out of the use or inability to use the
160 | Work (including but not limited to damages for loss of goodwill,
161 | work stoppage, computer failure or malfunction, or any and all
162 | other commercial damages or losses), even if such Contributor
163 | has been advised of the possibility of such damages.
164 |
165 | 9. Accepting Warranty or Additional Liability. While redistributing
166 | the Work or Derivative Works thereof, You may choose to offer,
167 | and charge a fee for, acceptance of support, warranty, indemnity,
168 | or other liability obligations and/or rights consistent with this
169 | License. However, in accepting such obligations, You may act only
170 | on Your own behalf and on Your sole responsibility, not on behalf
171 | of any other Contributor, and only if You agree to indemnify,
172 | defend, and hold each Contributor harmless for any liability
173 | incurred by, or claims asserted against, such Contributor by reason
174 | of your accepting any such warranty or additional liability.
175 |
176 | END OF TERMS AND CONDITIONS
177 |
178 | APPENDIX: How to apply the Apache License to your work.
179 |
180 | To apply the Apache License to your work, attach the following
181 | boilerplate notice, with the fields enclosed by brackets "[]"
182 | replaced with your own identifying information. (Don't include
183 | the brackets!) The text should be enclosed in the appropriate
184 | comment syntax for the file format. We also recommend that a
185 | file or class name and description of purpose be included on the
186 | same "printed page" as the copyright notice for easier
187 | identification within third-party archives.
188 |
189 | Copyright [yyyy] [name of copyright owner]
190 |
191 | Licensed under the Apache License, Version 2.0 (the "License");
192 | you may not use this file except in compliance with the License.
193 | You may obtain a copy of the License at
194 |
195 | http://www.apache.org/licenses/LICENSE-2.0
196 |
197 | Unless required by applicable law or agreed to in writing, software
198 | distributed under the License is distributed on an "AS IS" BASIS,
199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
200 | See the License for the specific language governing permissions and
201 | limitations under the License.
202 |
--------------------------------------------------------------------------------
/Material/P2P聊天软件设计文档.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/P2P聊天软件设计文档.pdf
--------------------------------------------------------------------------------
/Material/chat_dialog.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/chat_dialog.jpg
--------------------------------------------------------------------------------
/Material/chat_dialog2.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/chat_dialog2.jpg
--------------------------------------------------------------------------------
/Material/client_gui.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/client_gui.jpg
--------------------------------------------------------------------------------
/Material/client_gui2.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/client_gui2.jpg
--------------------------------------------------------------------------------
/Material/register_gui.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/register_gui.jpg
--------------------------------------------------------------------------------
/Material/register_server_gui.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/Material/register_server_gui.jpg
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | P2P聊天软件设计
2 | ========================================================================================
3 |
4 | ## 功能要求
5 | * 用户界面(GUI)可自行设计,主要为用户提供方便。
6 | * 用户界面要及时的对用户的操作做出反应。
7 | * 要实现一个用户可以和多个用户同时进行聊天。
8 |
9 | ## 设计目标及流程
10 | 设计一个P2P聊天软件,由多个聊天客户端和一个中心服务器组成。各个聊天客户端可以两两相互发送消息。目的在于设计GUI、多线程和套接字编程。各个客户端用IP地址和TCP/IP监听端口号进行标识。每个客户提供一个名字,方便其它客户端。
11 |
12 | 此设计由两部分组成。
13 |
14 | ### 第一部分:注册
15 | P2P聊天中各个成员管理。每个成员称为一个peer,要有一个中心的服务处理peer的登记和对已经登记的peer进行更新。
16 | * 步骤1:一个peer选择一个名字,通过登记界面进行登记。
17 | * 步骤2:服务器拥有一个公有IP,在一个众所周知的端口进行监听。Peer向服务器发送‘register’请求,同时发送自己的登记信息(如己取的名字,自己的监听端口号等)。服务器收到‘register’请求后,如果这是每一个登记请求,服务器建立一个用于记录已经登记peer的列表(Peer List),否则更新Peer List。
18 | * 步骤3:服务器向来登记的peer发送Peer List。PeerList 由一些活跃的peer组成,一个活跃的peer是在最近30秒内进行登记的peer。
19 | * 步骤4:peer收到 Peer List后,以适当的形式显示出来。设计一个显示Peer List的GUI。
20 | * 步骤5:每个已经登记的peer每隔15秒向服务器登记,来使自己保持活跃,同时得到最近新登记的peer信息。如果需要,就在自己的PeerList GUI进行更新。
21 |
22 | ### 第二部分:交互
23 | 多个peer间相互发送消息。
24 | * 步骤1:在的客户端P1的用户U1(U1@P1)在自己Peer List GUI中选择一个peer,假设为U2@P2。
25 | * 步骤2:P1建立一个到P2的连接。
26 | * 步骤3:U1在自己的发送信息界面(Messaging GUI)编写信息,然后点击发送按钮,P1将信息通过步骤2中建立的连接发送到P2。
27 | * 步骤4:如果第3个用户U3@P3发送一条消息到U1@P1,如果U1此时正好有一个Messaging GUI与U3进行交互,那么就显示消息,如果没有,就要提示U1有新消息到来。两个User之间可以相互发送消息,每对User之间有一个单独的Messaging GUI。
28 |
29 | ## 软件组成
30 | 本软件由ChatClient和RegisterServer两部分组成,其中ChatClient为客户端,可执行注册和聊天过程,而RegisterServer为注册服务器,主要用于注册客户端和分发注册客户端信息。
31 |
32 | ## 版本更新日志
33 | v0.1
34 | + 构建出基础的软件结构,并未实现多线程(多进程)编程<使用了Qt的异步封装>
35 | + 通信机制还应该有所改善,不应该直接弹出聊天框,可以实现如QQ的消息提醒方式
36 | + 界面亟需改善
37 |
38 | ## 软件运行界面
39 | * 客户端注册界面
40 |
41 | 
42 |
43 | * 客户端界面
44 |
45 | 
46 |
47 | 
48 |
49 | * 注册服务器界面
50 |
51 | 
52 |
53 | * 客户端通信聊天界面
54 |
55 | 
56 |
57 | 备注:由于个人不会界面设计,因此界面十分粗糙。同时由于功能的相对不完善,因此,对于整个软件的架构设计还有一些方面的不完善,后面估计会考虑去重构该软件。
58 |
--------------------------------------------------------------------------------
/RegisterServer/Makefile:
--------------------------------------------------------------------------------
1 | #############################################################################
2 | # Makefile for building: RegisterServer
3 | # Generated by qmake (3.0) (Qt 5.6.0)
4 | # Project: RegisterServer.pro
5 | # Template: app
6 | # Command: C:\Qt\Qt5.6.0\5.6\mingw49_32\bin\qmake.exe -spec win32-g++ "CONFIG+=debug" "CONFIG+=qml_debug" -o Makefile RegisterServer.pro
7 | #############################################################################
8 |
9 | MAKEFILE = Makefile
10 |
11 | first: debug
12 | install: debug-install
13 | uninstall: debug-uninstall
14 | QMAKE = C:\Qt\Qt5.6.0\5.6\mingw49_32\bin\qmake.exe
15 | DEL_FILE = del
16 | CHK_DIR_EXISTS= if not exist
17 | MKDIR = mkdir
18 | COPY = copy /y
19 | COPY_FILE = copy /y
20 | COPY_DIR = xcopy /s /q /y /i
21 | INSTALL_FILE = copy /y
22 | INSTALL_PROGRAM = copy /y
23 | INSTALL_DIR = xcopy /s /q /y /i
24 | DEL_FILE = del
25 | SYMLINK = $(QMAKE) -install ln -f -s
26 | DEL_DIR = rmdir
27 | MOVE = move
28 | SUBTARGETS = \
29 | debug \
30 | release
31 |
32 |
33 | debug: FORCE
34 | $(MAKE) -f $(MAKEFILE).Debug
35 | debug-make_first: FORCE
36 | $(MAKE) -f $(MAKEFILE).Debug
37 | debug-all: FORCE
38 | $(MAKE) -f $(MAKEFILE).Debug all
39 | debug-clean: FORCE
40 | $(MAKE) -f $(MAKEFILE).Debug clean
41 | debug-distclean: FORCE
42 | $(MAKE) -f $(MAKEFILE).Debug distclean
43 | debug-install: FORCE
44 | $(MAKE) -f $(MAKEFILE).Debug install
45 | debug-uninstall: FORCE
46 | $(MAKE) -f $(MAKEFILE).Debug uninstall
47 | release: FORCE
48 | $(MAKE) -f $(MAKEFILE).Release
49 | release-make_first: FORCE
50 | $(MAKE) -f $(MAKEFILE).Release
51 | release-all: FORCE
52 | $(MAKE) -f $(MAKEFILE).Release all
53 | release-clean: FORCE
54 | $(MAKE) -f $(MAKEFILE).Release clean
55 | release-distclean: FORCE
56 | $(MAKE) -f $(MAKEFILE).Release distclean
57 | release-install: FORCE
58 | $(MAKE) -f $(MAKEFILE).Release install
59 | release-uninstall: FORCE
60 | $(MAKE) -f $(MAKEFILE).Release uninstall
61 |
62 | Makefile: RegisterServer.pro ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/win32-g++/qmake.conf ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_pre.prf \
63 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qdevice.pri \
64 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/device_config.prf \
65 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/common/angle.conf \
66 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qconfig.pri \
67 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore.pri \
68 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore_private.pri \
69 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput.pri \
70 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput_private.pri \
71 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic.pri \
72 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic_private.pri \
73 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick.pri \
74 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick_private.pri \
75 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput.pri \
76 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput_private.pri \
77 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender.pri \
78 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender_private.pri \
79 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender.pri \
80 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender_private.pri \
81 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase.pri \
82 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase_private.pri \
83 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer.pri \
84 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer_private.pri \
85 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver.pri \
86 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver_private.pri \
87 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth.pri \
88 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth_private.pri \
89 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bootstrap_private.pri \
90 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_clucene_private.pri \
91 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent.pri \
92 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent_private.pri \
93 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core.pri \
94 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core_private.pri \
95 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus.pri \
96 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus_private.pri \
97 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer.pri \
98 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer_private.pri \
99 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designercomponents_private.pri \
100 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui.pri \
101 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui_private.pri \
102 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help.pri \
103 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help_private.pri \
104 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labscontrols_private.pri \
105 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labstemplates_private.pri \
106 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location.pri \
107 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location_private.pri \
108 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia.pri \
109 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia_private.pri \
110 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets.pri \
111 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets_private.pri \
112 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network.pri \
113 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network_private.pri \
114 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc.pri \
115 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc_private.pri \
116 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl.pri \
117 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl_private.pri \
118 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions.pri \
119 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions_private.pri \
120 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_platformsupport_private.pri \
121 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning.pri \
122 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning_private.pri \
123 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport.pri \
124 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport_private.pri \
125 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml.pri \
126 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml_private.pri \
127 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmldevtools_private.pri \
128 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest.pri \
129 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest_private.pri \
130 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qtmultimediaquicktools_private.pri \
131 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick.pri \
132 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick_private.pri \
133 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickparticles_private.pri \
134 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets.pri \
135 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets_private.pri \
136 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script.pri \
137 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script_private.pri \
138 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools.pri \
139 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools_private.pri \
140 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors.pri \
141 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors_private.pri \
142 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus.pri \
143 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus_private.pri \
144 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport.pri \
145 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport_private.pri \
146 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql.pri \
147 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql_private.pri \
148 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg.pri \
149 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg_private.pri \
150 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib.pri \
151 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib_private.pri \
152 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uiplugin.pri \
153 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools.pri \
154 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools_private.pri \
155 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel.pri \
156 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel_private.pri \
157 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets.pri \
158 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets_private.pri \
159 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets.pri \
160 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets_private.pri \
161 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras.pri \
162 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras_private.pri \
163 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml.pri \
164 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml_private.pri \
165 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns.pri \
166 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns_private.pri \
167 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_functions.prf \
168 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_config.prf \
169 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/qt_config.prf \
170 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/win32-g++/qmake.conf \
171 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_post.prf \
172 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds.prf \
173 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_pre.prf \
174 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/default_pre.prf \
175 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resolve_config.prf \
176 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds_post.prf \
177 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_post.prf \
178 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qml_debug.prf \
179 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/rtti.prf \
180 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/precompile_header.prf \
181 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/warn_on.prf \
182 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt.prf \
183 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resources.prf \
184 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/moc.prf \
185 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/opengl.prf \
186 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/uic.prf \
187 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/windows.prf \
188 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/testcase_targets.prf \
189 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exceptions.prf \
190 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/yacc.prf \
191 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/lex.prf \
192 | RegisterServer.pro \
193 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/qtmaind.prl \
194 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Widgets.prl \
195 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Gui.prl \
196 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Network.prl \
197 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Core.prl
198 | $(QMAKE) -spec win32-g++ "CONFIG+=debug" "CONFIG+=qml_debug" -o Makefile RegisterServer.pro
199 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_pre.prf:
200 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qdevice.pri:
201 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/device_config.prf:
202 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/common/angle.conf:
203 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/qconfig.pri:
204 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore.pri:
205 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dcore_private.pri:
206 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput.pri:
207 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dinput_private.pri:
208 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic.pri:
209 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dlogic_private.pri:
210 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick.pri:
211 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquick_private.pri:
212 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput.pri:
213 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickinput_private.pri:
214 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender.pri:
215 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3dquickrender_private.pri:
216 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender.pri:
217 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_3drender_private.pri:
218 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase.pri:
219 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axbase_private.pri:
220 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer.pri:
221 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axcontainer_private.pri:
222 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver.pri:
223 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_axserver_private.pri:
224 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth.pri:
225 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bluetooth_private.pri:
226 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_bootstrap_private.pri:
227 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_clucene_private.pri:
228 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent.pri:
229 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_concurrent_private.pri:
230 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core.pri:
231 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_core_private.pri:
232 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus.pri:
233 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_dbus_private.pri:
234 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer.pri:
235 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designer_private.pri:
236 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_designercomponents_private.pri:
237 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui.pri:
238 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_gui_private.pri:
239 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help.pri:
240 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_help_private.pri:
241 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labscontrols_private.pri:
242 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_labstemplates_private.pri:
243 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location.pri:
244 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_location_private.pri:
245 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia.pri:
246 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimedia_private.pri:
247 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets.pri:
248 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_multimediawidgets_private.pri:
249 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network.pri:
250 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_network_private.pri:
251 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc.pri:
252 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_nfc_private.pri:
253 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl.pri:
254 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_opengl_private.pri:
255 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions.pri:
256 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_openglextensions_private.pri:
257 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_platformsupport_private.pri:
258 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning.pri:
259 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_positioning_private.pri:
260 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport.pri:
261 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_printsupport_private.pri:
262 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml.pri:
263 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qml_private.pri:
264 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmldevtools_private.pri:
265 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest.pri:
266 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qmltest_private.pri:
267 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_qtmultimediaquicktools_private.pri:
268 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick.pri:
269 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quick_private.pri:
270 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickparticles_private.pri:
271 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets.pri:
272 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_quickwidgets_private.pri:
273 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script.pri:
274 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_script_private.pri:
275 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools.pri:
276 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_scripttools_private.pri:
277 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors.pri:
278 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sensors_private.pri:
279 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus.pri:
280 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialbus_private.pri:
281 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport.pri:
282 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_serialport_private.pri:
283 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql.pri:
284 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_sql_private.pri:
285 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg.pri:
286 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_svg_private.pri:
287 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib.pri:
288 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_testlib_private.pri:
289 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uiplugin.pri:
290 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools.pri:
291 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_uitools_private.pri:
292 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel.pri:
293 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_webchannel_private.pri:
294 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets.pri:
295 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_websockets_private.pri:
296 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets.pri:
297 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_widgets_private.pri:
298 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras.pri:
299 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_winextras_private.pri:
300 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml.pri:
301 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xml_private.pri:
302 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns.pri:
303 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/modules/qt_lib_xmlpatterns_private.pri:
304 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_functions.prf:
305 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt_config.prf:
306 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/qt_config.prf:
307 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/win32-g++/qmake.conf:
308 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/spec_post.prf:
309 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds.prf:
310 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_pre.prf:
311 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/default_pre.prf:
312 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resolve_config.prf:
313 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exclusive_builds_post.prf:
314 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/default_post.prf:
315 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qml_debug.prf:
316 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/rtti.prf:
317 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/precompile_header.prf:
318 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/warn_on.prf:
319 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/qt.prf:
320 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/resources.prf:
321 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/moc.prf:
322 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/opengl.prf:
323 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/uic.prf:
324 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/win32/windows.prf:
325 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/testcase_targets.prf:
326 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/exceptions.prf:
327 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/yacc.prf:
328 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/mkspecs/features/lex.prf:
329 | RegisterServer.pro:
330 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/qtmaind.prl:
331 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Widgets.prl:
332 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Gui.prl:
333 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Network.prl:
334 | ../../../../Qt/Qt5.6.0/5.6/mingw49_32/lib/Qt5Core.prl:
335 | qmake: FORCE
336 | @$(QMAKE) -spec win32-g++ "CONFIG+=debug" "CONFIG+=qml_debug" -o Makefile RegisterServer.pro
337 |
338 | qmake_all: FORCE
339 |
340 | make_first: debug-make_first release-make_first FORCE
341 | all: debug-all release-all FORCE
342 | clean: debug-clean release-clean FORCE
343 | distclean: debug-distclean release-distclean FORCE
344 | -$(DEL_FILE) Makefile
345 |
346 | debug-mocclean:
347 | $(MAKE) -f $(MAKEFILE).Debug mocclean
348 | release-mocclean:
349 | $(MAKE) -f $(MAKEFILE).Release mocclean
350 | mocclean: debug-mocclean release-mocclean
351 |
352 | debug-mocables:
353 | $(MAKE) -f $(MAKEFILE).Debug mocables
354 | release-mocables:
355 | $(MAKE) -f $(MAKEFILE).Release mocables
356 | mocables: debug-mocables release-mocables
357 |
358 | check: first
359 | FORCE:
360 |
361 | $(MAKEFILE).Debug: Makefile
362 | $(MAKEFILE).Release: Makefile
363 |
--------------------------------------------------------------------------------
/RegisterServer/RegisterServer.pro:
--------------------------------------------------------------------------------
1 | #-------------------------------------------------
2 | #
3 | # Project created by QtCreator 2015-10-10T10:36:22
4 | #
5 | #-------------------------------------------------
6 |
7 | QT += core gui network
8 |
9 | greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
10 |
11 | TARGET = RegisterServer
12 | TEMPLATE = app
13 |
14 |
15 | SOURCES += main.cpp\
16 | window.cpp \
17 | registerconnection.cpp \
18 | registerserver.cpp \
19 | peerinfo.cpp
20 |
21 | HEADERS += window.h \
22 | registerconnection.h \
23 | header.h \
24 | registerserver.h \
25 | peerinfo.h
26 |
27 | RC_FILE += images/icon.rc
28 |
29 | OTHER_FILES += \
30 | images/icon.rc \
31 | images/server.ico
32 |
33 |
34 |
--------------------------------------------------------------------------------
/RegisterServer/RegisterServer.pro.user:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | EnvironmentId
7 | {1f2d4bf0-dd7c-4612-97c0-0e08f39cb8c2}
8 |
9 |
10 | ProjectExplorer.Project.ActiveTarget
11 | 0
12 |
13 |
14 | ProjectExplorer.Project.EditorSettings
15 |
16 | true
17 | false
18 | true
19 |
20 | Cpp
21 |
22 | CppGlobal
23 |
24 |
25 |
26 | QmlJS
27 |
28 | QmlJSGlobal
29 |
30 |
31 | 2
32 | UTF-8
33 | false
34 | 4
35 | false
36 | 80
37 | true
38 | true
39 | 1
40 | true
41 | false
42 | 0
43 | true
44 | 0
45 | 8
46 | true
47 | 1
48 | true
49 | true
50 | true
51 | false
52 |
53 |
54 |
55 | ProjectExplorer.Project.PluginSettings
56 |
57 |
58 |
59 | ProjectExplorer.Project.Target.0
60 |
61 | Desktop Qt 5.6.0 MinGW 32bit
62 | Desktop Qt 5.6.0 MinGW 32bit
63 | qt.56.win32_mingw49_kit
64 | 0
65 | 0
66 | 0
67 |
68 | C:/Users/Adoryn/P2PChatRoom/RegisterServer
69 |
70 |
71 | true
72 | qmake
73 |
74 | QtProjectManager.QMakeBuildStep
75 | true
76 |
77 | false
78 | false
79 | false
80 |
81 |
82 | true
83 | Make
84 |
85 | Qt4ProjectManager.MakeStep
86 |
87 | false
88 |
89 |
90 |
91 | 2
92 | 构建
93 |
94 | ProjectExplorer.BuildSteps.Build
95 |
96 |
97 |
98 | true
99 | Make
100 |
101 | Qt4ProjectManager.MakeStep
102 |
103 | true
104 | clean
105 |
106 |
107 | 1
108 | 清理
109 |
110 | ProjectExplorer.BuildSteps.Clean
111 |
112 | 2
113 | false
114 |
115 | Debug
116 |
117 | Qt4ProjectManager.Qt4BuildConfiguration
118 | 2
119 | true
120 |
121 |
122 | C:/Users/Adoryn/P2PChatRoom/build-RegisterServer-Desktop_Qt_5_6_0_MinGW_32bit-Release
123 |
124 |
125 | true
126 | qmake
127 |
128 | QtProjectManager.QMakeBuildStep
129 | false
130 |
131 | false
132 | false
133 | false
134 |
135 |
136 | true
137 | Make
138 |
139 | Qt4ProjectManager.MakeStep
140 |
141 | false
142 |
143 |
144 |
145 | 2
146 | 构建
147 |
148 | ProjectExplorer.BuildSteps.Build
149 |
150 |
151 |
152 | true
153 | Make
154 |
155 | Qt4ProjectManager.MakeStep
156 |
157 | true
158 | clean
159 |
160 |
161 | 1
162 | 清理
163 |
164 | ProjectExplorer.BuildSteps.Clean
165 |
166 | 2
167 | false
168 |
169 | Release
170 |
171 | Qt4ProjectManager.Qt4BuildConfiguration
172 | 0
173 | true
174 |
175 |
176 | C:/Users/Adoryn/P2PChatRoom/build-RegisterServer-Desktop_Qt_5_6_0_MinGW_32bit-Profile
177 |
178 |
179 | true
180 | qmake
181 |
182 | QtProjectManager.QMakeBuildStep
183 | true
184 |
185 | false
186 | true
187 | false
188 |
189 |
190 | true
191 | Make
192 |
193 | Qt4ProjectManager.MakeStep
194 |
195 | false
196 |
197 |
198 |
199 | 2
200 | 构建
201 |
202 | ProjectExplorer.BuildSteps.Build
203 |
204 |
205 |
206 | true
207 | Make
208 |
209 | Qt4ProjectManager.MakeStep
210 |
211 | true
212 | clean
213 |
214 |
215 | 1
216 | 清理
217 |
218 | ProjectExplorer.BuildSteps.Clean
219 |
220 | 2
221 | false
222 |
223 | Profile
224 |
225 | Qt4ProjectManager.Qt4BuildConfiguration
226 | 0
227 | true
228 |
229 | 3
230 |
231 |
232 | 0
233 | 部署
234 |
235 | ProjectExplorer.BuildSteps.Deploy
236 |
237 | 1
238 | 在本地部署
239 |
240 | ProjectExplorer.DefaultDeployConfiguration
241 |
242 | 1
243 |
244 |
245 | false
246 | 1000
247 |
248 | true
249 |
250 | false
251 | false
252 | false
253 | false
254 | true
255 | 0.01
256 | 10
257 | true
258 | 1
259 | 25
260 |
261 | 1
262 | true
263 | false
264 | true
265 | valgrind
266 |
267 | 0
268 | 1
269 | 2
270 | 3
271 | 4
272 | 5
273 | 6
274 | 7
275 | 8
276 | 9
277 | 10
278 | 11
279 | 12
280 | 13
281 | 14
282 |
283 | 2
284 |
285 | RegisterServer
286 |
287 | Qt4ProjectManager.Qt4RunConfiguration:C:/Users/Adoryn/P2PChatRoom/RegisterServer/RegisterServer.pro
288 | true
289 |
290 | RegisterServer.pro
291 | false
292 | false
293 |
294 | 3768
295 | false
296 | true
297 | false
298 | false
299 | true
300 |
301 | 1
302 |
303 |
304 |
305 | ProjectExplorer.Project.TargetCount
306 | 1
307 |
308 |
309 | ProjectExplorer.Project.Updater.FileVersion
310 | 18
311 |
312 |
313 | Version
314 | 18
315 |
316 |
317 |
--------------------------------------------------------------------------------
/RegisterServer/debug.log:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/RegisterServer/debug.log
--------------------------------------------------------------------------------
/RegisterServer/header.h:
--------------------------------------------------------------------------------
1 | #ifndef HEADER_H
2 | #define HEADER_H
3 |
4 | // General Methods
5 | #include
6 | #include
7 | #include
8 | #include
9 | #include
10 | #include
11 | #include
12 | #include
13 | #include
14 | #include
15 | #include
16 | #include
17 | #include
18 | #include
19 |
20 | // Widgets
21 | #include
22 | #include
23 | #include
24 | #include
25 | #include
26 | #include
27 | #include
28 | #include
29 | #include
30 | #include
31 | #include
32 | #include
33 | #include
34 | #include
35 | #include
36 | #include
37 |
38 | // Notification Methods
39 | #include
40 |
41 | // Qt Network
42 | #include
43 | #include
44 | #include
45 | #include
46 | #include
47 | #include
48 |
49 | // Related to Json File operations
50 | #include
51 | #include
52 | #include
53 | #include
54 |
55 | #define MaxBufferSize 1024000
56 | #define DEBUG 1
57 |
58 | #endif // HEADER_H
59 |
--------------------------------------------------------------------------------
/RegisterServer/images/icon.rc:
--------------------------------------------------------------------------------
1 | IDI_ICON1 ICON DISCARDABLE "server.ico"
--------------------------------------------------------------------------------
/RegisterServer/images/server.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/adomy/P2PChatRoom/7871062b5125fdda109ed8506e692e749c60e878/RegisterServer/images/server.ico
--------------------------------------------------------------------------------
/RegisterServer/main.cpp:
--------------------------------------------------------------------------------
1 | #include "window.h"
2 | #include "header.h"
3 | #include
4 |
5 | void outputMessage(QtMsgType type, const QMessageLogContext &context, const QString &msg);
6 | void clearLogFile();
7 |
8 | int main(int argc, char *argv[])
9 | {
10 | clearLogFile();
11 | qInstallMessageHandler(outputMessage);
12 | QApplication a(argc, argv);
13 | Window w;
14 | w.show();
15 |
16 | return a.exec();
17 | }
18 |
19 | void clearLogFile()
20 | {
21 | QFile file("registerLog.txt");
22 | file.open(QIODevice::WriteOnly | QIODevice::Append);
23 | file.resize(0);
24 | file.flush();
25 | file.close();
26 | }
27 |
28 | void outputMessage(QtMsgType type, const QMessageLogContext &context, const QString &msg)
29 | {
30 | static QMutex mutex;
31 |
32 | QString text;
33 | switch(type)
34 | {
35 | case QtDebugMsg:
36 | text = QString("Debug:");
37 | break;
38 |
39 | case QtWarningMsg:
40 | text = QString("Warning:");
41 | break;
42 |
43 | case QtCriticalMsg:
44 | text = QString("Critical:");
45 | break;
46 |
47 | case QtFatalMsg:
48 | text = QString("Fatal:");
49 | break;
50 |
51 | default:
52 | break;
53 | }
54 |
55 | QString context_info = QString("(%1:%2)").arg(QString(context.file)).arg(context.line);
56 | QString message = QString("%1 %2 %3").arg(text).arg(context_info).arg(msg);
57 |
58 | mutex.lock();
59 |
60 | QFile file("registerLog.txt");
61 | file.open(QIODevice::WriteOnly | QIODevice::Append);
62 | QTextStream text_stream(&file);
63 | text_stream << message << "\r\n";
64 | file.flush();
65 | file.close();
66 |
67 | mutex.unlock();
68 | }
69 |
--------------------------------------------------------------------------------
/RegisterServer/peerinfo.cpp:
--------------------------------------------------------------------------------
1 | #include "peerinfo.h"
2 |
3 | static const int TimeOut = 22 * 1000;
4 |
5 | PeerInfo::PeerInfo(QObject *parent, QString peername, QHostAddress ip, int port) :
6 | QObject(parent)
7 | {
8 | this->setPeerInfo(peername, ip, port);
9 | this->state = true;
10 | this->activeTimer = new QTimer();
11 | this->activeTimer->setInterval(TimeOut);
12 | this->activeTimer->start();
13 |
14 | if(DEBUG)
15 | qDebug() << "PeerInfo active timer started.";
16 | connect(activeTimer, SIGNAL(timeout()), this, SLOT(handleTimeOut()));
17 | }
18 |
19 | PeerInfo::~PeerInfo()
20 | {
21 | }
22 |
23 | QString PeerInfo::getPeerName()
24 | {
25 | return this->peerName;
26 | }
27 |
28 | QString PeerInfo::getPeerIP()
29 | {
30 | return this->peerIP.toString();
31 | }
32 |
33 | int PeerInfo::getPeerPort()
34 | {
35 | return this->peerPort;
36 | }
37 |
38 | void PeerInfo::setPeerInfo(QString peername, QHostAddress ip, int port)
39 | {
40 | this->peerName = peername;
41 | this->peerIP = ip;
42 | this->peerPort = port;
43 | }
44 |
45 | void PeerInfo::handleTimeOut()
46 | {
47 | this->state = false;
48 | this->activeTimer->stop();
49 | emit this->peerExpire(this);
50 | }
51 |
52 | void PeerInfo::refresh()
53 | {
54 | if(this->state == false)
55 | this->state = true;
56 |
57 | this->activeTimer->setInterval(TimeOut);
58 | this->activeTimer->start();
59 | }
60 |
61 | void PeerInfo::clear()
62 | {
63 | this->state = true;
64 | this->activeTimer->stop();
65 | }
66 |
67 |
68 |
--------------------------------------------------------------------------------
/RegisterServer/peerinfo.h:
--------------------------------------------------------------------------------
1 | #ifndef PEERINFO_H
2 | #define PEERINFO_H
3 |
4 | #include "header.h"
5 | #include
6 |
7 | class PeerInfo : public QObject
8 | {
9 | Q_OBJECT
10 | public:
11 | explicit PeerInfo(QObject *parent = 0, QString peername = "unknown", QHostAddress ip = QHostAddress("127.0.0.1"), int port = 0);
12 | ~PeerInfo();
13 |
14 | QString getPeerName();
15 | QString getPeerIP();
16 | int getPeerPort();
17 | void setPeerInfo(QString, QHostAddress, int);
18 | void refresh();
19 | void clear();
20 |
21 | signals:
22 | void peerExpire(PeerInfo *);
23 |
24 | public slots:
25 | void handleTimeOut();
26 |
27 | private:
28 | QString peerName;
29 | QHostAddress peerIP;
30 | int peerPort;
31 | bool state;
32 |
33 | QTimer *activeTimer;
34 | };
35 |
36 | #endif // PEERINFO_H
37 |
--------------------------------------------------------------------------------
/RegisterServer/registerLog.txt:
--------------------------------------------------------------------------------
1 | Debug: (window.cpp:113) Register server ip address: "192.168.1.174"
2 | Debug: (window.cpp:114) Register server port: 10001
3 | Debug: (window.cpp:128) Register server started.
4 | Debug: (window.cpp:170) Handle new connection.
5 | Debug: (window.cpp:379) Add new connection into registerConns.
6 | Debug: (registerconnection.cpp:156) Get greeting message: "unknown:192.168.1.174:9001"
7 | Debug: (registerconnection.cpp:166) Received greeting message: "unknown:192.168.1.174:9001"
8 | Debug: (window.cpp:184) Enter handle_new_register_msg function:
9 | Debug: (window.cpp:185) New register message: "unknown@192.168.1.174:9001"
10 | Debug: (window.cpp:199) Register message information:
11 | Debug: (window.cpp:200) Hostname: "unknown"
12 | Debug: (window.cpp:201) IP address: "192.168.1.174"
13 | Debug: (window.cpp:202) Port: "9001"
14 | Debug: (peerinfo.cpp:15) PeerInfo active timer started.
15 | Debug: (window.cpp:400) Add new PeerInfo into peerList: "unknown"
16 | Debug: (window.cpp:359) Broadcast peerList changed message
17 | Debug: (window.cpp:340) Generate PeerList String.
18 | Debug: (window.cpp:369) Broadcast message sent.
19 | Debug: (window.cpp:228) Handle new register msg done.
20 | Debug: (window.cpp:252) Register connection network error.
21 | Debug: (window.cpp:279) Register connection error: "Remote host closed."
22 | Debug: (window.cpp:410) Remove PeerInfo from peerList "unknown"
23 | Debug: (window.cpp:390) Remove connection from registerConns.
24 | Debug: (window.cpp:359) Broadcast peerList changed message
25 | Debug: (window.cpp:340) Generate PeerList String.
26 | Debug: (window.cpp:369) Broadcast message sent.
27 | Debug: (window.cpp:291) Handle network error done.
28 | Debug: (window.cpp:147) Register server stopped!
29 |
--------------------------------------------------------------------------------
/RegisterServer/registerconnection.cpp:
--------------------------------------------------------------------------------
1 | #include "registerconnection.h"
2 |
3 | static const int TransferTimeout = 40 * 1000;
4 | static const char SeparateToken = ' ';
5 |
6 | RegisterConnection::RegisterConnection(QObject *parent) :
7 | QTcpSocket(parent)
8 | {
9 | this->greetingMessage = QString("Register Validation");
10 | this->registerMessage = QString("");
11 | this->state = WaitingForGreeting;
12 | this->currentDataType = UNDEFINED;
13 | this->isGreetingMessageSent = false;
14 | this->numBytesForCurrentDataType = -1;
15 | this->transferTimerId = 0;
16 |
17 | connect(this, SIGNAL(readyRead()), this, SLOT(processReadyRead()));
18 | connect(this, SIGNAL(connected()), this, SLOT(sendGreetingMessage()));
19 | connect(this, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(handleSocketError(QAbstractSocket::SocketError)));
20 | }
21 |
22 | RegisterConnection::~RegisterConnection()
23 | {
24 |
25 | }
26 |
27 | QString RegisterConnection::getPeerServerName()
28 | {
29 | return this->name;
30 | }
31 |
32 | QHostAddress RegisterConnection::getPeerServerIP()
33 | {
34 | return this->ip;
35 | }
36 |
37 | int RegisterConnection::getPeerServerPort()
38 | {
39 | return this->port;
40 | }
41 |
42 | void RegisterConnection::handleSocketError(QAbstractSocket::SocketError error)
43 | {
44 | emit this->registerError(this, error);
45 | }
46 |
47 | void RegisterConnection::timerEvent(QTimerEvent *timerEvent)
48 | {
49 | if(timerEvent->timerId() == this->transferTimerId)
50 | {
51 | this->abort();
52 | this->killTimer(transferTimerId);
53 | transferTimerId = 0;
54 | }
55 | }
56 |
57 | void RegisterConnection::sendGreetingMessage()
58 | {
59 | QByteArray greet = this->greetingMessage.toUtf8();
60 | QByteArray msg = "GREETING " + QByteArray::number(greet.size()) + ' ' + greet;
61 | if(this->write(msg) == msg.size())
62 | this->isGreetingMessageSent = 1;
63 | }
64 |
65 | bool RegisterConnection::sendPeriodicPeerlistMessage(QString message)
66 | {
67 | QByteArray peerStr = message.toUtf8();
68 | QByteArray msg = "PEERLIST " + QByteArray::number(peerStr.size()) + ' ' + peerStr;
69 | return this->write(msg) == msg.size();
70 | }
71 |
72 | int RegisterConnection::readDataIntoBuffer(int maxSize)
73 | {
74 | if(maxSize > MaxBufferSize)
75 | return 0;
76 |
77 | int numBytesBeforeRead = this->buffer.size();
78 | if(numBytesBeforeRead >= MaxBufferSize)
79 | {
80 | this->abort();
81 | return 0;
82 | }
83 |
84 | while(this->bytesAvailable() > 0 && buffer.size() <= maxSize)
85 | {
86 | this->buffer.append(this->read(1));
87 | if(buffer.endsWith(SeparateToken))
88 | break;
89 | }
90 |
91 | return buffer.size() - numBytesBeforeRead;
92 | }
93 |
94 | int RegisterConnection::dataLengthForCurrentDataType()
95 | {
96 | if(this->bytesAvailable() <=0 || this->readDataIntoBuffer() <= 0 || !this->buffer.endsWith(SeparateToken))
97 | return 0;
98 |
99 | this->buffer.chop(1);
100 | int length = this->buffer.toInt();
101 | this->buffer.clear();
102 |
103 | return length;
104 | }
105 |
106 | bool RegisterConnection::hasEnoughData()
107 | {
108 | if(this->transferTimerId != 0)
109 | {
110 | this->killTimer(this->transferTimerId);
111 | this->transferTimerId = 0;
112 | }
113 |
114 | if(this->numBytesForCurrentDataType <= 0)
115 | this->numBytesForCurrentDataType = this->dataLengthForCurrentDataType();
116 |
117 | if(bytesAvailable() < this->numBytesForCurrentDataType || this->numBytesForCurrentDataType <= 0)
118 | {
119 | this->transferTimerId = this->startTimer(TransferTimeout);
120 | return false;
121 | }
122 |
123 | return true;
124 | }
125 |
126 | void RegisterConnection::processReadyRead()
127 | {
128 | if(this->state == WaitingForGreeting)
129 | {
130 | if(!readProtocolHeader())
131 | return;
132 | if(this->currentDataType != GREETING)
133 | {
134 | this->abort();
135 | return;
136 | }
137 |
138 | this->state = ReadingGreeting;
139 | }
140 |
141 | if(this->state == ReadingGreeting)
142 | {
143 | if(!this->hasEnoughData())
144 | return;
145 |
146 | this->buffer = this->read(this->numBytesForCurrentDataType);
147 | if(this->buffer.size() != this->numBytesForCurrentDataType)
148 | {
149 | this->abort();
150 | return;
151 | }
152 |
153 | QString greeting = QString::fromUtf8(this->buffer);
154 |
155 | if(DEBUG)
156 | qDebug() << "Get greeting message: " << greeting;
157 |
158 | QStringList addrList = greeting.split(":");
159 | this->name = addrList.at(0);
160 | QString ipStr = addrList.at(1);
161 | QString portStr = addrList.at(2);
162 | this->ip = QHostAddress(ipStr);
163 | this->port = portStr.toInt();
164 |
165 | if(DEBUG)
166 | qDebug() << "Received greeting message: " << QString::fromUtf8(this->buffer);
167 |
168 | this->buffer.clear();
169 | this->numBytesForCurrentDataType = -1;
170 | this->currentDataType = UNDEFINED;
171 |
172 | if(!this->isValid())
173 | {
174 | this->abort();
175 | return;
176 | }
177 |
178 | if(!this->isGreetingMessageSent)
179 | this->sendGreetingMessage();
180 |
181 | this->state = ReadyForUse;
182 | }
183 |
184 | do
185 | {
186 | if(currentDataType == UNDEFINED)
187 | {
188 | if(!readProtocolHeader())
189 | return;
190 | }
191 |
192 | if(!this->hasEnoughData())
193 | return;
194 |
195 | this->processData();
196 | }while(this->bytesAvailable() > 0);
197 | }
198 |
199 | bool RegisterConnection::readProtocolHeader()
200 | {
201 | if(this->transferTimerId != 0)
202 | {
203 | this->killTimer(this->transferTimerId);
204 | this->transferTimerId = 0;
205 | }
206 |
207 | if(this->readDataIntoBuffer() <= 0)
208 | {
209 | this->transferTimerId = this->startTimer(TransferTimeout);
210 | return false;
211 | }
212 |
213 | if(this->buffer == "GREETING ")
214 | this->currentDataType = GREETING;
215 | else if (this->buffer == "REGISTER ")
216 | this->currentDataType = REGISTER;
217 | else if (this->buffer == "PEERLIST ")
218 | this->currentDataType = PEERLIST;
219 | else
220 | {
221 | this->currentDataType = UNDEFINED;
222 | this->abort();
223 | return false;
224 | }
225 |
226 | this->buffer.clear();
227 | this->numBytesForCurrentDataType = this->dataLengthForCurrentDataType();
228 | return true;
229 | }
230 |
231 | void RegisterConnection::processData()
232 | {
233 | this->buffer = this->read(this->numBytesForCurrentDataType);
234 | if(this->buffer.size() != this->numBytesForCurrentDataType)
235 | {
236 | this->abort();
237 | return;
238 | }
239 |
240 | switch(this->currentDataType)
241 | {
242 | case REGISTER:
243 | this->registerMessage = QString::fromUtf8(this->buffer);
244 | emit this->newRegisterMsg(this, this->registerMessage);
245 | break;
246 | case PEERLIST:
247 | break;
248 | default:
249 | break;
250 | }
251 |
252 | this->currentDataType = UNDEFINED;
253 | this->numBytesForCurrentDataType = -1;
254 | this->buffer.clear();
255 | }
256 |
--------------------------------------------------------------------------------
/RegisterServer/registerconnection.h:
--------------------------------------------------------------------------------
1 | /* 说明:
2 | * RegisterConnection用于与中心验证服务器通信,主要交换Register注册信息和PeerList活跃用户信息
3 | * 这里,我们也有几个设计说明:
4 | * (1) 我们仍然设置Greeting的过程用于初始的连接建立过程
5 | * (2) 我们设置周期定时器用于周期发送Register信息和获取最新的活跃用户信息
6 | *
7 | */
8 |
9 | #ifndef REGISTERCONNECTION_H
10 | #define REGISTERCONNECTION_H
11 |
12 | #include "header.h"
13 | #include
14 |
15 | class RegisterConnection : public QTcpSocket
16 | {
17 | Q_OBJECT
18 | public:
19 | enum RegisterConnectionState
20 | {
21 | WaitingForGreeting,
22 | ReadingGreeting,
23 | ReadyForUse
24 | };
25 |
26 | enum DataType
27 | {
28 | GREETING,
29 | REGISTER,
30 | PEERLIST,
31 | UNDEFINED
32 | };
33 |
34 | explicit RegisterConnection(QObject *parent = 0);
35 | ~RegisterConnection();
36 |
37 | QString getPeerServerName();
38 | QHostAddress getPeerServerIP();
39 | int getPeerServerPort();
40 |
41 | signals:
42 | void newRegisterMsg(RegisterConnection *, QString);
43 | void registerError(RegisterConnection *, QAbstractSocket::SocketError);
44 |
45 | protected:
46 | void timerEvent(QTimerEvent *);
47 |
48 | public slots:
49 | void processReadyRead();
50 | void sendGreetingMessage();
51 | bool sendPeriodicPeerlistMessage(QString message);
52 | void handleSocketError(QAbstractSocket::SocketError);
53 |
54 | private:
55 |
56 | // receive
57 | int readDataIntoBuffer(int maxSize = MaxBufferSize);
58 | int dataLengthForCurrentDataType();
59 | bool readProtocolHeader();
60 | bool hasEnoughData();
61 | void processData();
62 |
63 | QString name;
64 | QHostAddress ip;
65 | int port;
66 |
67 | QByteArray buffer;
68 | enum RegisterConnectionState state;
69 | enum DataType currentDataType;
70 | int numBytesForCurrentDataType;
71 | int transferTimerId;
72 | bool isGreetingMessageSent;
73 | QString greetingMessage;
74 | QString registerMessage;
75 | };
76 |
77 | #endif // REGISTERCONNECTION_H
78 |
--------------------------------------------------------------------------------
/RegisterServer/registerserver.cpp:
--------------------------------------------------------------------------------
1 | #include "registerserver.h"
2 |
3 | RegisterServer::RegisterServer(QObject *parent) :
4 | QTcpServer(parent)
5 | {
6 | }
7 |
8 | void RegisterServer::setServerInfo(QHostAddress ip, int port)
9 | {
10 | this->myPort = port;
11 | this->myIP = ip;
12 | }
13 |
14 | bool RegisterServer::startServer()
15 | {
16 | return this->listen(this->myIP, this->myPort);
17 | }
18 |
19 | void RegisterServer::incomingConnection(qintptr socketDescriptor)
20 | {
21 | RegisterConnection *connection = new RegisterConnection(this);
22 | connection->setSocketDescriptor(socketDescriptor);
23 | emit newRegisterConnection(connection);
24 | }
25 |
--------------------------------------------------------------------------------
/RegisterServer/registerserver.h:
--------------------------------------------------------------------------------
1 | #ifndef REGISTERSERVER_H
2 | #define REGISTERSERVER_H
3 |
4 | #include "header.h"
5 | #include "registerconnection.h"
6 | #include
7 |
8 | class RegisterServer : public QTcpServer
9 | {
10 | Q_OBJECT
11 | public:
12 | explicit RegisterServer(QObject *parent = 0);
13 |
14 | void setServerInfo(QHostAddress ip, int port);
15 | bool startServer();
16 |
17 | signals:
18 | void newRegisterConnection(RegisterConnection *connection);
19 |
20 | protected:
21 | void incomingConnection(qintptr socketDescriptor);
22 |
23 | private:
24 | QHostAddress myIP;
25 | int myPort;
26 | };
27 |
28 | #endif // REGISTERSERVER_H
29 |
--------------------------------------------------------------------------------
/RegisterServer/window.cpp:
--------------------------------------------------------------------------------
1 | #include "window.h"
2 |
3 | Window::Window(QWidget *parent)
4 | : QMainWindow(parent)
5 | {
6 | this->listLabel = new QLabel(QObject::tr("Register Host List: "), this);
7 | this->registerListWidget = new QListWidget(this);
8 | this->logLabel = new QLabel(QObject::tr("Register Log: "), this);
9 | this->logRegister = new QTextEdit(this);
10 | this->ipLabel = new QLabel(QObject::tr("Server IP:"), this);
11 | this->ipBox = new QComboBox(this);
12 | this->ipLabel->setBuddy(this->ipBox);
13 | this->portLabel = new QLabel(QObject::tr("Server Port:"), this);
14 | this->portBox = new QSpinBox(this);
15 | this->portLabel->setBuddy(this->portBox);
16 |
17 | this->networkInterfacesCombo();
18 | this->portBox->setRange(1024, 65535);
19 | this->portBox->setValue(10001);
20 |
21 | this->startButton = new QPushButton(QObject::tr("Start"), this);
22 | this->stopButton = new QPushButton(QObject::tr("Stop"), this);
23 | this->logRegister->setReadOnly(true);
24 | this->startButton->setFocusPolicy(Qt::StrongFocus);
25 | this->stopButton->setEnabled(false);
26 |
27 | this->peerList.clear();
28 | this->registerConns.clear();
29 | this->serverIP = QHostAddress("127.0.0.1");
30 | this->serverPort = 10001;
31 | this->server = new RegisterServer();
32 |
33 | this->initLayout();
34 | this->resize(QSize(550, 360));
35 |
36 | connect(startButton, SIGNAL(clicked()), this, SLOT(startNetwork()));
37 | connect(stopButton, SIGNAL(clicked()), this, SLOT(stopNetwork()));
38 | }
39 |
40 | Window::~Window()
41 | {
42 | this->server->close();
43 | }
44 |
45 | // 通过读取网卡接口的信息获取本机的所有IP地址,并通过QComboBox呈现
46 | void Window::networkInterfacesCombo()
47 | {
48 | QList list = QNetworkInterface::allAddresses();
49 | foreach( QHostAddress address, list )
50 | {
51 | if(address.protocol() == QAbstractSocket::IPv4Protocol)
52 | this->ipBox->addItem(address.toString());
53 | }
54 | }
55 |
56 | // 设置整个Window的界面布局
57 | void Window::initLayout()
58 | {
59 | QVBoxLayout *listLayout = new QVBoxLayout;
60 | listLayout->addWidget(this->listLabel);
61 | listLayout->addWidget(this->registerListWidget);
62 |
63 | QHBoxLayout *ipLayout = new QHBoxLayout;
64 | ipLayout->addWidget(this->ipLabel);
65 | ipLayout->addWidget(this->ipBox);
66 | ipLayout->setStretch(0, 1);
67 | ipLayout->setStretch(1, 3);
68 |
69 | QHBoxLayout *portLayout = new QHBoxLayout;
70 | portLayout->addWidget(this->portLabel);
71 | portLayout->addWidget(this->portBox);
72 | portLayout->setStretch(0, 1);
73 | portLayout->setStretch(1, 3);
74 |
75 | QVBoxLayout *logLayout = new QVBoxLayout;
76 | logLayout->addWidget(this->logLabel);
77 | logLayout->addWidget(this->logRegister);
78 | logLayout->addLayout(ipLayout);
79 | logLayout->addLayout(portLayout);
80 |
81 | QHBoxLayout *buttonLayout = new QHBoxLayout;
82 | buttonLayout->addStretch();
83 | buttonLayout->addWidget(this->startButton);
84 | buttonLayout->addWidget(this->stopButton);
85 |
86 | QHBoxLayout *hLayout = new QHBoxLayout;
87 | hLayout->addLayout(listLayout);
88 | hLayout->addLayout(logLayout);
89 | hLayout->setStretch(0, 2);
90 | hLayout->setStretch(1, 3);
91 |
92 | QVBoxLayout *mainLayout = new QVBoxLayout;
93 | mainLayout->addLayout(hLayout);
94 | mainLayout->addLayout(buttonLayout);
95 | mainLayout->setStretch(1, 8);
96 | mainLayout->setStretch(2, 1);
97 |
98 | QWidget *widget = new QWidget(this);
99 | widget->setLayout(mainLayout);
100 |
101 | this->setCentralWidget(widget);
102 | }
103 |
104 | // 启动中心注册服务器
105 | void Window::startNetwork()
106 | {
107 | // 获取控件中的地址信息,包括IP地址和端口号
108 | QString ip = this->ipBox->currentText();
109 | this->serverIP = QHostAddress(ip);
110 | this->serverPort = this->portBox->value();
111 | if(DEBUG)
112 | {
113 | qDebug() << "Register server ip address: " << this->serverIP.toString();
114 | qDebug() << "Register server port: " << this->serverPort;
115 | }
116 |
117 | // 设置服务器信息以及启动服务器
118 | this->server->setServerInfo(this->serverIP, this->serverPort);
119 | if(this->server->startServer())
120 | {
121 | this->startButton->setEnabled(false);
122 | this->ipBox->setEnabled(false);
123 | this->portBox->setEnabled(false);
124 | this->stopButton->setEnabled(true);
125 | this->appendLogInfo("Register server started.");
126 |
127 | if(DEBUG)
128 | qDebug() << "Register server started.";
129 | }
130 | else
131 | {
132 | QMessageBox::warning(this, tr("Error"), tr("Cannot start register server!"));
133 | this->appendLogInfo("Cannot start register server.");
134 |
135 | if(DEBUG)
136 | qDebug() << "Cannot start register server.";
137 | return;
138 | }
139 |
140 | connect(this->server, SIGNAL(newRegisterConnection(RegisterConnection *)), this, SLOT(handleNewConnection(RegisterConnection *)));
141 | }
142 |
143 | // 停止注册中心服务器
144 | void Window::stopNetwork()
145 | {
146 | if(DEBUG)
147 | qDebug() << "Register server stopped!";
148 | this->appendLogInfo("Register server stopped.");
149 | this->server->close();
150 | for(int i = 0; i < this->registerConns.size(); i++)
151 | {
152 | RegisterConnection *c = this->registerConns.at(i);
153 | c->close();
154 | }
155 | this->peerList.clear();
156 | this->registerConns.clear();
157 |
158 | // Widget update
159 | this->registerListWidget->clear();
160 | this->startButton->setEnabled(true);
161 | this->ipBox->setEnabled(true);
162 | this->portBox->setEnabled(true);
163 | this->stopButton->setEnabled(false);
164 | }
165 |
166 | // 处理新建立的连接,即当有远端客户端发起注册请求时,建立TCP连接,发送注册信息
167 | void Window::handleNewConnection(RegisterConnection *connection)
168 | {
169 | if(DEBUG)
170 | qDebug() << "Handle new connection.";
171 |
172 | this->addRegisterConnection(connection);
173 |
174 | connect(connection, SIGNAL(newRegisterMsg(RegisterConnection *, QString)), this, SLOT(handleNewRegisterMsg(RegisterConnection *, QString)));
175 | connect(connection, SIGNAL(registerError(RegisterConnection*,QAbstractSocket::SocketError)),
176 | this, SLOT(handleRegisterError(RegisterConnection*,QAbstractSocket::SocketError)));
177 | }
178 |
179 | // 处理新的注册信息,如果注册信息更新,便更新相应表项
180 | void Window::handleNewRegisterMsg(RegisterConnection *connection, QString message)
181 | {
182 | if(DEBUG)
183 | {
184 | qDebug() << "Enter handle_new_register_msg function:";
185 | qDebug() << "New register message: " << message;
186 | }
187 |
188 | QStringList infoList = message.split("@");
189 | QString hostName = infoList.at(0);
190 | QString addr = infoList.at(1);
191 | QStringList addrList = addr.split(":");
192 | QString ipStr = addrList.at(0);
193 | QHostAddress ip = QHostAddress(ipStr);
194 | QString portStr = addrList.at(1);
195 | int port = portStr.toInt();
196 |
197 | if(DEBUG)
198 | {
199 | qDebug() << "Register message information: ";
200 | qDebug() << "Hostname: " << hostName;
201 | qDebug() << "IP address:" << ipStr;
202 | qDebug() << "Port:" << portStr;
203 | }
204 |
205 | PeerInfo *pi = findPeer(hostName, ip, port);
206 | if(pi)
207 | {
208 | pi->refresh();
209 | this->appendLogInfo("Activate exist register: " + message);
210 | if(DEBUG)
211 | qDebug() << "Active timer of PeerInfo reset.";
212 | }
213 | else
214 | {
215 | pi = new PeerInfo(this, hostName, ip, port);
216 | this->addPeerInfoIntoList(pi);
217 | connect(pi, SIGNAL(peerExpire(PeerInfo *)), this, SLOT(handlePeerTimeout(PeerInfo *)));
218 |
219 | // 刷新Register的列表控件
220 | this->updateRegisterListWidget();
221 | this->appendLogInfo("New register: " + message);
222 |
223 | // 发送新的PeerList到远端
224 | this->broadcastPeerChange();
225 | }
226 |
227 | if(DEBUG)
228 | qDebug() << "Handle new register msg done.";
229 | }
230 |
231 | // 处理PeerList表项过期
232 | void Window::handlePeerTimeout(PeerInfo *pi)
233 | {
234 | if(DEBUG)
235 | qDebug() << "PeerInfo expired: " << pi->getPeerName();
236 | this->appendLogInfo("PeerInfo expired: " + pi->getPeerName());
237 |
238 | RegisterConnection *c = this->findConnection(pi);
239 | this->removePeerInfoFromList(pi);
240 | this->removeRegisterConnection(c);
241 | this->broadcastPeerChange();
242 | this->updateRegisterListWidget();
243 |
244 | if(DEBUG)
245 | qDebug() << "Handle expired done.";
246 | }
247 |
248 | // 处理注册Client断线的情况
249 | void Window::handleRegisterError(RegisterConnection *connection, QAbstractSocket::SocketError error)
250 | {
251 | if(DEBUG)
252 | qDebug() << "Register connection network error.";
253 |
254 | QString errorString;
255 | switch(error)
256 | {
257 | case QAbstractSocket::ConnectionRefusedError:
258 | errorString = "Connection refused!";
259 | break;
260 | case QAbstractSocket::RemoteHostClosedError:
261 | errorString = "Remote host closed.";
262 | break;
263 | case QAbstractSocket::HostNotFoundError:
264 | errorString = "Host not found!";
265 | break;
266 | case QAbstractSocket::NetworkError:
267 | errorString = "Network error!";
268 | break;
269 | case QAbstractSocket::AddressInUseError:
270 | errorString = "Address already in use!";
271 | break;
272 | case QAbstractSocket::UnknownSocketError:
273 | default:
274 | errorString = "Unknown socket error!";
275 | break;
276 | }
277 |
278 | if(DEBUG)
279 | qDebug() << "Register connection error: " << errorString;
280 |
281 | this->appendLogInfo("Connection Error: " + errorString);
282 | PeerInfo *pi = this->findPeer(connection->getPeerServerName(), connection->getPeerServerIP(), connection->getPeerServerPort());
283 | this->appendLogInfo("Delete register: " + pi->getPeerName());
284 | this->removePeerInfoFromList(pi);
285 | pi->clear();
286 | this->removeRegisterConnection(connection);
287 | this->broadcastPeerChange();
288 | this->updateRegisterListWidget();
289 |
290 | if(DEBUG)
291 | qDebug() << "Handle network error done.";
292 | }
293 |
294 | // 更新ListWidget控件信息
295 | void Window::updateRegisterListWidget()
296 | {
297 | this->registerListWidget->clear();
298 | for(int i = 0; i < this->peerList.size(); i++)
299 | {
300 | PeerInfo *pi = this->peerList.at(i);
301 | QString itemString = pi->getPeerName() + "@"
302 | + pi->getPeerIP() + ":"
303 | + QString::number(pi->getPeerPort());
304 | this->registerListWidget->addItem(new QListWidgetItem(itemString));
305 | }
306 | }
307 |
308 | PeerInfo * Window::findPeer(QString name, QHostAddress ip, int port)
309 | {
310 | for(int i = 0; i < this->peerList.size(); i++)
311 | {
312 | PeerInfo *p = this->peerList.at(i);
313 | if(p->getPeerName() == name &&
314 | p->getPeerIP() == ip.toString() &&
315 | p->getPeerPort() == port)
316 | return p;
317 | }
318 |
319 | return NULL;
320 | }
321 |
322 | RegisterConnection * Window::findConnection(PeerInfo *pi)
323 | {
324 | qDebug() << "Enter findConnection.";
325 | for(int i = 0; i < this->registerConns.size(); i++)
326 | {
327 | RegisterConnection *c = this->registerConns.at(i);
328 | if(c->getPeerServerName() == pi->getPeerName() &&
329 | c->getPeerServerIP().toString() == pi->getPeerIP() &&
330 | c->getPeerServerPort() == pi->getPeerPort())
331 | return c;
332 | }
333 |
334 | return NULL;
335 | }
336 |
337 | QString Window::genPeerListStr()
338 | {
339 | if(DEBUG)
340 | qDebug() << "Generate PeerList String.";
341 |
342 | QString peerListStr("");
343 | for(int i = 0; i < this->peerList.size(); i++)
344 | {
345 | PeerInfo *p = this->peerList.at(i);
346 | QString peerStr = p->getPeerName() + "@"
347 | + p->getPeerIP() + ":"
348 | + QString::number(p->getPeerPort()) + ";";
349 | peerListStr += peerStr;
350 | }
351 | peerListStr.chop(1);
352 |
353 | return peerListStr;
354 | }
355 |
356 | void Window::broadcastPeerChange()
357 | {
358 | if(DEBUG)
359 | qDebug() << "Broadcast peerList changed message";
360 |
361 | QString str = this->genPeerListStr();
362 | for(int i = 0; i < this->registerConns.size(); i++)
363 | {
364 | RegisterConnection *c = this->registerConns.at(i);
365 | c->sendPeriodicPeerlistMessage(str);
366 | }
367 |
368 | if(DEBUG)
369 | qDebug() << "Broadcast message sent.";
370 | }
371 |
372 | void Window::addRegisterConnection(RegisterConnection *connection)
373 | {
374 | this->mutex2.lock();
375 | this->registerConns.push_back(connection);
376 | this->mutex2.unlock();
377 |
378 | if(DEBUG)
379 | qDebug() << "Add new connection into registerConns.";
380 | }
381 |
382 | void Window::removeRegisterConnection(RegisterConnection *connection)
383 | {
384 | this->mutex2.lock();
385 | this->registerConns.removeOne(connection);
386 | connection->deleteLater();
387 | this->mutex2.unlock();
388 |
389 | if(DEBUG)
390 | qDebug() << "Remove connection from registerConns.";
391 | }
392 |
393 | void Window::addPeerInfoIntoList(PeerInfo *pi)
394 | {
395 | this->mutex1.lock();
396 | this->peerList.push_back(pi);
397 | this->mutex1.unlock();
398 |
399 | if(DEBUG)
400 | qDebug() << "Add new PeerInfo into peerList:" << pi->getPeerName();
401 | }
402 |
403 | void Window::removePeerInfoFromList(PeerInfo *pi)
404 | {
405 | this->mutex1.lock();
406 | this->peerList.removeOne(pi);
407 | this->mutex1.unlock();
408 |
409 | if(DEBUG)
410 | qDebug() << "Remove PeerInfo from peerList" << pi->getPeerName();
411 | }
412 |
413 | void Window::appendLogInfo(QString msg)
414 | {
415 | QDateTime time = QDateTime::currentDateTime();
416 | QString timeString = time.toString("yyyy-MM-dd hh:mm:ss");
417 | this->logRegister->append(timeString + " >\n" + msg);
418 | }
419 |
--------------------------------------------------------------------------------
/RegisterServer/window.h:
--------------------------------------------------------------------------------
1 | #ifndef WINDOW_H
2 | #define WINDOW_H
3 |
4 | #include "header.h"
5 | #include "peerinfo.h"
6 | #include "registerconnection.h"
7 | #include "registerserver.h"
8 | #include
9 |
10 | class Window : public QMainWindow
11 | {
12 | Q_OBJECT
13 |
14 | public:
15 | Window(QWidget *parent = 0);
16 | ~Window();
17 |
18 | public slots:
19 | void startNetwork();
20 | void stopNetwork();
21 | void handleNewConnection(RegisterConnection *connection);
22 | void handleRegisterError(RegisterConnection *, QAbstractSocket::SocketError);
23 | void handleNewRegisterMsg(RegisterConnection *, QString message);
24 | void handlePeerTimeout(PeerInfo *);
25 |
26 | private:
27 | // 私有函数及方法(主要包括界面初始化、网络操作工具函数等)
28 | void initLayout();
29 | void networkInterfacesCombo();
30 | void updateRegisterListWidget();
31 | void appendLogInfo(QString);
32 |
33 | QString genPeerListStr();
34 | PeerInfo* findPeer(QString, QHostAddress, int);
35 | RegisterConnection* findConnection(PeerInfo *);
36 |
37 | void addRegisterConnection(RegisterConnection *);
38 | void removeRegisterConnection(RegisterConnection *);
39 | void addPeerInfoIntoList(PeerInfo *);
40 | void removePeerInfoFromList(PeerInfo *);
41 | void broadcastPeerChange();
42 |
43 | // 私有成员变量(主要与网络相关)
44 | QMutex mutex1, mutex2;
45 | RegisterServer *server;
46 | QList registerConns;
47 | QList peerList;
48 | QHostAddress serverIP;
49 | int serverPort;
50 |
51 | // 私有成员变量(主要与界面相关)
52 | QLabel *listLabel;
53 | QListWidget *registerListWidget;
54 | QLabel *logLabel;
55 | QTextEdit *logRegister;
56 | QLabel *ipLabel;
57 | QComboBox *ipBox;
58 | QLabel *portLabel;
59 | QSpinBox *portBox;
60 | QPushButton *startButton;
61 | QPushButton *stopButton;
62 |
63 | };
64 |
65 | #endif // WINDOW_H
66 |
--------------------------------------------------------------------------------