admin管理员组文章数量:1582655
前端JavaScript HTML CSS 为了减小JavaScript动态操作节点的开支消耗,引入了Vue技术
数据库 MySQL 保存聊天信息、用户名、用户密码。采用JDBC编程
后端 servlet 用会话session记忆每个用户状态信息
交互 前端与后端用Ajax交互,静态页面之间通过URL的查询字符部分传递数据(不敏感的)
登录部分我想实现一个登录与注册的一个互相切换(无页面跳转),抽象出来就是一堆HTML节点与另一堆的交替互换。如果用原生方法——JavaScript直接操作节点,这样不仅代码冗长且性能开支大,不宜采用。想到Vue里面有个内置组件component,倒是可以一试。
来看component语法是这样的→
<component :is="view"></component>//其中view可以是任何合法的标识符
//它标识一个组件,通过指定它就可以动态改变component这个组件
在HTML里面定义好这个组件后,在JavaScript里面就要这么写了→
var register = {
template:"<div style=\"position:absolute;top:150px;left:500px;\">" +"<br>"+
"Register your username : </p><input type=\"text\" name=\"username\" id=\"username\" class=\"inputStyle\"><br><br>\n" +
"Register your password : </p><input type=\"password\" name=\"password\" id=\"password\" class=\"inputStyle\"><br><br><br>\n" +
" <input type=\"button\" value=\"Register\" onclick=\"sendZCrequest();\" class=\"buttonStyle\"> \n" +
" <input type=\"button\" value=\"Reset\" onclick=\"ZCreset();\"class=\"buttonStyle\"></div>"
}
var login = {
template:"<div style=\"position:absolute;top:150px;left:500px;\">" +"<br>"+
"Login your username : </p><input type=\"text\" name=\"username1\" id=\"username1\" class=\"inputStyle\"><br><br>\n" +
"Login your password : </p><input type=\"password\" name=\"password1\" id=\"password1\" class=\"inputStyle\"><br><br><br>\n" +
" <input type=\"button\" value=\"Login\" onclick=\"sendDLrequest();\"class=\"buttonStyle\"> " +
" <input type=\"button\" value=\"Reset\" onclick=\"DLreset();\"class=\"buttonStyle\"></div>"
}
var app = new Vue({
el:"#back",//back为被挂载的节点id
components:{login,register},//字符串被解析成组件
data(){
return{view:"login"}
},
methods:{
shift(view){
this.view=view;
}
}
});
注意到里面的组件对象是用一堆HTML代码组成的字符串,在vue对象里这些字符串会被解析成一堆节点并生成到el属性绑定的id所属的节点里,充当子节点。
另外还分享一下自己原创的两个样式(整个聊天室都有用到)
.buttonStyle{
height: 27px;
width: 80px;
border: 0;
background-color:#6C6C6C;
box-shadow:0 0 1px #272727,
0 0 10px 2px #3C3C3C,
0 0 10px 4px #4F4F4F;
border-radius: 4px;
font-family: Calibri;
font-weight: 800;
font-style: italic;
color: aqua;
cursor: pointer;
}
.buttonStyle:hover{
animation: buttonEffect 0.4s linear;
transition-timing-function: linear;
}
.buttonStyle:active{
transform: scale(1.2);
bottom: -3px;
transition-timing-function: ease-in-out;
}
@keyframes buttonEffect {
0%{background: radial-gradient(ellipse 20px 8px,white,black,black);}
20%{background: radial-gradient(ellipse 30px 12px,white,black,black);}
40%{background: radial-gradient(ellipse 40px 16px,white,black,black);}
60%{background: radial-gradient(ellipse 50px 20px,white,black,black);}
80%{background: radial-gradient(ellipse 60px 24px,white,black,black);}
100%{background: radial-gradient(ellipse 70px 280px,white,black,black);}
}
.inputStyle{
width: 200px;
height: 30px;
background-color:#4F4F4F;
border-radius: 8px;
border-width: 5px 5px 5px 5px;
border-style: inset;
border-color: black;
font-family: "Droid Sans Mono Slashed";
font-weight: 300;
font-style: italic;
color: aqua;}
.inputStyle:focus{
background-color:black;
}
.inputStyle:hover{
animation: inputEffect 0.8s linear;
transition-timing-function: linear;
}
@keyframes inputEffect {
0%{border-top-color: aqua;
background: linear-gradient(to right,aqua,black 20%)}
25%{border-right-color: aqua;
background: linear-gradient(to right,aqua,black 40%)}
50%{border-bottom-color: aqua;
background: linear-gradient(to right,aqua,black 60%)}
75%{border-left-color: aqua;
background: linear-gradient(to right,aqua,black 80%)}
100%{border-color: cyan;
background: linear-gradient(to right,aqua,black 100%)}
}
登录界面完整代码如下→
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=UTF-8">
<title>Welcome to Login page</title>
<script type="text/javascript" src="vue.js"></script>
</head>
<body>
<style type="text/css">
@import "buttonStyle.css";
@import "inputStyle.css";
#prompt{position:absolute;
top:465px;
left:460px;
font-size:20px;
font-weight: 300;
color: darkred;
text-shadow:darkred;/*向右阴影*/
}
#back{position:fixed;
top:0;
left:0;
width:100%;
height:100%;
background: linear-gradient(to bottom,#3C3C3C,#FFFFFF 400px);
}
div{height:290px;
width:250px;
padding: 20px;
border-radius:5px;
border:solid 1px black;}
p{ font-style:italic;
font-weight:500;
font-size: 20px;
font-family:\6977\4F53_GB2312;
color: greenyellow;
cursor: pointer;
}
p:hover{
color: aqua;
}
p:active{
transform: scale(1.2);
}
</style>
<div id="back">
<p style="text-align: center;top:30px" @click="shift('register')">No account you possess,please click here to register....</p>
<p style="text-align: center;top:60px" @click="shift('login')">Click here to back to login....</p>
<component :is="view"></component>
<p id="prompt"></p>
</div>
<script type="text/javascript">
var XMLHttpReq;
function DLreset(){//重置事件
document.getElementById("username1").value="";
document.getElementById("password1").value="";
}
function ZCreset(){
document.getElementById("username").value="";
document.getElementById("password").value="";
}
function createXML(){
if(window.XMLHttpRequest)
// DOM 2 浏览器
{XMLHttpReq = new XMLHttpRequest();}
else if(window.ActiveXObject)
{//1 IE 浏览器
try
{XMLHttpReq= new Activexobject("Msxm12.XMLHTTP");}
catch(e)
{try
{XMLHttpReq = new ActivexObject("Microsoft.XMLHTTP")}
catch(e){}
}}//在考虑不同浏览器的兼容问题下,创建一个XMLHttpRequest对象
}
function sendZCrequest(){//注册请求
var username = document.getElementById("username").value;
var password = document.getElementById("password").value;
createXML();
XMLHttpReq.open("post","ZCcontroller",true);// 通过open()方法取得与服务器的连接,发送POST请求
XMLHttpReq.setRequestHeader("Content-Type",
"application/x-www-form-urlencoded");// 设置请求头-发送 POST 请求时需要该请求头
XMLHttpReq.onreadystatechange = processResponse;// 指定 XMLHttpRequest 状态改变时的处理函数
XMLHttpReq.send("username="+username+"&password="+password);
}
function sendDLrequest(){//登录请求
var username1 = document.getElementById("username1").value;
var password1 = document.getElementById("password1").value;
createXML();
XMLHttpReq.open("post","DLcontroller",true);// 通过open()方法取得与服务器的连接,发送POST请求
XMLHttpReq.setRequestHeader("Content-Type",
"application/x-www-form-urlencoded");// 设置请求头-发送 POST 请求时需要该请求头
XMLHttpReq.onreadystatechange = processResponse;// 指定 XMLHttpRequest 状态改变时的处理函数
XMLHttpReq.send("username1="+username1+"&password1="+password1);
}
function processResponse(){
if(XMLHttpReq.readyState == 4){
if(XMLHttpReq.status == 200){
var app = document.getElementById("prompt");
if(app.hasChildNodes())
{app.removeChild(app.firstChild);}
var txt1=XMLHttpReq.responseText;
var signal="success";
if(txt1.trim()==signal)//用trim对接收到的数据进行过滤
{var username1 = document.getElementById("username1").value;
var location="http://localhost:8080/web/Chat.html?name="+encodeURIComponent(username1);
window.location.href=location;}
var txt=document.createTextNode(XMLHttpReq.responseText);
app.appendChild(txt);
}
else{
window.alert("资源加载出现错误!!");
}
}
}
var register = {
template:"<div style=\"position:absolute;top:150px;left:500px;\">" +"<br>"+
"Register your username : </p><input type=\"text\" name=\"username\" id=\"username\" class=\"inputStyle\"><br><br>\n" +
"Register your password : </p><input type=\"password\" name=\"password\" id=\"password\" class=\"inputStyle\"><br><br><br>\n" +
" <input type=\"button\" value=\"Register\" onclick=\"sendZCrequest();\" class=\"buttonStyle\"> \n" +
" <input type=\"button\" value=\"Reset\" onclick=\"ZCreset();\"class=\"buttonStyle\"></div>"
}
var login = {
template:"<div style=\"position:absolute;top:150px;left:500px;\">" +"<br>"+
"Login your username : </p><input type=\"text\" name=\"username1\" id=\"username1\" class=\"inputStyle\"><br><br>\n" +
"Login your password : </p><input type=\"password\" name=\"password1\" id=\"password1\" class=\"inputStyle\"><br><br><br>\n" +
" <input type=\"button\" value=\"Login\" onclick=\"sendDLrequest();\"class=\"buttonStyle\"> " +
" <input type=\"button\" value=\"Reset\" onclick=\"DLreset();\"class=\"buttonStyle\"></div>"
}
var app = new Vue({
el:"#back",
components:{login,register},
data(){
return{view:"login"}
},
methods:{
shift(view){
this.view=view;
}
}
});
</script>
</body>
</html>
效果图(那个层叠背景录制效果不佳,真实效果还需亲身体验)
聊天界面部分
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=1024" http-equiv="Content-Type" content="text/html;charset=UTF-8">
<title></title>
</head>
<body style="background-color:darkseagreen" onload="sendEmptyrequest();">
<script type="text/javascript">
var XMLHttpReq;
function createXML(){
if(window.XMLHttpRequest)
// DOM 2 浏览器
{XMLHttpReq = new XMLHttpRequest();}
else if(window.ActiveXObject)
{//1 IE 浏览器
try
{XMLHttpReq= new Activexobject("Msxm12.XMLHTTP");}
catch(e)
{try
{XMLHttpReq = new ActivexObject("Microsoft.XMLHTTP")}
catch(e){}
}}//在考虑不同浏览器的兼容问题下,创建一个XMLHttpRequest对象
}
function sendrequest(){
var chatmassage= document.getElementById("chatInput").value;
var b=window.location.search.split("?");
var a=b[1].split("=");
var username=decodeURIComponent(a[1]);
createXML();
XMLHttpReq.open("post","MSGcontroller",true);// 通过open()方法取得与服务器的连接,发送POST请求
XMLHttpReq.setRequestHeader("Content-Type",
"application/x-www-form-urlencoded");// 设置请求头-发送 POST 请求时需要该请求头
XMLHttpReq.onreadystatechange = processResponse;// 指定 XMLHttpRequest 状态改变时的处理函数
XMLHttpReq.send("chatmassage="+chatmassage+"&username="+username);
document.getElementById("chatInput").value="";
}
function sendEmptyrequest(){
createXML();
XMLHttpReq.open("post","MSGcontroller",true);// 通过open()方法取得与服务器的连接,发送POST请求
XMLHttpReq.setRequestHeader("Content-Type",
"application/x-www-form-urlencoded");// 设置请求头-发送 POST 请求时需要该请求头
XMLHttpReq.onreadystatechange = processResponse;// 指定 XMLHttpRequest 状态改变时的处理函数
XMLHttpReq.send(null);
setTimeout("sendEmptyrequest()",500);
}
function processResponse(){
if(XMLHttpReq.readyState == 4){
if(XMLHttpReq.status == 200){
var massages=JSON.parse(XMLHttpReq.responseText);
var text="";
for(var i=0;i<massages.length;i++)
{text=text+massages[i]+"\n";}
document.getElementById("chatbox").value=text;
}
else{
window.alert("资源加载出现错发!");
}
}
}
function withdraw(){//发送撤回消息请求
var signal=confirm("😊是否要撤回您发的最后一条消息?😊")
if(signal){
var b=window.location.search.split("?");
var a=b[1].split("=");
var username=decodeURIComponent(a[1]);
createXML();
XMLHttpReq.open("post","MSGcontroller",true);// 通过open()方法取得与服务器的连接,发送POST请求
XMLHttpReq.setRequestHeader("Content-Type",
"application/x-www-form-urlencoded");// 设置请求头-发送 POST 请求时需要该请求头
XMLHttpReq.onreadystatechange = processResponse;// 指定 XMLHttpRequest 状态改变时的处理函数
XMLHttpReq.send("withdraw="+"true"+"&username="+username);
alert("😊撤回成功😊")}
}
</script>
<style type="text/css">
@import "buttonStyle.css";
@import "inputStyle.css";
@import "Textarea.css";
.back{position:fixed;
top:0;
left:0;
width:100%;
height:100%;
background-image:url(background1.jpg);
background-repeat: no-repeat;
background-position:center;}
p{font-style:italic;
font-weight:200;
font-size: 20px;
font-family:\6977\4F53_GB2312;
color:black;
}
</style>
<div class="back">
<div style="position:absolute;top:135px;left:105px;">
<p>Welcome to this page!</p>
<p>Every question you have will be solved</p>
<p>by exchange with others as enthusiastic</p>
<p>as you in this site!</p>
<p>Here you can even meet like-minded</p>
<p>people and become intimate friends.</p>
</div>
<textarea disabled id="chatbox" style="position:absolute;left:500px;top:0px;height:430px;width:300px;color:yellow"></textarea>
<input type="text" id="chatInput" class="inputStyle" style="position: absolute;left:497px;top:450px;width:300px">
<input type="button" class="buttonStyle" value="发送" style="position:absolute;left:500px;top:510px" onclick="sendrequest();">
<input type="button" class="buttonStyle" value="撤回" style="position:absolute;left:730px;top:510px" onclick="withdraw();">
</div>
</body>
</html>
servlet部分
package lee;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import net.sf.json.JSONArray;
import java.util.ArrayList;
/**
* Servlet implementation class MSGcontroller
*/
@WebServlet("/MSGcontroller")
public class MSGcontroller extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public MSGcontroller() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
request.setCharacterEncoding("UTF-8");
String withdraw=request.getParameter("withdraw");
String chatmassage=request.getParameter("chatmassage");
String username=request.getParameter("username");
HttpSession session=request.getSession();//得到这个请求对应的会话,如果无,该方法会自动创建一个
session.setAttribute("username", username);
response.setContentType("text/html;charset=UTF-8");
if(withdraw!=null)
{
manager.withdraw((String)session.getAttribute("username"));//在会话上绑定值,用以标识一个请求的状态信息
}
if(chatmassage!=null)
{username=(String)session.getAttribute("username");
manager.addChatmsg(username,chatmassage);}
ArrayList<String> Buffer=manager.getBuffer();
JSONArray jsonarray=JSONArray.fromObject(Buffer);//list转化成JSONArarry
response.getWriter().println(jsonarray);
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
package lee;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@WebServlet("/ZCcontroller")
public class ZCcontroller extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public ZCcontroller() {
super();
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("UTF-8");
String username=request.getParameter("username");
String password=request.getParameter("password");
response.setContentType("text/html;charset=UTF-8");
if(!username.equals("") && !password.equals("") && username!=null && password!=null)
{if(manager.examinationZC(username))
{
manager.addmsg(username,password);
response.getWriter().println("欢迎<<"+username+">>加入我们的大家庭! ! "+"\n"
+"快去登录吧😘~❤❤~😘");}
else {response.getWriter().println("😟您心仪的用户名<<"+username+">>已经被别人先注册啦,请重新注册😗");
}}
else {response.setContentType("text/html;charset=UTF-8");
response.getWriter().println("😒输入不能为空哦,请重新进行注册~~/(ㄒoㄒ)/~~");}
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
package lee;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* Servlet implementation class DLcontroller
*/
@WebServlet("/DLcontroller")
public class DLcontroller extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public DLcontroller() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
request.setCharacterEncoding("UTF-8");
String username=request.getParameter("username1");
String password=request.getParameter("password1");
response.setContentType("text/html;charset=UTF-8");
if(!username.equals("") && !password.equals("") && username!=null && password!=null) {
if(manager.examinationDL(username, password)) {
response.getWriter().println("success");
}
else {response.getWriter().println("😂连自己的用户名和密码都不记得了吗,再想想吧😊");
}
}
else {
response.getWriter().println("😒输入不能为空哦,请重新进行登录😊");
}
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
JDBC部分
package lee;
import java.sql.ResultSet;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.util.ArrayList;
class manager {
static private String driver="com.mysql.cj.jdbc.Driver";//数据库驱动类所对应的字符串
static private String URL="jdbc:mysql://localhost:3306/mydatabase?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8";
//URL语法格式如下
//jdbc:mysql:是固定的写法,后面跟主机名localhost,3306是默认的MySQL端口号
//serverTimezone=UTC是指定时区时间为世界统一时间
//useUnicode=true是指是否使用Unicode字符集,赋值为true
//characterEncoding=utf-8是指定字符编码格式为UTF8
static private Connection cnt=null;
static void initConnection() {//建立与数据库的连接
try {
Class.forName(driver);
cnt=DriverManager.getConnection(URL,"root","941593760s");
}
catch(SQLException e) {
e.printStackTrace();
}
catch(ClassNotFoundException e) {
e.printStackTrace();}
catch(Exception e) {
e.printStackTrace();
}}
static void addmsg(String username,String password) {//添加注册信息
if(cnt==null) {
initConnection();
}
try{
PreparedStatement ps=cnt.prepareStatement("insert into user values(?,?)");
ps.setString(1, username);
ps.setString(2, password);
ps.executeUpdate();
}
catch(SQLException e) {
e.printStackTrace();
}
catch(Exception e) {
e.printStackTrace();
}
}
static void addChatmsg(String username,String message) {//添加聊天记录
if(cnt==null) {
initConnection();
}
try{
PreparedStatement ps=cnt.prepareStatement("insert into messageLibrary (username,message) values(?,?)");
ps.setString(1, username);
ps.setString(2, message);
ps.executeUpdate();
}
catch(SQLException e) {
e.printStackTrace();
}
catch(Exception e) {
e.printStackTrace();
}
}
static boolean examinationDL(String username,String password) {//检验登录信息(密码与用户名)是否正确
if(cnt==null) {
initConnection();
}
try(
PreparedStatement ps=cnt.prepareStatement("select * from user where username=? and password=?"))
{ps.setString(1, username);
ps.setString(2, password);
ResultSet rs=ps.executeQuery();
if(rs.next()) {
return(true);}//登录成功
}
catch(Exception e) {
e.printStackTrace();
}
return(false);
}
static boolean examinationZC(String username) { //检验注册所用的用户名是否有重复 有重复返回false 无则返回true
if(cnt==null) {
initConnection();
}
try(
PreparedStatement ps=cnt.prepareStatement("select * from user where username=?"))
{ps.setString(1, username);
ResultSet rs=ps.executeQuery();
if(rs.next()) {
return(false);}//有重复的的名称,请重新注册(保证数据库里面的用户名唯一)
}
catch(Exception e) {
e.printStackTrace();
}
return(true);
}
static ArrayList<String> getBuffer() {//将所有的聊天信息添加在一个list集合里面,用于JSON数据交互的媒介
if(cnt==null) {
initConnection();
}
ArrayList<String> Buffer=new ArrayList<String>();//在方法里面创建对象,保证线程并发安全
if(Buffer.size()==0)
{Buffer.add("");}
try(
PreparedStatement ps=cnt.prepareStatement("select * from messageLibrary"))
{
ResultSet rs=ps.executeQuery();
while(rs.next()) {
Buffer.add(rs.getString("username")+" : "+rs.getString("message"));
}
}
catch(Exception e) {
e.printStackTrace();
}
return(Buffer);
}
static void withdraw(String username) {//撤回消息
if(cnt==null) {
initConnection();
}
try( PreparedStatement ps1=cnt.prepareStatement("select * from messageLibrary where username=? order by id DESC limit 1");
PreparedStatement ps2=cnt.prepareStatement("delete from messageLibrary where id=?"))
{ ps1.setString(1, username);
ResultSet rs=ps1.executeQuery();
if(rs.next()) {
int id=rs.getInt("id");
ps2.setInt(1, id);
ps2.executeUpdate();
}
}
catch(Exception e) {
e.printStackTrace();
}
}
}
版权声明:本文标题:Web开发了一个完整精美的聊天室(登录部分引入了Vue技术) 内容由热心网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:https://m.elefans.com/dianzi/1727895664a1136765.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论