OSDN Git Service

NP_PubMed v 0.2.0
[nucleus-jp/nucleus-plugins.git] / NP_PubMed / trunk / pubmed / template.php
1 <?php\r
2 \r
3 class PUBMED_TEMPLATE_BASE {\r
4         /*\r
5          * This class must be inhelited by PUBMED_TEMPLATE class.\r
6          * Note that PHP 5 is needed.\r
7          */\r
8         /* \r
9          * Default methods follow.\r
10          * These methods will be overrided in PUBMED_TEMPLATE class.\r
11          */\r
12         public function manualSort(){\r
13                 // If the order of manuscript is manually sorted (PNAS etc),\r
14                 // this method must return true.\r
15                 return false;\r
16         }\r
17         public function sortPapers(){\r
18                 $this->sortByAuthorName();\r
19         }\r
20         public function parse_header(){\r
21                 return '<br />';\r
22         }\r
23         public function parse_footer(){\r
24                 return '<br />';\r
25         }\r
26         public function parse($num,$pmid,$xml,$authors,$year,$journal,$volume,$pages,$title){\r
27                 return <<<END\r
28 \r
29 <p>{$this->parse_authors($authors)} ({$year})<br />\r
30 <i>{$journal}</i> <b>{$volume}</b>, {$pages}<br />\r
31 {$title}</p>\r
32 \r
33 END;\r
34         }\r
35         public function parse_authors($authors, $and=', and '){\r
36                 $num=count($authors);\r
37                 switch($num){\r
38                         case 1:\r
39                                 $result=$this->parse_author($authors[0]);\r
40                                 break;\r
41                         case 2:\r
42                                 $result=$this->parse_author($authors[0]).$and.$this->parse_author($authors[1]);\r
43                                 break;\r
44                         default:\r
45                                 $result=$this->parse_author($authors[0]);\r
46                                 for($i=1;$i<$num;$i++){\r
47                                         if ($i==1) $result.=', ';\r
48                                         elseif ($i==$num-1) $result.=$and;\r
49                                         $result.=$this->parse_author($authors[$i]);\r
50                                 }\r
51                                 break;\r
52                 }\r
53                 return htmlspecialchars($result);\r
54         }\r
55         public function parse_author($author){\r
56                 $result=$author->LastName.', ';\r
57                 $initials=$author->Initials;\r
58                 for($i=0;$i<strlen($initials);$i++) $result.=substr($initials,$i,1).'.';\r
59                 return $result;\r
60         }\r
61         /*\r
62          * Following methods shouldn't be overrided.\r
63          */\r
64         protected $sortdata=array(),$data=array();\r
65         public static final function getTemplate($template){\r
66                 // Static method.\r
67                 // Define PUBLED_TEMPLATE class\r
68                 if (!preg_match('/^[a-z0-9A-Z_]+$/',$template)) exit('Bad template name!');\r
69                 $file=dirname(__FILE__)."/templates/{$template}.php";\r
70                 if (!file_exists($file)) return false;\r
71                 require_once($file);\r
72                 $obj = new PUBMED_TEMPLATE;\r
73                 return $obj;\r
74         }\r
75         public final function setData($more,$sort){\r
76                 // $more is the $item->more.\r
77                 if (!preg_match('#<MedlineCitation[^>]*>([\s\S]*?)</MedlineCitation>#',$more,$m)) return;\r
78                 $xml="<?xml version='1.0'?>\r\n<document>\r\n$m[1]\r\n</document>";\r
79                 $xml=simplexml_load_string($xml);\r
80                 $pmid=(int)$xml->PMID;\r
81                 $this->data[$pmid]=$xml;\r
82                 if (!isset($this->sortdata[$sort])) $this->sortdata[$sort]=$pmid;\r
83                 else $this->sortdata[]=$pmid;\r
84         }\r
85         public final function parse_all(){\r
86                 echo $this->parse_header();\r
87                 $num=0;\r
88                 $sortdata=$this->sortdata;\r
89                 ksort($sortdata);\r
90                 foreach($sortdata as $pmid) {\r
91                         $xml=$this->data[$pmid];\r
92                         $num++;\r
93                         // Get year\r
94                         $year=$xml->Article->Journal->JournalIssue->PubDate->Year;\r
95                         // Get journal name\r
96                         $journal=$xml->Article->Journal->ISOAbbreviation;\r
97                         // Get volume\r
98                         $volume=$xml->Article->Journal->JournalIssue->Volume;\r
99                         // Get paper title\r
100                         $title=$xml->Article->ArticleTitle;\r
101                         if (substr($title,-1,1)!=='.') $title.='.';\r
102                         // Get the start and end pages\r
103                         $pages=explode('-',(string)$xml->Article->Pagination->MedlinePgn);\r
104                         $pages=$pages[0].'-'.substr($pages[0],0,strlen($pages[0])-strlen($pages[1])).$pages[1];\r
105                         // Let's parse the citation\r
106                         echo $this->parse( (int)$num,(int)$pmid,$xml,$xml->Article->AuthorList->Author\r
107                                 ,htmlspecialchars($year) // Don't use (int) because it may be like 2008a\r
108                                 ,htmlspecialchars($journal)\r
109                                 ,(int)$volume\r
110                                 ,htmlspecialchars($pages)\r
111                                 ,htmlspecialchars($title)\r
112                                 );\r
113                 }\r
114                 echo $this->parse_footer();\r
115         }\r
116         /* Sort methods follow.\r
117          * note that these methods will be called from "sortPapers" method\r
118          */\r
119         public final function sortByAuthorName(){\r
120                 $citations=array();\r
121                 $papers=array();\r
122                 $i=0;\r
123                 foreach($this->data as $pmid=>&$xml){\r
124                         $i++;\r
125                         // Get date\r
126                         $year=(int)$xml->Article->Journal->JournalIssue->PubDate->Year;\r
127                         $month=(string)$xml->Article->Journal->JournalIssue->PubDate->Month;\r
128                         $month=$this->month($month);\r
129                         $month=$month<10 ? "0$month" : "$month";\r
130                         $day=(int)$xml->Article->Journal->JournalIssue->PubDate->Day;\r
131                         $day=$day<10 ? "0$day" : "$day";\r
132                         $date="$year-$month-$day";\r
133                         // Get Authors\r
134                         $authors=$xml->Article->AuthorList->Author;\r
135                         $firstauthor=$authors[0]->LastName.', '.$authors[0]->Initials;\r
136                         $authornum=count($authors);\r
137                         switch($authornum){\r
138                                 case 1:\r
139                                         $citation=$authors[0]->LastName.", $year";\r
140                                         break;\r
141                                 case 2:\r
142                                         $citation=$authors[0]->LastName.' and '.$authors[1]->LastName.", $year";\r
143                                         break;\r
144                                 default:\r
145                                         $citation=$authors[0]->LastName." et al., $year";\r
146                                         break;\r
147                         }\r
148                         if (!isset($citations[$citation])) $citations[$citation]=array();\r
149                         $citations[$citation][]=$pmid;\r
150                         // Construct the sort key and cache data\r
151                         $key="$firstauthor $year $citation $date $i";\r
152                         $papers[$key]=$pmid;\r
153                 }\r
154                 // Modify Year (for example, 2008 => 2008a, 2008b, etc.\r
155                 $abc='abcdefghijklmnopqrstuvwxyz';\r
156                 foreach($citations as $key=>$value){\r
157                         if (count($value)<2) continue;\r
158                         for ($i=0;$i<count($value);$i++){\r
159                                 $pmid=$value[$i];\r
160                                 $year=(int)$this->data[$pmid]->Article->Journal->JournalIssue->PubDate->Year;\r
161                                 $this->data[$pmid]->Article->Journal->JournalIssue->PubDate->Year=(string)$year.substr($abc,$i,1);\r
162                         }\r
163                 }\r
164                 // Sort the data\r
165                 ksort($papers);\r
166                 // Let's get the result.\r
167                 $result=array();\r
168                 foreach($papers as $pmid) $result[]=$pmid;\r
169                 $this->sortdata=$result;\r
170         }\r
171         protected final function month($month){\r
172                 if (is_numeric($month)) return (int)$month;\r
173                 switch(strtolower($month)){\r
174                         case 'january':\r
175                         case 'jan': return 1;\r
176                         case 'february':\r
177                         case 'feb': return 2;\r
178                         case 'march':\r
179                         case 'mar': return 3;\r
180                         case 'april':\r
181                         case 'apr': return 4;\r
182                         case 'may': return 5;\r
183                         case 'june':\r
184                         case 'jun': return 6;\r
185                         case 'july':\r
186                         case 'jul': return 7;\r
187                         case 'august':\r
188                         case 'aug': return 8;\r
189                         case 'september':\r
190                         case 'sep': return 9;\r
191                         case 'october':\r
192                         case 'oct': return 10;\r
193                         case 'november':\r
194                         case 'nov': return 11;\r
195                         case 'december':\r
196                         case 'dec': return 12;\r
197                         default: return 0;\r
198                 }\r
199         }\r
200         \r
201 }