Kategorien
Webdesign

Mit PHP CSV lesen und HTML-Tabellen erzeugen

Kurz und bündig…

<?php
 
// Konfiguration
$csvFile = "daten.csv";
$firstRowHeader = true;
$maxRows = 10;
 
// Daten auslesen und Tabelle generieren
$handle = fopen($csvFile, "r");
$counter = 0;
echo "<table class=\"csvTable\">";
while(($data = fgetcsv($handle, 999, ";")) && ($counter < $maxRows)) {
 
  echo "<tr>";
  if(($counter == 0) && $firstRowHeader) {
    echo "<th>".$data[0]."</th>";
    echo "<th>".$data[1]."</th>";
    echo "<th>".$data[2]."</th>";
  }
  else {
    echo "<td>".$data[0]."</td>";
    echo "<td>".$data[1]."</td>";
    echo "<td>".$data[2]."</td>";
  }
  echo "</tr>";
 
  $counter++;
}
echo "</table>"; 
 
fclose($handle);
 
?>
Kategorien
Webdesign

SQL: Duplikate mit Anzahl ausgeben

Ausgabe aller Duplikate (einer Spalte) und deren Anzahl per SQL ermitteln.

SELECT Spalte, (COUNT(*)-1) AS Anzahl
FROM Tabelle
GROUP BY Spalte
HAVING COUNT(*)>1
ORDER BY COUNT(*) DESC;
Spalte Anzahl
A. Müller 5
B. Schneider 2
W. Weber 1
Kategorien
Webdesign

Einfacher Spamschutz für E-Mail-Adressen

Einfacher aber effektiver Spamschutz für E-Mail-Adressen mit Javascript und jQuery.
Ist JavaScript deaktiviert, erscheint nur info [at] domain.com.

<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript">

$(function(){
  $('.email').each(function(index) {
    var s = $(this).text().replace(" [at] ", "&#64;");
    $(this).html("<a href=\"mailto:" + s + "\">" + s + "</a>");
  });
});

</script>

Aus: info [at] domain.com
wird: info@domain.com

Im Quelltext die E-Mail-Adressen in span-Tags mit der Klasse „email“ setzen:
<span class=“email“>info [at] domain.com</span>

D.h. alle Elemente mit der Klasse „email“ werden in les- und klickbare E-Mail-Adressen umgewandelt.

Ohne jQuery könnte es z.B. so aussehen:

<script type="text/javascript">

function convertMailAddress() {
  var emailElements;
  if (document.getElementsByClassName)
    emailElements = document.getElementsByClassName("email");
  else
    emailElements = document.getElementsByClassNameForOldies("email");
  var elementContent, replaceContent;
  for (var i=0; i<emailElements.length; i++) {
    elementContent = emailElements[i].innerHTML;
    replaceContent = elementContent.replace(" [at] ", "&#64;");
    emailElements[i].innerHTML =
      "<a href=\"mailto:" + replaceContent + "\">" + replaceContent + "</a>";
  }
}

// http://javascript.about.com/library/bldom08.htm
document.getElementsByClassNameForOldies = function(cl) {
  var retnode = [];
  var myclass = new RegExp('\\b'+cl+'\\b');
  var elem = this.getElementsByTagName('*');
  for (var i = 0; i < elem.length; i++) {
    var classes = elem[i].className;
    if (myclass.test(classes)) retnode.push(elem[i]);
  }
  return retnode;
};

window.onload = convertMailAddress;

</script>

 

 

Kategorien
Webdesign

WordPress Plugins beim Einsatz als CMS

WordPress eignet sich für kleine, einfache Websites auch ganz gut als CMS. Es ist schnell eingerichtet, bietet viele Erweiterungen und ganz wichtig – der Kunde findet sich sehr schnell zurecht. Oft habe ich sogar nur am Telefon „geschult“.
Grundlage ist immer ein einfaches CMS-Template. Artikel, Kommentare usw. – alles was nicht gebraucht wird ist deaktiviert.

Neben den bekannten z.B. Kontaktformular-Plugins, kommt man aber um ein paar weitere nicht herum (ich zumindest), weil WordPress in der Version 2.9.2 das (noch) nicht bietet.

Page Links To
Leitet einen Menüpunkt, was ja einer Seite entspricht, auf eine beliebige URL um.
http://wordpress.org/extend/plugins/page-links-to

Exclude Pages
Versteckt Menüpunkte in der Navigation.
http://wordpress.org/extend/plugins/exclude-pages

