Index: /trunk/admin/batch_manager.php
===================================================================
--- /trunk/admin/batch_manager.php	(revision 17764)
+++ /trunk/admin/batch_manager.php	(revision 17765)
@@ -115,4 +115,11 @@
       );
   }
+  
+  if (substr_compare($_GET['cat'],'tag-',0,4)==0)
+  {
+    $_SESSION['bulk_manager_filter']=array();
+    $_SESSION['bulk_manager_filter']['tags'] = array(intval(substr($_GET['cat'],4)));
+    $_SESSION['bulk_manager_filter']['tag_mode'] = 'AND';
+  }
 }
 
Index: /trunk/admin/batch_manager_unit.php
===================================================================
--- /trunk/admin/batch_manager_unit.php	(revision 17764)
+++ /trunk/admin/batch_manager_unit.php	(revision 17765)
@@ -181,7 +181,4 @@
     );
   $template->assign(array('navbar' => $nav_bar));
-
-  // tags
-  $all_tags = get_all_tags();
 
   $element_ids = array();
Index: /trunk/admin/include/functions.php
===================================================================
--- /trunk/admin/include/functions.php	(revision 17764)
+++ /trunk/admin/include/functions.php	(revision 17765)
@@ -1206,5 +1206,5 @@
     return array('error' => l10n('The name of an album must not be empty'));
   }
-    
+
   $insert = array(
     'name' => $category_name,
@@ -1475,9 +1475,12 @@
     }
 
-    mass_inserts(
-      IMAGE_TAG_TABLE,
-      array_keys($inserts[0]),
-      $inserts
-      );
+    if (count($inserts))
+    {
+      mass_inserts(
+        IMAGE_TAG_TABLE,
+        array_keys($inserts[0]),
+        $inserts
+        );
+    }
   }
 }
@@ -1499,5 +1502,5 @@
     return false;
   }
-  
+
   // get existing associations
   $query = '
@@ -1510,5 +1513,5 @@
 ;';
   $result = pwg_query($query);
-  
+
   $existing = array();
   while ($row = pwg_db_fetch_assoc($result))
@@ -2120,36 +2123,44 @@
 
   $taglist = array();
+  $altlist = array();
   while ($row = pwg_db_fetch_assoc($result))
   {
-    if (!$only_user_language and preg_match_all('#\[lang=(.*?)\](.*?)\[/lang\]#is', $row['name'], $matches))
-    {
-      foreach ($matches[2] as $tag_name)
+    $raw_name = $row['name'];
+    $name = trigger_event('render_tag_name', $raw_name);
+
+    $taglist[] =  array(
+        'name' => $name,
+        'id' => '~~'.$row['id'].'~~',
+      );
+
+    if (!$only_user_language)
+    {
+      $alt_names = trigger_event('get_tag_alt_names', array(), $raw_name);
+
+      // TEMP 2.4
+      if (count($alt_names)==0 and preg_match_all('#\[lang=(.*?)\](.*?)\[/lang\]#is', $row['name'], $matches))
       {
-        array_push(
-          $taglist,
-          array(
-            'name' => trigger_event('render_tag_name', $tag_name),
+        foreach ($matches[2] as $alt)
+        {
+          $alt_names[] = $alt;
+        }
+      }
+
+      foreach( array_diff( array_unique($alt_names), array($name) ) as $alt)
+      {
+        $altlist[] =  array(
+            'name' => $alt,
             'id' => '~~'.$row['id'].'~~',
-            )
           );
       }
-
-      $row['name'] = preg_replace('#\[lang=(.*?)\](.*?)\[/lang\]#is', null, $row['name']);
-    }
-
-    if (strlen($row['name']) > 0)
-    {
-      array_push(
-        $taglist,
-        array(
-          'name' => trigger_event('render_tag_name', $row['name']),
-          'id' => '~~'.$row['id'].'~~',
-          )
-        );
-    }
-  }
-
-  $cmp = create_function('$a,$b', 'return strcasecmp($a["name"], $b["name"]);');
-  usort($taglist, $cmp);
+    }
+  }
+
+  usort($taglist, 'tag_alpha_compare');
+  if (count($altlist))
+  {
+    usort($altlist, 'tag_alpha_compare');
+    $taglist = array_merge($taglist, $altlist);
+  }
 
   return $taglist;
Index: /trunk/admin/tags.php
===================================================================
--- /trunk/admin/tags.php	(revision 17764)
+++ /trunk/admin/tags.php	(revision 17765)
@@ -46,5 +46,5 @@
 ;';
   $existing_names = array_from_query($query, 'name');
-  
+
 
   $current_name_of = array();
@@ -59,5 +59,5 @@
     $current_name_of[ $row['id'] ] = $row['name'];
   }
-  
+
   $updates = array();
   // we must not rename tag with an already existing name
@@ -111,5 +111,5 @@
 ;';
   $existing_names = array_from_query($query, 'name');
-  
+
 
   $current_name_of = array();
@@ -124,5 +124,5 @@
     $current_name_of[ $row['id'] ] = $row['name'];
   }
-  
+
   $updates = array();
   // we must not rename tag with an already existing name
@@ -180,5 +180,5 @@
             );
         }
