这不是一般的统计,准确的说,这是给留过言的朋友用的。在我看来留言交流是一种方式,但我想知道最近有哪些朋友过来过,哪些来了在潜水。。。前几天正好crossyou写了一篇文章关于如何显示在线博友的,思路很好。我在网上找了一段php+xml显示在线人数的方法,将其用到wordpress里面,基本原理还是根据保存的cookie,把来访的博友信息读出来放到一个地方保存,需要时取出来。没用到数据库,ajax也省略了,效果最初是展示目前博客在线的(非bot)访客信息,留言有cookie的显示头像和网址,对没有留言的显示匿名网友和IP地址。
好像有人反映太邪恶了点,没有留言的就显示IP给大家看,这个还是撤掉了。我又换了另一种,就是只显示留言过的朋友访问信息,刷新按时间先后,比较像XX空间,淫淫网之类的“谁看了我”功能。
废话不说了,上代码:
<?php function online(){ $Now=time()+(60*60*get_settings("gmt_offset")); //服务器时间不同 $FileName= TEMPLATEPATH.'/view.xml'; //保存位置,需要755权限,默认位置:主题跟目录 $num=9;//数量 $XML=new DomDocument; $XML->load($FileName); $Items=$XML->getElementsByTagName("item"); $I=0; //循环初始化 $s=0; $output=''; if(isset($_COOKIE['comment_author_'.COOKIEHASH])) { $author = $_COOKIE['comment_author_'.COOKIEHASH]; }else{ $author =''; } if(isset($_COOKIE['comment_author_email_'.COOKIEHASH])) { $Email = $_COOKIE['comment_author_email_'.COOKIEHASH]; }else{ $Email ='xxx@xxx.com'; } if(isset($_COOKIE['comment_author_url_'.COOKIEHASH])) { $url = $_COOKIE['comment_author_url_'.COOKIEHASH]; }else{ $url ='http://'.getenv('REMOTE_ADDR');//无地址的那就放IP地址了 } foreach ($Items as $Item){ $Oldauthor=$Item->childNodes->item(0)->nodeValue; $OldEmail=$Item->childNodes->item(1)->nodeValue; $Oldurl=$Item->childNodes->item(2)->nodeValue; $Time=$Item->childNodes->item(3)->nodeValue; $output.= '<li class="r_item"><div class="row">'.get_avatar($OldEmail, 32).'<span class="r_name">'.$Oldauthor.' 于 '.$Time.'</span><span class="r_excerpt"><a href="'.$Oldurl.'" rel="nofollow">'.$Oldurl.'</a></span></div><div class="clear"></div></li>'; if($I >$num){ $Item=$XML->documentElement->getElementsByTagName("item")->item($s); //删掉久远的 $XML->documentElement->removeChild($Item); $XML->save($FileName); $s++; } if( $Oldauthor==$author || $OldEmail== $Email ){ $Item=$XML->documentElement->getElementsByTagName("item")->item($I); //删掉原来的,因为这淫又来了 $XML->documentElement->removeChild($Item); $XML->save($FileName); } $I++; } if($author !=''){//没cookie的不要进去 $XML->formatOutput = true; $XML_Online=$XML->getElementsByTagName("online")->item(0); $XML_Online_Item=$XML->createElement("item"); $Newauthor =$XML->createElement("author",$author); $XML_Online_Item->appendChild($Newauthor); $NewEmail=$XML->createElement("Email",$Email); $XML_Online_Item->appendChild($NewEmail); $NewUrl=$XML->createElement("url",$url); $XML_Online_Item->appendChild($NewUrl); $XML_Online_Item_Time=$XML->createElement("time",$Now); $XML_Online_Item->appendChild($XML_Online_Item_Time); $XML_Online->appendChild($XML_Online_Item); $XML->save($FileName); } if($Items->length<=1){ $output.= '<li class="r_item"><div class="row"><span class="r_excerpt">最近只有你来过⊙﹏⊙b汗</span></div><div class="clear"></div></li>'."\n"; } echo $output; }
以上加到主题function里面,另外需要一个xml文件
新建一个文本文件,内容如下,并另存为.XML(放置的地址与上面设置的地址一致,注意必须是相对路径,并且可写。)
<?xml version="1.0" encoding="utf-8"?> <online> <item><author>you</author><Email>1@123.com</Email><url>http://127.0.0.1</url><time>1281802053</time></item></online>
里面的格式就是这样的,也许会有一些安全隐患,比如不要让别人下载到xml文件,邮箱地址是没有加密的。所以xml地址自己知道就可以了。(注:加密的我也写过,保存md5()后的邮箱就行了)
最近在学着试试把来访数据保存到数据库里面,但又想每次要多很多查询,肯定前台还是做ajax比较好。不过更复杂的功能已经有插件了,似乎还是简单点好。
最后,已知有一个bug,有时候一个人会显示两行,不定期发作,懂的朋友请教下为啥?
08.30更新,测试了很久,在php代码后面加上
unset($Now,$FileName,$XML,$Items,$I,$s);
OK~
rw xml里写的那堆都是什么意思。。尤其是1281802053
@snowxh ,unix时间戳
这个功能有点吓人~我从自力那来的,一进来就看到欢迎来自 自力博客朋友。。。。刚又发现个吓人的功能,我刚没提交留言又从自力那点了下结果发现“嗨~, Afio 我发现你来了很多次也没有留言! 欢迎发表你的看法.”
@Afio ,谁让你潜水的
这个留言框好丰富地说
我插个图片试试[img src=http://pic.yupoo.com/moonvision/60330985958c/medium.jpg alt=测试 /]
改版了啊,我的破ie6,很不适应啊,我该升级了。
@河海浪子
嗯,目前只兼容到IE7
额,这也算来过两回了
汗,看了半天不懂得怎么调用??
@亿品元素
调用就底部那句直接输出函数啊
想请教一个楼主,具体是哪一句调用输出的哦,研究了一晚都没研究出来呢
@问号鱼 ,
<?php online();?>@winy ,再次请教楼主,在xml文件里的unix时间戳那里为什么用上了还是没有像你最新来访一样转换成具体的时间呢?
@问号鱼 ,那是因为我用了一个转换相对时间的php函数:参考下面
function time_since($older_date, $newer_date = false){$chunks = array(array(60 * 60 , '小时'),array(60 , '分钟'),);
$newer_date = ($newer_date == false) ? (time()+(60*60*get_settings("gmt_offset"))) : $newer_date;
$since = $newer_date - $older_date;
if($since<86400 and $since>60){
for ($i = 0, $j = count($chunks); $i < $j; $i++){
$seconds = $chunks[$i][0];
$name = $chunks[$i][1];
if (($count = floor($since / $seconds)) != 0){
break;}}
$output = "$count{$name}";
if ($i + 1 < $j){
$seconds2 = $chunks[$i + 1][0];
$name2 = $chunks[$i + 1][1];
if (($count2 = floor(($since - ($seconds * $count)) / $seconds2)) != 0){
$output .= " $count2{$name2}";}}
return $output." 前";}
elseif($since<60 and $since=60){
return "1 分钟 之内";}
else{return strftime ("%y %m-%d %R" ,$older_date);;
}}
@winy ,
谢谢楼主解答,另外请问楼主这段代码是放在哪里的?我放在function.php处貌似没转换成功呢
一个人显示两行发作了...
有加unset($Now,$FileName,$XML,$Items,$I,$s);,真的管用咩?
@MOPVHS ,原来是重复写入~~