Breadcrumb NavXT
Fügt eine „Brotkrummen-Navigation“ ein, mit vielen Einstellungsmöglichkeiten.
http://wordpress.org/extend/plugins/breadcrumb-navxt

TinyMCE Advanced
Erweitert den Standard-Editor TinyMCE um etliche Funktionen.
http://wordpress.org/extend/plugins/tinymce-advanced

Google XML Sitemaps
Stellt eine Sitemap für Suchmaschinen zur Verfügung.
http://wordpress.org/extend/plugins/google-sitemap-generator

Kategorien
Webdesign

Mehrsprachige Websites kodieren

Ich musste mal ein PHP-Frameworks für englische, russische, chinesische und arabische Inhalte entwickeln. Im Internet findet sich dazu auch eine Vielzahl von Artikeln, über die „richtige“ Kodierung von mehrsprachigen Websites. Wie lassen sich also z.B. kyrillische, chinesische oder auch arabische Zeichen korrekt darstellen. Leider widersprechen sich manche der Tipps.

Daher nun meine Vorgehendweise (getestet auf PC, MAC, Linux mit jeweils unterschiedlichen Browsern):

  • Erst mal muss eine Schrift mit entsprechende Zeichenumfang installiert sein (z.B. Arial Unicode)
  • Mit einem UTF-8-fähigen Editor arbeiten (sollen die Meisten können)
  • Alle Dateien als UTF-8 ohne BOM kodieren
  • Tag-Attribute im HTML-Head entsprechend anpassen, hier z.B. für arabisch:
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ar" lang="ar" dir="rtl">
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

notepad
Code-Ausschnitt als Beispiel

notepad-format
Einstellungen zum Format im Freeware-Editor Notepad++

Mehr Infos dazu:

Unicode Open-Source-Editor Nodepad++
http://notepad-plus.sourceforge.net/

Infos zu UTF-8
http://de.wikipedia.org/wiki/UTF-8

Infos zu BOM (Byte Order Mark)
http://de.wikipedia.org/wiki/Byte_Order_Mark

Grundlagen der Zeichenkodierung
http://toscho.de/2008/grundlagen-zeichenkodierung/

Kategorien
Webdesign

Harmonische Farben finden

Hier ein paar Online-Tools zum Zusammenstellen harmonischer Farben:

Kategorien
Webdesign

ASP.NET: Twitter Feeds per XmlDataSource- und Repeater-Control in Websites einbinden

RSS- bzw. Atom-Feeds von Twitter, Blogs usw. lassen sich sehr einfach mit dem XmlDataSource-Control in die eigene Website einbinden. Dazu ist quasi keine einzige Zeile „richtiger“ Code notwendig, sonder lediglich zwei ASP.NET-Controls.

Das Beispiel bezieht sich explizit auf einen Twitter Atom-Feed, lässt sich aber an jeden beliebigen anderen Feed anpassen. Wichtig: Immer genau die XML-Struktur des Feeds über die Quelltextansicht anschauen. Bei Twitter sieht das z.B. so aus:

<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">
  <channel>
    <title>Twitter / unckel</title>
    <link>http://twitter.com/unckel</link>
    <atom:link type="application/rss+xml" href="http://twitter.com/statuses/user_timeline/23050865.rss" rel="self"/>
    <description>Twitter updates from unckel designworks / unckel.</description>
    <language>en-us</language>
    <ttl>40</ttl>
  <item>
    <title>unckel: tweet tweet!</title>
    <description>unckel: tweet tweet!</description>
    <pubDate>Wed, 18 Nov 2009 07:45:26 +0000</pubDate>
    <guid>http://twitter.com/unckel/statuses/5821036943</guid>
    <link>http://twitter.com/unckel/statuses/5821036943</link>
  </item>
  <item>
    ... usw ...
  </item>
  </channel>
</rss>

Wichtig ist hier also der Inhalt der <items> und das wären insbesondere <title>, <pubDate> und <link>.

<asp:XmlDataSource ID="XmlDataSource1" runat="server" 
	DataFile="http://twitter.com/statuses/user_timeline/23050865.rss"
	XPath="rss/channel/item" EnableCaching="false" />

<asp:Repeater ID="Repeater1" runat="server" DataSourceID="XmlDataSource1">
<ItemTemplate>
	<a href="<%# XPath("link") %>"><%# XPath("title") %></a><br />
	<%# XPath("pubDate") %><br />
	<hr />
</ItemTemplate>
</asp:Repeater>
Kategorien
Webdesign

ASP.NET: Einfache Log-Datei schreiben