-  
+
         if (count($inserts) > 0)
         {
@@ -227,5 +227,5 @@
     $destination_tag_id = $_POST['destination_tag'];
     $tag_ids = explode(',', $_POST['merge_list']);
-    
+
     if (is_array($tag_ids) and count($tag_ids) > 1)
     {
@@ -243,5 +243,5 @@
         $name_of_tag[ $row['id'] ] = trigger_event('render_tag_name', $row['name']);
       }
-      
+
       $tag_ids_to_delete = array_diff(
         $tag_ids,
@@ -298,5 +298,5 @@
         $tags_deleted[] = $name_of_tag[$tag_id];
       }
-      
+
       array_push(
         $page['infos'],
@@ -326,9 +326,9 @@
 
   delete_tags($_POST['tags']);
-  
+
   array_push(
     $page['infos'],
     l10n_dec(
-      'The following tag was deleted', 
+      'The following tag was deleted',
       'The %d following tags were deleted',
       count($tag_names)).' : '.
@@ -344,5 +344,5 @@
 {
   check_pwg_token();
-  
+
   delete_orphan_tags();
   $_SESSION['page_infos'] = array(l10n('Orphan tags deleted'));
@@ -378,5 +378,5 @@
         )
       );
-    
+
     array_push(
       $page['infos'],
@@ -441,10 +441,42 @@
 // +-----------------------------------------------------------------------+
 
+
+// tag counters
+$query = '
+SELECT tag_id, COUNT(image_id) AS counter
+  FROM '.IMAGE_TAG_TABLE.'
+  GROUP BY tag_id';
+$tag_counters = simple_hash_from_query($query, 'tag_id', 'counter');
+
+// all tags
+$query = '
+SELECT *
+  FROM '.TAGS_TABLE.'
+;';
+$result = pwg_query($query);
+$all_tags = array();
+while ($tag = pwg_db_fetch_assoc($result))
+{
+  $raw_name = $tag['name'];
+  $tag['name'] = trigger_event('render_tag_name', $raw_name);
+  $tag['counter'] = intval(@$tag_counters[ $tag['id'] ]);
+  $tag['U_VIEW'] = make_index_url(array('tags'=>array($tag)));
+  $tag['U_EDIT'] = 'admin.php?page=batch_manager&amp;cat=tag-'.$tag['id'];
+
+  $alt_names = trigger_event('get_tag_alt_names', array(), $raw_name);
+  $alt_names = array_diff( array_unique($alt_names), array($tag['name']) );
+  if (count($alt_names))
+  {
+    $tag['alt_names'] = implode(', ', $alt_names);
+  }
+  $all_tags[] = $tag;
+}
+usort($all_tags, 'tag_alpha_compare');
+
+
+
 $template->assign(
   array(
-    'TAG_SELECTION' => get_html_tag_selection(
-      get_all_tags(),
-      'tags'
-      ),
+    'all_tags' => $all_tags,
     )
   );
@@ -461,5 +493,5 @@
     $list_name = 'MERGE_TAGS_LIST';
   }
-  
+
   $template->assign(
     array(
Index: /trunk/admin/themes/default/template/tags.tpl
===================================================================
--- /trunk/admin/themes/default/template/tags.tpl	(revision 17764)
+++ /trunk/admin/themes/default/template/tags.tpl	(revision 17765)
@@ -41,5 +41,5 @@
       <tr>
         <td>{$tag.NAME}</td>
-        <td><input type="text" name="tag_name-{$tag.ID}" value="{$tag.NAME}" size="30"></td>
+        <td><input type="text" name="tag_name-{$tag.ID}" value="{$tag.NAME}" size="50"></td>
       </tr>
       {/foreach}
@@ -65,5 +65,5 @@
       <tr>
         <td>{$tag.NAME}</td>
-        <td><input type="text" name="tag_name-{$tag.ID}" value="{$tag.NAME}" size="30"></td>
+        <td><input type="text" name="tag_name-{$tag.ID}" value="{$tag.NAME}" size="50"></td>
       </tr>
       {/foreach}
@@ -96,5 +96,5 @@
     <label>
       {'New tag'|@translate}
-      <input type="text" name="add_tag" size="30">
+      <input type="text" name="add_tag" size="50">
     </label>
     
@@ -104,6 +104,27 @@
   <fieldset>
     <legend>{'Tag selection'|@translate}</legend>
-    
-    {$TAG_SELECTION}
+{html_style}
+.showInfo{ldelim}position:static; display:inline-block; text-indent:6px}
+{/html_style}
+{footer_script}{literal}
+jQuery('.showInfo').tipTip({
+    'delay' : 0,
+    'fadeIn' : 200,
+    'fadeOut' : 200,
+    'maxWidth':'300px',
+    'keepAlive':true,
+    'activation':'click'
+  });
+{/literal}{/footer_script}
+<ul class="tagSelection">
+{foreach from=$all_tags item=tag}
+	<li>{capture name='showInfo'}<b>{$tag.name}</b><br>{$pwg->l10n_dec('%d photo', '%d photos', $tag.counter)} <a href="{$tag.U_VIEW}">{'View'|@translate}</a> <a href="{$tag.U_EDIT}">{'Edit'|@translate}</a>{if !empty($tag.alt_names)}<br>{$tag.alt_names}{/if}{/capture}
+		<a class="showInfo" title="{$smarty.capture.showInfo|@htmlspecialchars}">i</a>
+		<label>
+			<input type="checkbox" name="tags[]" value="{$tag.id}"> {$tag.name}
+		</label>
+	</li>
+{/foreach}
+</ul>
 
     <p>