Muss mal schnell was mitgeloggt werden, bietet sich z.B. der StreamWriter an.

using System.IO;
...
string fileName = String.Format("log-{0}.txt", DateTime.Now.ToString("yyyy-MM-dd"));
string dataRow = String.Format("{0}; {1}; {2}", DateTime.Now, var1, var2);

StreamWriter myFile = new StreamWriter(Server.MapPath("~/App_Data/" + fileName), true);
myFile.WriteLine(dataRow);
myFile.Close();
Kategorien
Webdesign

ASP.NET: Canonical-Link-Tag dynamisch anpassen und einfügen

Doppelte Inhalte mögen Suchmaschinen bekanntermaßen nicht. Doch meistens können Webseiten über http://domain.de und http://www.domain.de erreicht werden. Für die Suchmaschine sind das zwei unterschiedliche Dinge.

Ein recht einfacher Ansatz mit ASP.NET kann so aussehen:

// using System.Web.UI.HtmlControls;

HtmlLink canonicalLink = new HtmlLink();
canonicalLink.Attributes["rel"] = "canonical";
canonicalLink.Href = Request.Url.AbsoluteUri.Replace("www.", "");
Page.Header.Controls.Add(canonicalLink);

Das ganze kommt dann z.B. in den Event-Handler Page_Load (Master-Datei, Basisklasse, …). Es wird dann im HTML-Head der Seite das entsprechende Tag erzeugt:
<link rel=“canonical“ href=“http://domain.de/site.aspx“ />

Über Request.Url.AbsoluteUri wird die aktuelle URL samt Host und Parametern ermittelt und per Replace(„www.“, „“) einfach, sofern vorhanden, das „www.“ entfernt. Aber Vorsicht: Alle Fundstellen mit „www.“ werden entfernt! Also auch etwaige übergebenen Parameter > d.h bei Bedarf nachbessern.

Alternativ kann aber auch per 301-Redirect in der global.asax umgeleitet werden.
Das könnte dann wie folgt aussehen:

<%@ Application Language="C#" %>
<script runat="server">
void Application_BeginRequest(object sender, EventArgs e)
{
  string url = HttpContext.Current.Request.Url.ToString().ToLower();
  
  if (!url.StartsWith("http://domain.de"))
  {
    // alle auf .de leiten
    url = url.Replace("domain.net", "domain.de");
    url = url.Replace("domain.com", "domain.de");
  
    // "www." entfernen
    url = url.Replace("http://www.domain", "http://domain");

    // permanente (301) Umleitung
    HttpContext.Current.Response.Status = "301 Moved Permanently";
    HttpContext.Current.Response.AddHeader("Location", url);
  }
}
</script>

Hier wird jeden Anfrage geprüft und ggf. auf die bevorzugte Domain per 301 umgeleitet – sprich das „www.“ einfach entfernt.

Kategorien
Webdesign

ASP.NET: Telefonliste mit Initiale per Repeater auflisten

Hier mal ein Quick ’n‘ Dirty-Ansatz einer Telefonliste mit Initialen.

.aspx

<asp:Repeater ID="Repeater1" runat="server">
  <HeaderTemplate>
    <table>
  </HeaderTemplate>
  <ItemTemplate>
    <%#SetInitial(Eval("Nachname").ToString())%>
    <tr>
      <td><a href="profil.aspx?ID=<%#Eval("ID")%>">
        <%#Eval("Nachname")%>, <%#Eval("Vorname")%></a></td>
      <td><%#Eval("Telefon")%></td>
      <td><%#Eval("EMail")%></td>
    </tr>
  </ItemTemplate>
  <FooterTemplate>
    </table>
  </FooterTemplate>
</asp:Repeater>

.aspx.cs

// C#
private char initialOld;

public string SetInitial(string lastName)
{
  char initial = Convert.ToChar(lastName.Substring(0, 1).ToUpper());

  if (initial == 'Ä') initial = 'A'; // Umlaute werden unter den
  if (initial == 'Ü') initial = 'U'; // dazugehörigen Vokaln gelisten
  if (initial == 'Ö') initial = 'O';

  if (initialOld != initial)
  {
    initialOld = initial;
    return string.Format(@"
     <tr>
       <td colspan=""3"">
         <span class=""initial""><br/>&nbsp;<br/>{0}</span>
         <a name=""i{1}""></a><span><a href=""#top"">zum Index</a></span>
         <hr />
       </td>
     </tr>", initial, initial);
  }
  else
  {
    return null;
  }
}