<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Athlan • Piotr Pelczar • blog programisty</title>
	<atom:link href="http://athlan.pl/feed/" rel="self" type="application/rss+xml" />
	<link>http://athlan.pl</link>
	<description>Napisać kod zrozumiały dla komputera potrafi byle głupek. Dobrzy programiści tworzą kod zrozumiały dla człowieka...</description>
	<lastBuildDate>Sat, 17 Jul 2010 18:54:07 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0</generator>
		<item>
		<title>MySQL DATE() dla pola DATETIME</title>
		<link>http://athlan.pl/mysql-date-function-datetime/</link>
		<comments>http://athlan.pl/mysql-date-function-datetime/#comments</comments>
		<pubDate>Sat, 17 Jul 2010 10:04:39 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Databases]]></category>
		<category><![CDATA[Optymalizacja]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[Przemyślenia]]></category>
		<category><![CDATA[SQL]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=472</guid>
		<description><![CDATA[Oblicza MySQL nie są do końca znane przy tworzeniu aplikacji, a problemy optymalizacyjne stają się nie lada problemem przy funkcjonowaniu wersji produkcyjnej projektu. Nie sposób przewidzieć wszystkich możliwości użycia pól, założenia zarówno wspólnych, jak i pojedynczych indeksów posiadających zakładaną przez nas moc i zajętą pamięć na dysku. Ostatnimi czasy budowałem dość skomplikowany projekt, jeżeli chodzi [...]]]></description>
			<content:encoded><![CDATA[<p>Oblicza <strong>MySQL</strong> nie są do końca znane przy tworzeniu aplikacji, a problemy optymalizacyjne stają się nie lada problemem przy funkcjonowaniu wersji produkcyjnej projektu. Nie sposób przewidzieć wszystkich możliwości użycia pól, założenia zarówno wspólnych, jak i pojedynczych indeksów posiadających zakładaną przez nas moc i zajętą pamięć na dysku.</p>
<p>Ostatnimi czasy budowałem dość skomplikowany projekt, jeżeli chodzi o złożoność zapytań i wykonywanych przez nie operacje matematyczne. Pomimo tego, że aplikacja była doskonale przemyślana, a struktury bazy danych perfekcyjnie jej podporządkowane, gdzieś tkwił problem, bowiem jedno z zapytań generowało pozornie prosty (wizualnie) rezultat, baza reagowała na zapytanie dopiero po 2.5 sekundy dla 30k+ rekordów. Patrząc na strukturę kluczy i zapytania, zwłaszcza, że pola, na których operowałem były różnego rodzaju liczbami i datami zacząłem się poważnie martwić i rozkładać zapytanie na czynniki pierwsze, kończąc na warunkach. Wyobraźcie sobie moje zdziwienie, gdy doszedłem do tego, że całe obciążenie (ponad 2.3 sekundy) generował warunek:</p>

<div class="wp_syntax"><div class="code"><pre class="mysql" style="font-family:monospace;"><span style="color: #990099; font-weight: bold;">WHERE</span> <span style="color: #000099;">DATE</span><span style="color: #FF00FF;">&#40;</span>ticket_date<span style="color: #FF00FF;">&#41;</span> <span style="color: #CC0099;">&gt;=</span> <span style="color: #008000;">&quot; ... &quot;</span></pre></div></div>

<p>Gdzie ticket_date to pole typu <strong>DATETIME</strong>. Od razu doszedłem do wniosku, że w parze idzie złe przygotowanie danych przez PHP, a angażowana jest w to wszystko baza, na której forsuje się użycie funkcji <strong>DATE()</strong>. Przynajmniej dla 30k+ rekordów zindeksowanego pola. Prosty zabieg zamiany jednej linijki kodu na drugą przyniósł porządane efekty.</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000088;">$aTerms</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #0000ff;">'DATE(ticket_date) &gt;= &quot;'</span> <span style="color: #339933;">.</span> <span style="color: #000088;">$sDate</span> <span style="color: #339933;">.</span> <span style="color: #0000ff;">'&quot;'</span></pre></div></div>


<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000088;">$aTerms</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #0000ff;">'ticket_date &gt;= &quot;'</span> <span style="color: #339933;">.</span> <span style="color: #990000;">date</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'Y-m-d H:i:s'</span><span style="color: #339933;">,</span> <span style="color: #990000;">strtotime</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$sDate</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">.</span> <span style="color: #0000ff;">'&quot;'</span></pre></div></div>

<p>Budując aplikację zwracam szczególną uwagę na strukturę bazy, indeksowanie pól, rysuję diagramy przewidujące wykorzystanie danych pod różne zapytania, ale&#8230; tak banalny błąd przy przeanalizowanej aplikacji rozłożył mnie na łopatki. Z drugiej strony, zapomniałem o jednej bardzo ważnej rzeczy: maksymalnym odciążeniu bazy danych przy preparowaniu argumentów warunków, skoro warunki te mogą być w odpowiedni i przede wszystkim szybki sposób spreparowane na poziomie modelu (abstrakcyjnie rzecz ujmując, pozbywam się pojęcia PHP), który przygotują zapytanie tylko do wykonania operacji na surowych danych, bez konieczności ich ewentualnego przeliczania. Oczywiście nie zawsze taki efekt da się uzyskać, ale należy to maksymalnie <strong>optymalizować</strong>.</p>
<p>Jedno jest wiadome: przeliczanie DATE() dla rekordów w warunku jest nieoptymalne dla pola DATETIME.</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/mysql-date-function-datetime/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		</item>
		<item>
		<title>jQuery Animate i Easing</title>
		<link>http://athlan.pl/jquery-animate-i-easing/</link>
		<comments>http://athlan.pl/jquery-animate-i-easing/#comments</comments>
		<pubDate>Sat, 08 May 2010 08:17:41 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[CSS]]></category>
		<category><![CDATA[Internet]]></category>
		<category><![CDATA[JS/Ajax]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[Publikacje]]></category>
		<category><![CDATA[Solutions]]></category>
		<category><![CDATA[XHTML]]></category>
		<category><![CDATA[jQuery]]></category>
		<category><![CDATA[interface]]></category>
		<category><![CDATA[javascript]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=457</guid>
		<description><![CDATA[Nie można kwestionować faktu, że jQuery.animate() jest jednym z najbardziej potężnych narzędzi jQuery. Służy on do animowania atrybutów CSS (czyli zmiany ich wartości w czasie od obecnego stanu A do definiowanego stanu B). Najprostszą implementacją jQuery Animate jest podanie zbioru atrybutów CSS, które mają ulec zmianie oraz czasu, w jakim ta zmiana ma nastąpić. Nie będę się [...]]]></description>
			<content:encoded><![CDATA[<p>Nie można kwestionować faktu, że <code><a href="http://api.jquery.com/animate/">jQuery.animate()</a></code> jest jednym z najbardziej potężnych narzędzi <strong>jQuery</strong>. Służy on do animowania <strong>atrybutów CSS</strong> (czyli zmiany ich wartości w czasie od obecnego stanu A do definiowanego stanu B). Najprostszą implementacją <strong>jQuery Animate</strong> jest podanie zbioru atrybutów CSS, które mają ulec zmianie oraz czasu, w jakim ta zmiana ma nastąpić. Nie będę się zagłębiał w najprostsze przykłady użycia, <a rel="nofollow" href="http://api.jquery.com/animate/">są one dostępne w oficjalnej dokumentacji</a> jQuery.</p>
<p>Należy pamiętać, że dzięki jQuery jesteśmy w stanie nie tylko płynnie zmieniać kolory, wielkość czcionki, obramowanie, ale także pozycje elementów, nadając stronie dynamicznego kształtu. Domyślnym sposobem animowania (<em>easing</em>) jest płynne przechodzenie. Istnieje natomiast sposób na zmianę adaptera animowania. Robert Penner &#8211; autor pluginu <a rel="nofollow" href="http://gsgd.co.uk/sandbox/jquery/easing/"><strong>jQuery Easing</strong></a> dostarczył nam niewiarygodnie efektowne i proste w implementacji narzędzie. Na oficjalnej stronie pluginu można znaleźć <a rel="nofollow" href="http://gsgd.co.uk/sandbox/jquery/easing/">wiele przykładów animacji</a>, które dostarcza nam dodatek. Efekty widoczne są zwłaszcza przy animowaniu pozycji i wymiarów obiektu, ale następują także w przypadku zmiany koloru &#8211; czyli są aplikowane do zmiany stanu każdego z atrybutów CSS.</p>
<p>Dziś postaram się pokazać efekty, jakie można uzyskać za pomocą <strong>jQuery Animate</strong> rozszerzonego o <strong>jQuery Interface</strong> oraz <strong>Easing</strong>.</p>
<ul>
<li><a href="http://athlan.pl/code/jQueryAnimateEasing/">Przykład różnego rodzaju easingu</a>.</li>
</ul>
<p>Pierwszym krokiem jest wygenerowanie własnej biblioteki <a href="http://jqueryui.com/download">jQuery Interface</a>. Dzięki generatorowi, jesteśmy w stanie ściągnąć tylko te części Interface, które są nam de facto potrzebne, zmniejszając jednocześnie ilość kodu. Klikamy &#8216;deselect all components&#8217;, a w sekcji <em>Effects</em> wybieramy efekty, których będziemy używać. Mnie w tej chwili interesuje <em>Bounce</em> i <em>Slide</em>. W paczce otrzymamy wersję deweloperską (z wcięciami) oraz <em>minified</em>, gotową do publikacji na serwerze.</p>
<p>Do wykorzystania efektu slideowania a&#8217;la iPhone (elastyczne odbicie od krawędzi ściany ekranu) sprowadza się drobny kawałek kodu, w którym istotnym jest parametr <em>easing</em>:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'#example'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">animate</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span> left<span style="color: #339933;">:</span> <span style="color: #CC0000;">500</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> <span style="color: #009900;">&#123;</span> duration<span style="color: #339933;">:</span> <span style="color: #CC0000;">1000</span><span style="color: #339933;">,</span> easing<span style="color: #339933;">:</span> <span style="color: #3366CC;">'easeOutElastic'</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>Na pewno komuś się przyda.</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/jquery-animate-i-easing/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Chmura tagów Tagcloud w PHP</title>
		<link>http://athlan.pl/chmura-tagow-tagcloud-php/</link>
		<comments>http://athlan.pl/chmura-tagow-tagcloud-php/#comments</comments>
		<pubDate>Sun, 07 Mar 2010 19:12:21 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Internet]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[Publikacje]]></category>
		<category><![CDATA[Solutions]]></category>
		<category><![CDATA[mysql]]></category>
		<category><![CDATA[tagcloud]]></category>
		<category><![CDATA[tagi]]></category>
		<category><![CDATA[tags]]></category>
		<category><![CDATA[web2.0]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=439</guid>
		<description><![CDATA[Ostatnio byłem zobligowany napisać nową klasę tagów do mojego projektu Sypacz.pl, która de facto zachowała stare API, lecz rozszerzyła swoje funkcjonalności, więc w kodzie projektu nie było wielu zmian. Wena spowodowała to, że zacząłem pisać kod od zera. Cały problem polega na tym, aby napisać na tyle elastyczną klasę tagów, która przyjmie nam zestaw danych, [...]]]></description>
			<content:encoded><![CDATA[<p>Ostatnio byłem zobligowany napisać nową klasę tagów do mojego projektu <a href="http://sypacz.pl">Sypacz.pl</a>, która de facto zachowała stare API, lecz rozszerzyła swoje funkcjonalności, więc w kodzie projektu nie było wielu zmian. Wena spowodowała to, że zacząłem pisać kod od zera.</p>
<p>Cały problem polega na tym, aby napisać na tyle elastyczną klasę tagów, która przyjmie nam zestaw danych, a następnie zaprezentować ją w formie chmury, czym zaopiekuje się arkusz stylów CSS:</p>
<p><code>Nazwa tagu => Ilość występowań</code></p>
<p>Parę osób mnie pytało, jak wyciągnąć takie informacje z bazy danych:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;">SELECT tag_name<span style="color: #339933;">,</span> <span style="color: #990000;">COUNT</span><span style="color: #009900;">&#40;</span>tag_name<span style="color: #009900;">&#41;</span> <span style="color: #b1b100;">AS</span> tag_times FROM tags GROUP BY tag_name ORDER BY tag_times LIMIT <span style="color: #cc66cc;">1</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">50</span></pre></div></div>

<p>Wykorzystałem obiekt <a href="http://athlan.pl/code/Attribute.Class">Vframe_Attribute</a>, aby ustandaryzować komponent względem pozostałych w moim frameworku. Jeżeli ktoś nie chce używać obiektu Attribute, może w prosty sposób przekształcić klasę tagów, otrzymując ten sam efekt, deklarując tylko atrybut chroniony <code>protected $_aAttributes = array();</code>. Temat chmury tagów wydaje mi się na tyle trywialny, że nie ma się co nad nim zbyt wiele rozwodzić, zamieszczę tylko klasę i opiszę krótko w przykładach jej możliwości.</p>
<ul>
<li><a href="http://athlan.pl/code/Tagcloud.Class">Vframe_Tagcloud</a> &#8211; klasa tagów,</li>
<li><a href="http://athlan.pl/code/Attribute.Class"> Vframe_Attribute</a> &#8211; pomocnicza klasa atrybutów dla stosu $_aAttributes, dziedziczenie można usunąć i zadeklarować atrybut samemu.</li>
</ul>
<p>Aby stworzyć nowy obiekt tagów, po prostu wywołujemy konstruktor:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000088;">$oCloud</span> <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Vframe_Tagcloud<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Konstruktor nie przyjmuje żadnych argumentów, wiec możemy od razu przejść do podawania obiektowi tagów. W tym miejscu warto nadmienić, że każdy znak jest rozróżniany (ze względów elastycznych), więc jeżeli chcesz, aby Nazwatagu oraz nazwatagu były rozpoznawane jako jeden klucz, wypadałoby użyć funkcji <a href="http://php.net/strtolower">strtolower</a> lub <a href="http://php.net/mb_strtolower">mb_strtolower</a> (dla Multibyte Strings):</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #b1b100;">foreach</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aDataTags</span> <span style="color: #b1b100;">as</span> <span style="color: #000088;">$iKey</span> <span style="color: #339933;">=&gt;</span> <span style="color: #000088;">$aRow</span><span style="color: #009900;">&#41;</span>
  <span style="color: #000088;">$oCloud</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">add</span><span style="color: #009900;">&#40;</span><span style="color: #990000;">strtolower</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aRow</span><span style="color: #009900;">&#91;</span><span style="color: #0000ff;">'tag_name'</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #000088;">$aRow</span><span style="color: #009900;">&#91;</span><span style="color: #0000ff;">'tag_times'</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Najistotniejszą częścią klasy jest sposób renderowania chmury, które może działać w dwóch trybach:</p>
<ul>
<li><strong>Tryb prosty</strong> zwraca nam nazwę tagu oraz jego wagę po przeliczeniu w formie liczby.</li>
<li><strong>Tryb zaawansowany</strong> zwraca nam nazwę tagu oraz tablicę z danymi:
<ul>
<li><code>level</code> &#8211; waga tagu po przeliczeniu,</li>
<li><code>count</code> &#8211; ilość występowań, taka jaką podaliśmy,</li>
<li><code>count_percentage</code> &#8211; informacja, w jakiej procentowej części ilości występowań znajduje się tag, przyjmując za 100% tag, który występuje najczęściej.</li>
</ul>
</li>
</ul>
<p>Aby w prosty sposób wyrenderować chmurę tagów, używamy poniższego przykładu:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000088;">$aDataTagsRender</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$oCloud</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">render</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Najczęściej używa się trybu prostego. Oba tryby są dalej rozbudowane, bowiem <strong>mamy możliwość zdefiniowania zakresu i dokładności wag tagów</strong>. <u>Domyślnie wagi tagów zawierają się pomiędzy 1, a 10</u>. Możemy na przykład przyjąć, że najmniejszą wagą jest liczba 3, największą 5, a precyzja wag tagów to 2 miejsca po przecinku:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000088;">$aDataTagsRender</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$oCloud</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">render</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">3</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">5</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>W celu uniknięcia precyzji po przecinku (chcemy otrzymać liczby całkowite), ustawimy precyzję na 0.</p>
<p>Aby wywołać tryb zaawansowany, musimy podać 4 argument dla metody <code>render()</code> i ustawić go na <code>true</code>.</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000088;">$aDataTagsRender</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$oCloud</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">render</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">1</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">5</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">,</span> <span style="color: #009900; font-weight: bold;">true</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Warto w tym miejscu nadmienić, że tagi mogą nie być posortowane alfabetycznie (co ma miejsce podczas tworzenia chmury tagów). Wystarczy wywołać funkcję <code>ksort</code> (key sort).</p>
<p>Finalny przykład używania klasy tagów, celem wywołania klas CSS level_X, gdzie X to liczba całkowita z zakresu od 1 do 10, resztę robi CSS (kolorowanie, nakładanie rozmiaru):</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #b1b100;">if</span><span style="color: #009900;">&#40;</span><span style="color: #990000;">count</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aDataTags</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
&nbsp;
<span style="color: #000088;">$oCloud</span> <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> Vframe_Tagcloud<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #b1b100;">foreach</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aDataTags</span> <span style="color: #b1b100;">as</span> <span style="color: #000088;">$iKey</span> <span style="color: #339933;">=&gt;</span> <span style="color: #000088;">$aRow</span><span style="color: #009900;">&#41;</span>
  <span style="color: #000088;">$oCloud</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">add</span><span style="color: #009900;">&#40;</span><span style="color: #990000;">strtolower</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aRow</span><span style="color: #009900;">&#91;</span><span style="color: #0000ff;">'tag_name'</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #000088;">$aRow</span><span style="color: #009900;">&#91;</span><span style="color: #0000ff;">'tag_times'</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000088;">$aDataTags</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$oCloud</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">render</span><span style="color: #009900;">&#40;</span><span style="color: #cc66cc;">1</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">10</span><span style="color: #339933;">,</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #990000;">ksort</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aDataTags</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #b1b100;">foreach</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$aDataTags</span> <span style="color: #b1b100;">as</span> <span style="color: #000088;">$sTag</span> <span style="color: #339933;">=&gt;</span> <span style="color: #000088;">$iTag</span><span style="color: #009900;">&#41;</span>
  <span style="color: #b1b100;">echo</span> <span style="color: #0000ff;">'&lt;a href=&quot;'</span> <span style="color: #339933;">.</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">route</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'tag'</span><span style="color: #339933;">,</span> <span style="color: #000088;">$sTag</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">.</span> <span style="color: #0000ff;">'&quot; class=&quot;level_'</span> <span style="color: #339933;">.</span> <span style="color: #000088;">$iTag</span> <span style="color: #339933;">.</span> <span style="color: #0000ff;">'&quot;&gt;'</span> <span style="color: #339933;">.</span> <span style="color: #000088;">$sTag</span> <span style="color: #339933;">.</span> <span style="color: #0000ff;">'&lt;/a&gt;'</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></div></div>

]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/chmura-tagow-tagcloud-php/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Recenzja iPhone 3G</title>
		<link>http://athlan.pl/recenzja-iphone-3g/</link>
		<comments>http://athlan.pl/recenzja-iphone-3g/#comments</comments>
		<pubDate>Sun, 17 Jan 2010 10:02:27 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Apple]]></category>
		<category><![CDATA[Internet]]></category>
		<category><![CDATA[Recenzje]]></category>
		<category><![CDATA[iPhone]]></category>
		<category><![CDATA[iTunes]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=413</guid>
		<description><![CDATA[Po trzech miesiącach użytkowania, jestem w stanie napisać konstruktywną recenzję iPhone 3G. Na samym w stępie chciałbym zaznaczyć, że urządzenie jest warte swojej ceny. Moja opinia nie jest w żaden sposób zdeterminowana ślepą miłością do marki Apple. Nie będę się tu rozwodził nad wyglądem, jest to indywidualna sprawa każdego użytkownika telefonu &#8211; dla mnie iPhone [...]]]></description>
			<content:encoded><![CDATA[<p>Po trzech miesiącach użytkowania, jestem w stanie napisać konstruktywną recenzję <strong>iPhone 3G</strong>.</p>
<p>Na samym w stępie chciałbym zaznaczyć, że urządzenie jest warte swojej ceny. Moja opinia nie jest w żaden sposób zdeterminowana ślepą miłością do marki <strong>Apple</strong>. Nie będę się tu rozwodził nad wyglądem, jest to indywidualna sprawa każdego użytkownika telefonu &#8211; dla mnie iPhone ma po prostu elegancki wygląd. Urządzenie wyposażone jest w 4 przyciski: blokowanie telefonu, home button (powrót), wyciszenie i sterowanie poziomem głośności &#8211; klawiaturę zastępuje ekran dotykowy. Warto nadmienić, że pojawia się ona tylko wtedy, gdy jest potrzebna. Telefon ma bardzo czuły ekran z obsługą multi-touch. Wbudowana funkcja auto-jasności pozwala oszczędzać baterię w miejscach ciemnych &#8211; polega to na redukcji oświetlenia ekranu w mroku, gdyż ludzkie oko doskonale widzi, co dzieje się wokół, a rozświetlony (jak za dnia) ekran telefonu powodował by irytację (jak w urządzeniach starszej generacji).</p>
<h4>Zwykłe użytkowanie urządzenia jako telefon</h4>
<p><a href="http://athlan.pl/wp-content/uploads/iphone-springboard.png"><img class="alignright size-full wp-image-428" title="iphone-springboard" src="http://athlan.pl/wp-content/uploads/iphone-springboard.png" alt="" width="250" height="375" /></a>Produkty Apple charakteryzują się dużą intuicyjnością interfejsu. Telefon podzielony jest na dwie zasadnicze części: Text messages (SMS) i telefon. Obie &#8220;aplikacje&#8221; zintegrowane są z komponentem kontaktów, który jest de facto ogólnodostępny dla innych aplikacji (twórcy telefonu podeszli do tej kwestii bardzo ideologicznie). Zasadniczym brakiem w oprogramowaniu jest brak raportów doręczenia SMS, ale można to obejść crackując telefon, o czym później. Dodatkowym minusem jest długie ładowanie się listy SMS przy jej większej ilości, co również można obejść crackując telefon, o czym również później : -). Kolejnym minusem jest to, że wszystkie kontakty przechowywane są w pamięci telefonu, a nie na karcie SIM, co gorsza &#8211; nie ma możliwości eksportu kontaktów na kartę SIM, a jedynie istnieje możliwość importu. Nie ma się czego obawiać &#8211; przy każdej synchronizacji iPhone z iTunes, kontakty zapisywane są w backupie.</p>
<h4>Telefon z niezniszczalnym software</h4>
<p>Zdarzyło mi się &#8220;popsuć&#8221; oprogramowanie iPhone instalując nieautoryzowane przez Apple oprogramowanie na własną odpowiedzialność. Przywrócenie telefonu do stanu używalności? Nic prostszego &#8211; instalujemy nowy software na iPhone via iTunes i klikamy przycisk Restore &#8211; wybieramy nasz backup i gotowe. Wszystkie kontakty, SMS&#8217;y, save&#8217;y z gier, aplikacje, muzyka widnieją z powrotem na ekranie naszego telefonu.</p>
<h4>Urządzenie przyjazne użytkownikowi</h4>
<p>Wyobraź sobie, że słuchasz muzyki, masz telefon w kieszeni, jest zimno. Musisz ściągnąć rękawiczki, wyciągnąć telefon, włączyć odtwarzacz muzyki, wejść  playlistę, kliknąć next, schować telefon, założyć rękawiczki. Nie ma się czym zachwycać, bo rozwiązania te zostały już zaimplementowane z poprzednich telefonach, ale Apple nie zapomniało o przycisku kontrolnym w zestawie słuchawkowym. Pomijając to, że wygląda elegancko, pozwala nam na odebranie/odrzucenie rozmowy i kontrolę iPod&#8217;a (play/pause &#8211; single click, next &#8211; double click, previous &#8211; tripple click).</p>
<p>Wcześniej wspomniałem o ekranie dostosowującym się do warunków oświetlenia. Gdy jest ciemno &#8211; ekran ciemnieje, bo nasze oko akomoduje się do otoczenia, oszczędzamy tym samym baterię. Gdy przykładamy telefon do ucha, ekran wygasza się, aby uniknąć przypadkowych kliknięć w ekran dotykając go uchem &#8211; tutaj również oszczędzamy baterię.</p>
<p><a href="http://athlan.pl/wp-content/uploads/iphone-ipod-cover.png"></a><a href="http://athlan.pl/wp-content/uploads/iphone-sms.png"><img class="alignright" title="iphone-sms" src="http://athlan.pl/wp-content/uploads/iphone-sms.png" alt="" width="250" height="167" /></a>Szybka edycja danych &#8211; na liście wystarczy wykonać gest przeciągnięcia palca w prawą stronę i pojawi nam się przycisk usunięcia go ze stosu &#8211; genialne. Pomyliłeś się pisząc SMS? Potrząśnij telefonem, a iPhone zaproponuje Ci wprowadzenie korekty. Niewygodnie pisze Ci się SMS&#8217;a? Przechyl iPhone na bok, a dostaniesz do dyspozycji większa klawiaturę i większy obszar pola tekstowego. Trzymasz iPhone w ręku i słuchasz muzyki? Potrząśnij telefonem, a zmieni się track. Chcesz przeglądnąć swoje albumy z iPodzie? przechyl telefon, a wyświetlą Ci się okładki, które dodałeś w iTunes.</p>
<p style="text-align: center;"><a href="http://athlan.pl/wp-content/uploads/iphone-ipod-cover.png"><img class="aligncenter" title="iphone-ipod-cover" src="http://athlan.pl/wp-content/uploads/iphone-ipod-cover.png" alt="" width="480" height="320" /></a></p>
<p>Szukanie w całym telefonie &#8211; kolejna opcja, która pomaga mi szybko dostać się do interesujących mnie rzeczy. Jedno pole wyszukiwania odpowiada za wyniki z: aplikacji, kontaktów, maili, sms&#8217;ów, tracków, artystów i albumów z iPod&#8217;a.</p>
<p>Nie ukrywajmy &#8211; Apple dostarcza nam masę aplikacji, z czego wiele jest darmowych. Co więcej, nasz telefon stara się utrzymać całe oprogramowanie w najnowszej wersji. Z telefonu możemy zrobić nawet zwykłą latarkę (której nie ma w urządzeniu) &#8211; aplikacja rozjaśnia ekran i pokrywa go białym kolorem. Nie wspominam już o masie gier serwowanych przez AppStore za darmo!</p>
<div style="text-align: center;"><a href="http://athlan.pl/wp-content/uploads/iphone-appstore.png"><img title="iphone-appstore" src="http://athlan.pl/wp-content/uploads/iphone-appstore.png" alt="" width="250" height="375" /></a> <a href="http://athlan.pl/wp-content/uploads/iphone-games.png"><img class="alignnone size-full wp-image-430" title="iphone-games" src="http://athlan.pl/wp-content/uploads/iphone-games.png" alt="" width="250" height="375" /></a></div>
<p>Przeglądanie Internetu nie było dla mnie prostsze &#8211; wbudowana przeglądarka Safari z obsługą kart i schowka jest idealnym narzędziem do surfowania po Sieci. Player YouTube również spełnia moje oczekiwania. Jeżeli jesteś społecznikiem &#8211; zintegruj swój telefon z Blip&#8217;em, Twitter&#8217;em, Flaker&#8217;em, Facebook&#8217;iem, importuj swoje ulubione kanały RSS, dodaj konta pocztowe i zainstaluj Parlingo &#8211; komunikator z obsługą sieci Gadu-Gadu, Jabbera, ICQ, AOL, Google Talk, MSN i innych.</p>
<h4>Nieautoryzowane oprogramowanie na iPhone &#8211; Jailbreak</h4>
<p><a href="http://athlan.pl/wp-content/uploads/iphone-jailbreak.png"><img class="alignright size-full wp-image-432" title="iphone-jailbreak" src="http://athlan.pl/wp-content/uploads/iphone-jailbreak.png" alt="" width="250" height="375" /></a>Jest wielu zwolenników crackowania oprogramowania iPhone, jest też wielu przeciwników. Moje stanowisko w tej sprawie &#8211; crackować. Co nam to daje? Wcześniej opisałem wiele nieudogodnień, które możemy poprawić w oprogramowaniu, np:</p>
<ul>
<li>raporty SMS są dostępne w Cydii pod nazwą iDelivery,</li>
<li>możemy wyłączyć przycisk automatycznej sekretarki w telefonie, który może nam się zdarzać przypadkowo kliknąć,</li>
<li>mamy możliwość pobierania filmików z YouTube&#8217;a za pomocą MXTube,</li>
<li>możemy scrobblować piosenki przesłuchiwane w iPodzie do last.fm za pomocą Scrobbl,</li>
<li>mamy możliwość zainstalowania kamerki, standardowo niedostępnej w iPhone &#8211; Cycorder,</li>
<li>odblokowanie nowych theme jest teraz możliwe &#8211; Winterboard,</li>
<li>dostosowanie telefonu, wyłączenie EDGE, wyłączanie niepotrzebnych ikonek w Springboard (typu giełda) &#8211; BossPrefs.</li>
</ul>
<p>I na koniec cały smaczek łamania oprogramowania:</p>
<h4>Czyli&#8230; telefon mi &#8216;zamula&#8217;</h4>
<p>Długie ładowanie SMS&#8217;ów, kontaktów, kalkulatora lub alarmów? Zcrackuj swój telefon i zainstaluj Backgrounder z pakietów Cydii. Pozwala on na działanie niektórych aplikacji &#8220;w tle&#8221;. Niektóre możemy ustawić jako automatycznie pracujące w trybie niewidocznym, innym nie pozwolić na taką opcję. Ile razy zdarzyło Ci się przerwać grę, gdy chciałeś odczytać SMS? Przytrzymaj Home button, gra schowa się do paska, odpisz na SMS&#8217;a i ponownie kliknij na ikonkę gry &#8211; powrócisz do stanu pierwotnego, a nie (jak w legalnym oprogramowaniu) proces zostanie całkowicie zakończony. Analogicznie sprawa wygląda w przypadku korzystania z komunikatora (np. Parlingo). Aby wyjść z trybu background, ponownie przytrzymaj Home button. Przycisk wprowadzania aplikacji w stan niewidoczny można skonfigurować indywidualnie, może to być np. Power button (Home jest chyba najwygodniejszy).</p>
<p>Dyskusja na temat działania aplikacji w tle jest burzliwa &#8211; pamiętajmy jednak, że crackując software narażamy się na nieoptymalne działanie telefonu i szybkie zużycie baterii, za co Apple nie odpowiada.</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/recenzja-iphone-3g/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>How to change iPhone`s SSH password</title>
		<link>http://athlan.pl/how-to-change-iphone-ssh-password/</link>
		<comments>http://athlan.pl/how-to-change-iphone-ssh-password/#comments</comments>
		<pubDate>Mon, 09 Nov 2009 12:47:39 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Apple]]></category>
		<category><![CDATA[iPhone]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=395</guid>
		<description><![CDATA[Jak zmienić hasło SSH w iPhone? Ostatnimi czasy jest głośno o pierwszym znanym robaku na iPhone. Na szczęście jest on nieszkodliwy, ale pokazuje, na co narażeni są użytkownicy instalujący nieautoryzowane przez Apple aplikacje na swoim telefonie. Jak zabezpieczyć iPhone&#8217;a? Dla tych, którzy mieli wcześniej styczność z Linux&#8217;em lub OSX to norma, lecz warto przypomnieć pozostałym o [...]]]></description>
			<content:encoded><![CDATA[<h1>Jak zmienić hasło SSH w iPhone?</h1>
<p>Ostatnimi czasy jest <a rel="nofollow" href="http://www.myapple.pl/news/121195-masz-iphonea-z-jailbreakiem-uwazaj-na-robaki.html">głośno</a> o pierwszym znanym robaku na iPhone. Na szczęście jest on nieszkodliwy, ale pokazuje, na co narażeni są użytkownicy instalujący nieautoryzowane przez Apple aplikacje na swoim telefonie. <strong>Jak zabezpieczyć iPhone&#8217;a? </strong>Dla tych, którzy mieli wcześniej styczność z Linux&#8217;em lub OSX to norma, lecz warto przypomnieć pozostałym o zmianie hasła <em>root</em>&#8216;a.</p>
<p style="padding-left: 30px; ">Z reguły SSH służy do zdalnego logowania się do urządzenia poprzez sieć. Połączenie jest szyfrowane, a technologia znana i uważana za bezpieczną, lecz nic nie stanie na przeszkodzie hakerowi, który po prostu zna hasło…</p>
<p>Aby spać spokojniej, możemy zmienić hasło dostępu do SSH. Aby to uczynić, wyszukujemy w <strong>Cydia</strong> paczkę o nazwie <strong>MobileTerminal</strong>. Po instalacji pojawi nam się dodatkowa ikona reprezentująca terminal. Włączamy aplikację, w której domyślnie jesteśmy zalogowani na użytkownika <em>mobile</em>, zmieniamy hasło:</p>
<pre>passwd</pre>
<p>System poprosi nas o podanie aktualnego hasła, które brzmi <em>alpine</em>. Wpisujemy nowy kod oraz potwierdzamy jego poprawność.</p>
<p>Wiele ludzi zapomina, że istnieje również użytkownik root. Mu także należy zmienić hasło. Aby przełączyć się na użytkownika <em>root</em>, wpisujemy:</p>
<pre>su root</pre>
<p>Podajemy hasło <em>alpine</em> oraz analogicznie zmieniamy nasz sekretny kod dla tego użytkownika. Ekran końcowy powinien wyglądać mniej więcej tak:</p>
<p><a href="http://athlan.pl/wp-content/uploads/iPhoneSSHpasswd.png"><img class="aligncenter size-full wp-image-396" title="iPhoneSSHpasswd" src="http://athlan.pl/wp-content/uploads/iPhoneSSHpasswd.png" alt="iPhoneSSHpasswd" width="320" height="480" /></a></p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/how-to-change-iphone-ssh-password/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>How to create iPhone ringtone from mp3</title>
		<link>http://athlan.pl/how-to-create-iphone-ringtone-from-mp3/</link>
		<comments>http://athlan.pl/how-to-create-iphone-ringtone-from-mp3/#comments</comments>
		<pubDate>Sat, 31 Oct 2009 10:48:24 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Apple]]></category>
		<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[iPhone]]></category>
		<category><![CDATA[iTunes]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=389</guid>
		<description><![CDATA[Jak zrobić dzwonek iPhone z mp3? 1. Włącz iTunes, przejdź do sekcji Music i wybierz utwór, który chcesz wykorzystać jako dzwonek. Jeżeli nie masz jeszcze swojej playlisty, możesz przeciągnąć plik na iTunes metodą drag&#8217;n'drop. 2. Kliknij prawym przyciskiem na wybrany utwór, z menu kontekstowego wybierz Get Info. W zakładkach okna znajdziesz sekcję Options. Po włączeniu [...]]]></description>
			<content:encoded><![CDATA[<p><strong>Jak zrobić dzwonek iPhone z mp3?</strong></p>
<p>1. Włącz <em><strong>iTunes</strong></em>, przejdź do sekcji <em>Music </em>i wybierz utwór, który chcesz wykorzystać jako dzwonek. Jeżeli nie masz jeszcze swojej playlisty, możesz przeciągnąć plik na iTunes metodą drag&#8217;n'drop.</p>
<p>2. Kliknij prawym przyciskiem na wybrany utwór, z menu kontekstowego wybierz <strong><em>Get Info</em></strong>. W zakładkach okna znajdziesz sekcję <strong><em>Options</em></strong>. Po włączeniu zakładki pojawią się parametry piosenki.</p>
<p>3. Zdecyduj, od którego momentu ma rozpocząć się Twój nowy dzwonek. W tym celu zaznacz pole <strong><em>Start Time</em></strong> i wprowadź czas w formacie MM:SS (minuty, sekundy). Jeżeli chcesz, aby dzwonek rozpoczynał się w od początku piosenki, ustaw czas na 0:00 lub odznacz pole Start Time. Pamiętaj, że możesz ustalać również dziesiętne, setne i milisekundy. Aby to uzyskać format czasu powinien wyglądać następująco MM:SS,X (minuty, sekundy, dziesiętna/setna/mili skunda), np.: 2:57,75 (czyli 2 minuty, 57 sekund i 3/4 sekundy).</p>
<p>4. Ustaw czas zakończenia dzwonka (<strong><em>Stop</em><span style="font-weight: normal;"> </span></strong><strong><em>Time</em></strong>) analogicznie do czasu jego rozpoczęcia. Pamiętaj, że Twój dzwonek może mieć maksymalnie 40 sekund.</p>
<p>5. Zapisz zmiany. Ponownie kliknij prawym przyciskiem na piosenkę, tym razem wybierz <strong><em>Create ACC version</em></strong>. Gdy proces konwersji pliku się zakończy, usłyszymy charakterystyczny dźwięk.</p>
<p>6. Ponownie klikamy prawym przyciskiem myszy na plik, wybieramy <strong><em>Show in Windows Exlorer</em></strong>. Jeżeli widzisz rozszerzenia plików, przejdź do kroku 8.</p>
<p>7. Kliknij <strong>Narzędzia </strong>-&gt; <strong>Opcje folderów</strong> -&gt; Zakładka: <strong>Widok</strong> -&gt; odznacz opcję <strong>Ukryj rozszerzenia znanych typów plików</strong>.</p>
<p>8. Zmień nazwę pliku, edytując rozszerzenie z <strong>m4a</strong> na <strong>m4r</strong>. Potwierdź zmianę rozszerzenia w ostrzeżeniu. Dwukrotnie kliknij w plik, po czym otworzy się on w iTunes.</p>
<p>9. W <strong><em>Devices </em></strong>wybierz swojego <strong>iPhone</strong>&#8216;a. Wybierz zakładkę <strong><em>Ringtones </em></strong>w podglądzie swojego telefonu. Zaznacz opcję <strong><em>Sync Ringtones</em></strong>.</p>
<p>10. Wykonaj synchronizację. W ustawieniach dźwięku powinien pojawić się Twój dzwonek.</p>
<p>Pamiętaj, żeby nie usuwać pliku dzwonka ze swojego komputera, przy ponownej synchronizacji zostanie on usunięty z naszego urządzenia.</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/how-to-create-iphone-ringtone-from-mp3/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Allegro nie zawsze wygodne</title>
		<link>http://athlan.pl/allegro-nie-zawsze-wygodne/</link>
		<comments>http://athlan.pl/allegro-nie-zawsze-wygodne/#comments</comments>
		<pubDate>Wed, 29 Jul 2009 23:51:57 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Internet]]></category>
		<category><![CDATA[Private]]></category>
		<category><![CDATA[Przemyślenia]]></category>
		<category><![CDATA[allegro]]></category>
		<category><![CDATA[aukcja]]></category>
		<category><![CDATA[aukcje]]></category>
		<category><![CDATA[oszustwo]]></category>
		<category><![CDATA[play station]]></category>
		<category><![CDATA[policja]]></category>
		<category><![CDATA[shopping]]></category>
		<category><![CDATA[zakupy]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=378</guid>
		<description><![CDATA[Jestem zwolennikiem ułatwiania sobie życia wykorzystując Internet do robienia zakupów i zarządzania swoim kapitałem. Natomiast po ostatniej akcji na Allegro, zacząłem wątpić w moje ograne ideały, uznaję to za ostrzeżenie i poprawiam markerem cienką linię pomiędzy realnym shoppingiem, a dokonywania zakupów via Allegro na znacznie grubszą. Zamiast kupić pada do Play Station 3 kiloma kliknięciami, musiałem [...]]]></description>
			<content:encoded><![CDATA[<p>Jestem zwolennikiem ułatwiania sobie życia wykorzystując <strong>Internet</strong> do robienia zakupów i zarządzania swoim kapitałem. Natomiast po ostatniej akcji na <strong>Allegro</strong>, zacząłem wątpić w moje ograne ideały, uznaję to za ostrzeżenie i poprawiam markerem cienką linię pomiędzy realnym shoppingiem, a dokonywania zakupów via Allegro na znacznie grubszą. Zamiast kupić pada do Play Station 3 kiloma kliknięciami, musiałem ruszać tyłek po kilku instytucjach.</p>
<p>Wszystko zaczęło się 25 czerwca, kiedy postanowiłem zakupić wcześniej wspominanego pada. Mam zwyczaj, że jeżeli jest opisana procedura płatności za przedmioty, a kontrahent jest <em>Super Sprzedawcą</em>, robię to od razu po dokonaniu zakupu &#8211; tak było i tym razem. System <a href="http://www.sello.pl/">Sello</a> wysłał mi potwierdzenie złożenia zamówienia.</p>
<p>Od 26.06 do 07.07 obserwowałem status wysyłki. Przelewu nie zaksięgowano po 13 dniach, stąd status wysyłki zakolorowany na czerwono. Sprawa zaczyna śmierdzieć, bowiem nie mogę się dodzwonić do kontrahenta (number busy), a gdy już mi się to udaje &#8211; nikt nie odbiera. Kilkukrotna próba kontaktu telefonicznego i mailowego pozostawiona bez odpowiedzi motywuje mnie, żeby&#8230;</p>
<p>09.07 wypełniłem wniosek w <strong>Centrum Sporów Allegro</strong>. Tego samego dnia wybrałem się na <strong>Policję</strong>, aby złożyć zawiadomienie o popełnieniu przestępstwa na tle wyłudzenia internetowego. Na komendzie czekałem około 40 minut zanim mnie przesłuchali, potem straciłem 30 minut na przesłuchanie i sporządzenie raportu.</p>
<p>Czas płynie i płynie&#8230;</p>
<p>27.07 &#8211; kontrahent dzwoni z wyjaśnieniami. &#8220;Okazało się&#8221;, że odwiedziła go Policja. Tłumaczenie: padła im baza klientów i zamówień, przez co nie mogli mnie zidentyfikować, pomimo szukania transakcji w historii sprzedaży na Allegro (przecież jest lista czarno na białym). Na moim koncie powinny być już zaksięgowane zwrócone pieniążki, ale niestety nie mogą wysłać mi mojego pada ze względu na to, że są zablokowani przez skarbówkę&#8230; muszą się rozliczyć. Za wszystko jeszcze raz przeprasza&#8230;</p>
<p>28.07 godz 11:00, telefon z Policji. Wezwanie na jutro, punkt 9 rano w pokoju numer 53. Sprawdzam konto, pieniążki są. Drukuję potwierdzenie zaksięgowania zwrotu jako załącznik do jutrzejszych zeznań.</p>
<p>29.07 godz 9:00 (wakacje są, daliby pospać). Zaniechujemy ściganie, dziękuję za pomoc. Kończę spór transakcyjny w panelu na Allegro i wystawiam negatywny komentarz:</p>
<blockquote><p>Towar nie dotarł do mnie do dziś. Po interwencji Policji sprawa się wyjaśniła. Natomiast nieuczciwym wobec innych użytkowników Allegro byłoby wystawienie poz. lub neut. komentarza za transakcję, która nie doszła do skutku. Miesiąc w plecy.</p></blockquote>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/allegro-nie-zawsze-wygodne/feed/</wfw:commentRss>
		<slash:comments>10</slash:comments>
		</item>
		<item>
		<title>MySQL: remove duplicate entries/rows</title>
		<link>http://athlan.pl/mysql-remove-duplicate/</link>
		<comments>http://athlan.pl/mysql-remove-duplicate/#comments</comments>
		<pubDate>Sun, 05 Jul 2009 08:02:04 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Databases]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[Publikacje]]></category>
		<category><![CDATA[SQL]]></category>
		<category><![CDATA[Solutions]]></category>
		<category><![CDATA[database]]></category>
		<category><![CDATA[delete]]></category>
		<category><![CDATA[duplicated]]></category>
		<category><![CDATA[mysql]]></category>
		<category><![CDATA[remove]]></category>
		<category><![CDATA[rows]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=332</guid>
		<description><![CDATA[Usuwając coś permanentnie z bazy danych musimy być bardzo ostrożni, bowiem przywrócenie danych jest bardzo trudne, czasem niemożliwe. Podstawową strukturę bazy danych powinno się budować na samym początku tworzenia aplikacji, z biegiem czasu rozbudowywać ją, ale unikać przebudowywania. Niestety są przypadki, gdzie trzeba przebudować jedną rzecz, co powoduje zmianę w wielu warstwach nie tyle aplikacji, [...]]]></description>
			<content:encoded><![CDATA[<p>Usuwając coś permanentnie z bazy danych musimy być bardzo ostrożni, bowiem przywrócenie danych jest bardzo trudne, czasem niemożliwe. Podstawową strukturę bazy danych powinno się budować na samym początku tworzenia aplikacji, z biegiem czasu rozbudowywać ją, ale unikać przebudowywania. Niestety są przypadki, gdzie trzeba przebudować jedną rzecz, co powoduje zmianę w wielu warstwach nie tyle aplikacji, co strukturze bazodanowej.</p>
<p>Dziś postaram się opisać, jakie kroki trzeba wykonać, aby bezpiecznie usunąć zdublowane rekordy z bazy danych nie tracąc żadnych danych:</p>
<ol>
<li>Tworzymy dwie <strong>kopie bazy danych</strong> lub tabel, na których będziemy pracowali. Najlepiej, aby pracować na drugiej kopii, nigdy na oryginale, a potem wdrożyć zmiany z drugiej kopii na oryginał. Przezorny zawsze ubezpieczony.</li>
<li>Analiza danych w tabeli. Musimy dokładnie wiedzieć jakie są relacje między tabelami, kiedy występują JOIN&#8217;y itp. Jeżeli rekordy są zdublowane, a posiadają ustalony ID, do których odwołuje się inny rekord z sąsiedniej tabeli, trzeba będzie w niej zmienić ID rekord zdublowanego na ID &#8220;substytuta&#8221;, bądź takiego rekordu, który nie spowoduje zmian w serwisie.</li>
<li>Wykonanie operacji <strong>usunięcia zdublowanych rekordów</strong>.</li>
</ol>
<p>Po wykonaniu kroku pierwszego zabieramy się za kolejny. Jest to najważniejszy moment naszych operacji. Aby ułatwić zrozumienie problemu, podam przykład z życia. Aplikacja posiadała poważny błąd, który umożliwiał zdublowanie użytkowników, ściślej: można było zdublować username. Za każdym razem, gdy użytkownik się logował i pisał komentarze, był ich właścicielem, ale comment_author posiadały różne ID tego samego użytkownika. Zaraz po skopiowaniu bazy danych spróbowałem przepisać ID autorów komentarzy na pierwszy rekord identyfikujący użytkownika, jaki istnieje w tabeli użytkowników. Skonstruowałem zapytanie:</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">UPDATE</span> cms_comments
<span style="color: #993333; font-weight: bold;">JOIN</span> cms_members <span style="color: #993333; font-weight: bold;">AS</span> user_original <span style="color: #993333; font-weight: bold;">ON</span><span style="color: #66cc66;">&#40;</span>user_original<span style="color: #66cc66;">.</span>user_id <span style="color: #66cc66;">=</span> comment_author<span style="color: #66cc66;">&#41;</span>
<span style="color: #993333; font-weight: bold;">SET</span> comment_author <span style="color: #66cc66;">=</span> <span style="color: #66cc66;">&#40;</span>
  <span style="color: #993333; font-weight: bold;">SELECT</span> user_first<span style="color: #66cc66;">.</span>user_id <span style="color: #993333; font-weight: bold;">FROM</span> cms_members <span style="color: #993333; font-weight: bold;">AS</span> user_first
  <span style="color: #993333; font-weight: bold;">WHERE</span> user_first<span style="color: #66cc66;">.</span>user_name <span style="color: #66cc66;">=</span> user_original<span style="color: #66cc66;">.</span>user_name
  <span style="color: #993333; font-weight: bold;">ORDER</span> <span style="color: #993333; font-weight: bold;">BY</span> user_first<span style="color: #66cc66;">.</span>user_id <span style="color: #993333; font-weight: bold;">ASC</span> <span style="color: #993333; font-weight: bold;">LIMIT</span> <span style="color: #cc66cc;">0</span><span style="color: #66cc66;">,</span> <span style="color: #cc66cc;">1</span><span style="color: #66cc66;">&#41;</span></pre></div></div>

<p>Usunięcie zdublowanych użytkowników było już tylko formalnością. Teraz się okaże, dlaczego zależało mi na wyciągnięciu dokładnie pierwszego rekordu reprezentującego &#8220;unikalnego&#8221; użytkownika: poniższe zapytanie (<strong>ALTER IGNORE TABLE ADD UNIQUE</strong>) usunie wszystkie kolejne rekordy oznaczone jako <strong>duplicated</strong>:</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">ALTER</span> <span style="color: #993333; font-weight: bold;">IGNORE</span> <span style="color: #993333; font-weight: bold;">TABLE</span> cms_members <span style="color: #993333; font-weight: bold;">ADD</span> <span style="color: #993333; font-weight: bold;">UNIQUE</span> <span style="color: #993333; font-weight: bold;">INDEX</span><span style="color: #66cc66;">&#40;</span>user_name<span style="color: #66cc66;">&#41;</span>;</pre></div></div>

<p>Krótki komentarz z manuala do <strong>ALTER TABLE</strong>:</p>
<blockquote><p><strong>IGNORE</strong> is a <span style="text-decoration: underline;">MySQL extension to standard SQL</span>. It controls how ALTER TABLE works if there are duplicates on unique keys in the new table or if warnings occur when strict mode is enabled. If IGNORE is not specified, the copy is aborted and rolled back if duplicate-key errors occur. If IGNORE is specified, <span style="text-decoration: underline;">only the first row is used of rows with duplicates on a unique key</span>, The other conflicting rows are deleted. Incorrect values are truncated to the closest matching acceptable value.</p></blockquote>
<p>Pisząc ostatnie posty związane z bazami danych, mam nadzieję, że komuś się przydadzą.</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/mysql-remove-duplicate/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Sesja fotograficzna &#8211; płyty winylowe</title>
		<link>http://athlan.pl/sesja-fotograficzna-plyty-winylowe/</link>
		<comments>http://athlan.pl/sesja-fotograficzna-plyty-winylowe/#comments</comments>
		<pubDate>Sat, 04 Jul 2009 23:03:54 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Fotografia]]></category>
		<category><![CDATA[Private]]></category>
		<category><![CDATA[Real live]]></category>
		<category><![CDATA[Zdjęcia]]></category>
		<category><![CDATA[nikon]]></category>
		<category><![CDATA[nikon D300]]></category>
		<category><![CDATA[sesja]]></category>
		<category><![CDATA[winyle]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=351</guid>
		<description><![CDATA[Dzieki uprzejmości Qiubag&#8216;a, miałem okazję być modelem do sesji winylowej. Z tego miejsca chciałbym zaprosić na jego blog fotograficzny. Fotografie wykonane były aparatem Nikon D300 i stałoogniskowym obiektywem 50mm o jasności 1.8. Używane były głównie przysłony f.7-f.8 ze względu na bardzo jasne otoczenie. Dodatkowo, tam gdzie była taka możliwość &#8211; dopalaliśmy zdjęcie lampą SB600 postawioną na [...]]]></description>
			<content:encoded><![CDATA[<p>Dzieki uprzejmości <strong>Qiubag</strong>&#8216;a, miałem okazję być modelem do sesji winylowej. Z tego miejsca chciałbym zaprosić na jego <a href="http://qiubag.com">blog fotograficzny</a>.</p>
<p>Fotografie wykonane były aparatem <strong>Nikon D300</strong> i stałoogniskowym obiektywem 50mm o jasności 1.8. Używane były głównie <strong>przysłony f.7-f.8</strong> ze względu na bardzo jasne otoczenie. Dodatkowo, tam gdzie była taka możliwość &#8211; dopalaliśmy zdjęcie lampą <strong>SB600</strong> postawioną na statywie &#8211; aby wypełnić ostre cienie (kontra). Postprocessing to tylko wywoływanie RAW-ów i delikatne kadrowanie.</p>

<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/1c/' title='Zapadł wyrok za nieszczerość... wybiła godzina zero!'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/1c-150x150.jpg" class="attachment-thumbnail" alt="Zapadł wyrok za nieszczerość... wybiła godzina zero!" title="Zapadł wyrok za nieszczerość... wybiła godzina zero!" /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/2c/' title='Są pewne wykorki, których nie można odroczyć!'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/2c-150x150.jpg" class="attachment-thumbnail" alt="Są pewne wykorki, których nie można odroczyć!" title="Są pewne wykorki, których nie można odroczyć!" /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/3c/' title='Pęknęła Hip-Hop&#039;u klisza.'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/3c-150x150.jpg" class="attachment-thumbnail" alt="Pęknęła Hip-Hop&#039;u klisza." title="Pęknęła Hip-Hop&#039;u klisza." /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/5c/' title='Minorum Gentium'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/5c-150x150.jpg" class="attachment-thumbnail" alt="Minorum Gentium" title="Minorum Gentium" /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/7c/' title='Płonie kolejny most, a ja mam frajdę!'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/7c-150x150.jpg" class="attachment-thumbnail" alt="Płonie kolejny most, a ja mam frajdę!" title="Płonie kolejny most, a ja mam frajdę!" /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/4c/' title='Wieją zachodnie wiatry, wieją zdradliwe wiry...'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/4c-150x150.jpg" class="attachment-thumbnail" alt="Wieją zachodnie wiatry, wieją zdradliwe wiry..." title="Wieją zachodnie wiatry, wieją zdradliwe wiry..." /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/6c/' title='Definicja Hip-hop.'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/6c-150x150.jpg" class="attachment-thumbnail" alt="Definicja Hip-hop." title="Definicja Hip-hop." /></a>
<a href='http://athlan.pl/sesja-fotograficzna-plyty-winylowe/8c/' title='Świat się kręci...'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/8c-150x150.jpg" class="attachment-thumbnail" alt="Świat się kręci..." title="Świat się kręci..." /></a>

]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/sesja-fotograficzna-plyty-winylowe/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>MySQL: how to convert NULL to 0 number/int</title>
		<link>http://athlan.pl/mysq-convert-null-to-0/</link>
		<comments>http://athlan.pl/mysq-convert-null-to-0/#comments</comments>
		<pubDate>Wed, 01 Jul 2009 23:24:57 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Databases]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[SQL]]></category>
		<category><![CDATA[Solutions]]></category>
		<category><![CDATA[mysql]]></category>
		<category><![CDATA[zero]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=321</guid>
		<description><![CDATA[Im więcej nietypowych rzeczy programuję, tym więcej nietypowych problemów musze pokonać. Co powiecie na sumę 2 liczb, z których jedna jest wartością NULL powstałą w wyniku działania SUM() lub pochodnych, gdzie nie odnaleziono żadnego rekordu. Badamy: SELECT 1+2+3 &#62;&#62; 6 SELECT 1+2+NULL &#62;&#62; NULL SELECT COALESCE( NULL, 0 ) &#62;&#62; 0 Zatem analogicznie do powyższego [...]]]></description>
			<content:encoded><![CDATA[<p>Im więcej nietypowych rzeczy programuję, tym więcej nietypowych problemów musze pokonać. Co powiecie na sumę 2 liczb, z których jedna jest wartością <strong>NULL</strong> powstałą w wyniku działania <strong>SUM()</strong> lub pochodnych, gdzie nie odnaleziono żadnego rekordu.</p>
<p>Badamy:</p>
<p><code>SELECT 1+2+3<br />
&gt;&gt; 6</code></p>
<p><code>SELECT 1+2+NULL<br />
&gt;&gt; NULL</code></p>
<p><code>SELECT COALESCE( NULL, 0 )<br />
&gt;&gt; 0</code></p>
<p>Zatem analogicznie do powyższego przykładu:</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">UPDATE</span> users <span style="color: #993333; font-weight: bold;">SET</span> user_points <span style="color: #66cc66;">=</span> user_points <span style="color: #66cc66;">+</span> COALESCE<span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#40;</span><span style="color: #993333; font-weight: bold;">SELECT</span> SUM<span style="color: #66cc66;">&#40;</span> <span style="color: #66cc66;">...</span> <span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">WHERE</span> <span style="color: #66cc66;">...</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">,</span> <span style="color: #cc66cc;">0</span><span style="color: #66cc66;">&#41;</span></pre></div></div>

<p>Punkty użytkownika już zawsze będą się sumowały poprawnie :-)</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/mysq-convert-null-to-0/feed/</wfw:commentRss>
		<slash:comments>10</slash:comments>
		</item>
		<item>
		<title>MySQL UPDATE JOIN</title>
		<link>http://athlan.pl/mysql-update-join/</link>
		<comments>http://athlan.pl/mysql-update-join/#comments</comments>
		<pubDate>Tue, 30 Jun 2009 09:46:27 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Databases]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[SQL]]></category>
		<category><![CDATA[Solutions]]></category>
		<category><![CDATA[database]]></category>
		<category><![CDATA[join]]></category>
		<category><![CDATA[mysql]]></category>
		<category><![CDATA[update]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=317</guid>
		<description><![CDATA[Ostatnimi czasy potrzebowałem danych z sąsiedniej tabeli przy UPDATE jedngo z pól w bazie danych. Danych do przetworzenia było sporo, więc zwracałem uwagę na wydajność zapytania. Aby zebrać potrzebne informacje, można użyć jednego ze sposobów: Zebrać potrzebne dane za pomocą SELECT&#8216;a, co sprawiłoby, że zajęta zostanie niepotrzebna pamięć w środowisku PHP podczas przypisania rezultatu do [...]]]></description>
			<content:encoded><![CDATA[<p>Ostatnimi czasy potrzebowałem danych z sąsiedniej tabeli przy <strong>UPDATE</strong> jedngo z pól w bazie danych. Danych do przetworzenia było sporo, więc zwracałem uwagę na wydajność zapytania. Aby zebrać potrzebne informacje, można użyć jednego ze sposobów:</p>
<ol>
<li>Zebrać potrzebne dane za pomocą <strong>SELECT</strong>&#8216;a, co sprawiłoby, że zajęta zostanie niepotrzebna pamięć w środowisku PHP podczas przypisania rezultatu do zmiennej.</li>
<li>Wykonać <strong>SET z podzapytaniem</strong>, ale potrzebnych mi było kilka kolumn z sąsiedniej tabeli, podzapytanie może zwrócić tylko jedną określoną wartość.</li>
<li>Wykonać <strong>JOIN</strong> przy update, czego niestety wówczas nie potrafiłem zrobić.</li>
</ol>
<p>Kartkując <a href="http://dev.mysql.com/doc/refman/5.0/en/update.html">manual</a> nie natrafiłem się w standardowej dokumentacji na nic konkretnego, aż nie spojrzałem na bardzo przydatne <a href="http://dev.mysql.com/doc/refman/5.0/en/update.html#c5402">komentarze użytkowników</a>. Okazało się, że przy <strong>UPDATE</strong> można wykonywać dowolne <strong>JOIN</strong>&#8216;y, schemat jest następujący:</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">UPDATE</span> <span style="color: #993333; font-weight: bold;">TABLE</span> <span style="color: #993333; font-weight: bold;">JOIN</span> another_table <span style="color: #993333; font-weight: bold;">SET</span> <span style="color: #66cc66;">...</span></pre></div></div>

<p>W tym momencie mamy do dyspozycji wszystkie pola z dołączonej tabeli. Bardzo przydatne.</p>
<p><strong>Przykład z życia.</strong></p>
<p>Miałem za zadanie odznaczyć typy bukmacherskie na trafione, nietrafione, odwołane z przyczyn odwołania całego meczu piłkarskiego oraz te, które jeszcze nie mogą zostać oznaczone jako trafione lub nie, gdyż mecz się jeszcze nie odbył.</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">UPDATE</span> typer_tickets_items
<span style="color: #993333; font-weight: bold;">LEFT</span> <span style="color: #993333; font-weight: bold;">JOIN</span> typer_events <span style="color: #993333; font-weight: bold;">ON</span><span style="color: #66cc66;">&#40;</span>event_id <span style="color: #66cc66;">=</span> item_event<span style="color: #66cc66;">&#41;</span>
<span style="color: #993333; font-weight: bold;">SET</span> item_status <span style="color: #66cc66;">=</span> <span style="color: #66cc66;">&#40;</span>
CASE
WHEN event_status <span style="color: #993333; font-weight: bold;">IS</span> <span style="color: #993333; font-weight: bold;">NULL</span> THEN <span style="color: #993333; font-weight: bold;">NULL</span> <span style="color: #808080; font-style: italic;"># mecz nie zostal rozegrany</span>
WHEN event_status <span style="color: #66cc66;">=</span> <span style="color: #66cc66;">-</span><span style="color: #cc66cc;">1</span> THEN <span style="color: #66cc66;">-</span><span style="color: #cc66cc;">1</span> <span style="color: #808080; font-style: italic;"># mecz anulowany</span>
WHEN event_status <span style="color: #66cc66;">=</span> item_bet THEN <span style="color: #cc66cc;">1</span> <span style="color: #808080; font-style: italic;"># typ trafiony</span>
ELSE <span style="color: #cc66cc;">0</span> END <span style="color: #808080; font-style: italic;"># typ nietrafiony</span>
<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">WHERE</span> item_status <span style="color: #993333; font-weight: bold;">IS</span> <span style="color: #993333; font-weight: bold;">NULL</span></pre></div></div>

<p>Mam nadzieję, że komuś się przyda&#8230;</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/mysql-update-join/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>JS Gamble game</title>
		<link>http://athlan.pl/js-gamble-game/</link>
		<comments>http://athlan.pl/js-gamble-game/#comments</comments>
		<pubDate>Sat, 16 May 2009 17:49:15 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[JS/Ajax]]></category>
		<category><![CDATA[Private]]></category>
		<category><![CDATA[gamble]]></category>
		<category><![CDATA[game]]></category>
		<category><![CDATA[javascript]]></category>
		<category><![CDATA[js]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=309</guid>
		<description><![CDATA[Wspólne wieczory z przyjaciółmi na wycieczce &#8211; to jest to &#8211; chyba każdy doświadczył gry w karty po nocach. Ale co jak na wycieczkę jedzie delegacja &#8220;komputerowców&#8221;, którzy nie biorą ze sobą nic oprócz ubrań, kawy i notebooków? Programista ma jedną przewagę nad innymi ludźmi &#8211; może stworzyć sobie własny wirtualny entertejment, kiedy pod ręką [...]]]></description>
			<content:encoded><![CDATA[<p>Wspólne wieczory z przyjaciółmi na wycieczce &#8211; to jest to &#8211; chyba każdy doświadczył gry w karty po nocach. Ale co jak na wycieczkę jedzie delegacja &#8220;komputerowców&#8221;, którzy nie biorą ze sobą nic oprócz ubrań, kawy i notebooków? Programista ma jedną przewagę nad innymi ludźmi &#8211; może stworzyć sobie własny wirtualny entertejment, kiedy pod ręką brak np&#8230; <strong>grę w kości kości</strong>.</p>
<p>Do szczęścia potrzebny był mi paint, notatnik i znajomość JavaScript. Stworzenie mini-gry <em>kości</em> zajęło niecałe 10 minut i fun na całą noc :-P</p>
<ul>
<li><a href="http://athlan.pl/code/gamble/">Demo gry w kości</a>, czyli to, co udało mi się na szybko wypocić.</li>
</ul>
<p><strong>Zasady gry</strong>:</p>
<p>Chyba każdemu znane, ale przypomnijmy:</p>
<blockquote><p>Kości to gra dla 2-4 osób, w której gracze turlają kostkami, by uzyskać określone układy oczek, za które otrzymuje się punkty. Wbrew pozorom nie jest to gra zależna tylko od szczęścia &#8212; liczy się w niej raczej umiejętność kalkulacji.</p>
<p>W każdej z 13 kolejek każdy z graczy ma do dyspozycji trzy rzuty kostkami. Pierwszy z nich odbywa się zawsze wszystkimi pięcioma kostkami, a w drugim i trzecim, które nie są obowiązkowe, wybrane kostki mogą zostać zatrzymane; rzut odbywa się wtedy tylko niezatrzymanymi.</p></blockquote>
<ul>
<li>Więcej zasad: <a href="http://www.kurnik.pl/kosci/zasady.phtml">http://www.kurnik.pl/kosci/zasady.phtml</a></li>
<li>Zaznaczamy te kości, którymy chcemy losować, mamy 3 rzuty dowolnymi kościami, potem przekazujemy myszkę koledze.</li>
<li>Gdy nie jest zaznaczona żadna kość do losowania, oznacza to, że chcemy losować wszystkimi kośćmi.</li>
</ul>
<p>Have fun ;p</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/js-gamble-game/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Przypadki w MySQL &#8211; CASE WHEN THEN ELSE END</title>
		<link>http://athlan.pl/mysql-case-when-then-else-end/</link>
		<comments>http://athlan.pl/mysql-case-when-then-else-end/#comments</comments>
		<pubDate>Wed, 29 Apr 2009 13:15:07 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Databases]]></category>
		<category><![CDATA[Planeta]]></category>
		<category><![CDATA[Publikacje]]></category>
		<category><![CDATA[SQL]]></category>
		<category><![CDATA[Solutions]]></category>
		<category><![CDATA[Add new tag]]></category>
		<category><![CDATA[case]]></category>
		<category><![CDATA[conditions]]></category>
		<category><![CDATA[database]]></category>
		<category><![CDATA[syntax]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=299</guid>
		<description><![CDATA[Podobnie jak w PHP, baza danych MySQL ma odpowiednik if, czyli przypadków (inaczej serii warunków, instrukcji warunkowych). Różnicą między implementacją CASE&#8216;a w MySQL i ifa PHP jest to, że baza danych zwraca konkretną wartość z case&#8217;a, a nie wykonuje dowolnej ilości dowolnych akcji. CASE Syntax: Najprostsza struktura CASE&#8217;aprzedstawia się nastepująco: CASE WHEN [conditions] THEN ... ELSE [...]]]></description>
			<content:encoded><![CDATA[<p>Podobnie jak w PHP, baza danych MySQL ma odpowiednik <a href="http://pl2.php.net/manual/en/control-structures.if.php">if</a>, czyli przypadków (inaczej serii warunków, instrukcji warunkowych). Różnicą między implementacją <a href="http://dev.mysql.com/doc/refman/5.0/en/case-statement.html">CASE</a>&#8216;a w MySQL i ifa PHP jest to, że baza danych zwraca konkretną wartość z case&#8217;a, a nie wykonuje dowolnej ilości dowolnych akcji.</p>
<p><strong>CASE Syntax:</strong></p>
<p>Najprostsza struktura CASE&#8217;aprzedstawia się nastepująco:</p>
<p><code>CASE WHEN [conditions] THEN ... ELSE ... END</code></p>
<p>Składnia powinna rozpocząć się słowem kluczowym CASE, a zakończyć END. Pomiędzy znajdują się warunki WHEN oraz operacja zwrócenia odpowiedniej wartości, która po nich następuje THEN (mamy możliwość uwzględnić nieskończenie wiele warunków). Jeżeli żaden warunek nie zostanie spełniony możemy użyć opcjonalnie ELSE.</p>
<p><strong>Przykłady z życia.</strong></p>
<p>Wyobraźmy sobie, że mamy posortować listę aukcji przedmiotów na Allegro od najtańszych, do najdroższych. Należy założyć, że są 2 typy aukcji: kup teraz i licytacja. Pole licytacji w bazie danych zawiera największą zaproponowaną kwotę przez użytkowników w procesie licytacji, a cena kup teraz ustalana jest przez sprzedającego. Są to dwa różne pola w bazie danych, a jedno kryterium sortowania, dlatego trzeba scalić cenę w jedną, wybierając odpowiednią. Musimy przewidzieć sytuację, w której aukcja jest typu kup teraz oraz licytacji, wówczas jeżeli najwyższa oferta jest większa od ceny kup teraz, wówczas wybieramy pole z największa propozycją:</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">SELECT</span> <span style="color: #66cc66;">&#40;</span>
  CASE
    WHEN <span style="color: #66cc66;">&#40;</span>auction_type <span style="color: #66cc66;">=</span> <span style="color: #ff0000;">'bidding'</span> <span style="color: #993333; font-weight: bold;">OR</span> auction_price_bid <span style="color: #66cc66;">&gt;</span> auction_price_buynow<span style="color: #66cc66;">&#41;</span>
      THEN auction_price_bid
    ELSE auction_price_buynow
  END<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> auction_price</pre></div></div>

<p>Stworzyliśmy pole auction_price, po którym można sortować aukcje od najtańszej do najdroższej i na odwrót.</p>
<p>Mam nadzieję, że krótki wpis przyda się początkującym. <span style="color: #c0c0c0;">Nic więcej nie trzeba opisywać, temat wydaje się co najmniej trywialny.</span></p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/mysql-case-when-then-else-end/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>18</title>
		<link>http://athlan.pl/18/</link>
		<comments>http://athlan.pl/18/#comments</comments>
		<pubDate>Tue, 21 Apr 2009 19:20:25 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Private]]></category>
		<category><![CDATA[Real live]]></category>
		<category><![CDATA[18]]></category>
		<category><![CDATA[athlan]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=296</guid>
		<description><![CDATA[Jestem pełnoletni.]]></description>
			<content:encoded><![CDATA[<p>Jestem pełnoletni.</p>
]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/18/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Samsung T260HD 26&#8243;</title>
		<link>http://athlan.pl/samsung-t260hd-26-cali/</link>
		<comments>http://athlan.pl/samsung-t260hd-26-cali/#comments</comments>
		<pubDate>Tue, 17 Mar 2009 23:24:58 +0000</pubDate>
		<dc:creator>Athlan</dc:creator>
				<category><![CDATA[Recenzje]]></category>
		<category><![CDATA[26"]]></category>
		<category><![CDATA[hardware]]></category>
		<category><![CDATA[monitor]]></category>
		<category><![CDATA[samsung]]></category>
		<category><![CDATA[Samsung T260HD]]></category>
		<category><![CDATA[sprzęt]]></category>
		<category><![CDATA[tv]]></category>

		<guid isPermaLink="false">http://athlan.pl/?p=276</guid>
		<description><![CDATA[Na moim biurku programisty pojawił się Samsung T260HD, przekątna 25,5 cala z tunerem TV. Zaraz po rozpakowaniu aż się przeraziłem, jakie to wielkie. Po kilkach godzinach używania, mogę z pełną odpowiedzialnością powiedzieć, że praca na rozdzielczości 1920¤1200 pikseli jest naprawdę wygodna. Od razu zabrałem się za testy PC i tunera TV. Zaprogramowałem kilka kanałów i skonfigurowałem [...]]]></description>
			<content:encoded><![CDATA[<p>Na moim biurku programisty pojawił się <strong>Samsung T</strong><strong>260HD</strong>, przekątna 25,5 cala z tunerem TV. Zaraz po rozpakowaniu aż się przeraziłem, <em>jakie to wielkie</em>. Po kilkach godzinach używania, mogę z pełną odpowiedzialnością powiedzieć, że praca na rozdzielczości 1920¤1200 pikseli jest naprawdę wygodna. Od razu zabrałem się za testy PC i tunera TV. Zaprogramowałem kilka kanałów i skonfigurowałem kontrast dla obu trybów: używania monitora na pececie i jako telewizor.</p>
<p>W poście postaram się wymienić wszystkie plusy i minusy produktu i podzielę się screenami, jak wygląda praca i przeglądanie Internetu na rozdzielczości 1920 pikseli wszerz.</p>
<p><strong>Parametry techniczne.</strong></p>
<table id="table1" border="0">
<tbody>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Przekątna ekranu</td>
<td bgcolor="#fafafa">25,5&#8243;</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Wymiary plamki</td>
<td bgcolor="#fafafa">0,258mm</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Maks. rozdzielczość obrazu</td>
<td bgcolor="#fafafa">1920&#215;1200</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Dopuszczalne rozdzielczości pracy</td>
<td bgcolor="#fafafa">1920&#215;1200</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Maksymalna częstotliwość odchylania poziomego</td>
<td bgcolor="#fafafa">30 ~ 81 kHz</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Maksymalna częstotliwość odchylania pionowego</td>
<td bgcolor="#fafafa">56 ~ 75 Hz</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Kąt widzenia pionowy</td>
<td bgcolor="#fafafa">160 stopni</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Kąt widzenia poziomy</td>
<td bgcolor="#fafafa">170 stopni</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Jasność</td>
<td bgcolor="#fafafa">300 cd/m2</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Współczynnik kontrastu</td>
<td bgcolor="#fafafa">10000:1</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Czas reakcji matrycy</td>
<td bgcolor="#fafafa">5 ms</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Wbudowane głośniki</td>
<td bgcolor="#fafafa">Tak</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Moc głośników</td>
<td bgcolor="#fafafa">2 x 3W</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Kolor obudowy</td>
<td bgcolor="#fafafa">czarno-bordowy</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Pobór mocy tryb normalny/czuwanie/wyłączony</td>
<td bgcolor="#fafafa">70W / 2W / -</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Rodzaj złącza wideo</td>
<td bgcolor="#fafafa">2 x HDMI, Component, D-Sub, DVI-D, Scart</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Tuner TV</td>
<td bgcolor="#fafafa">Tak</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Certyfikaty</td>
<td bgcolor="#fafafa">ISO 13406-2, ISO 9241-3,7,8, Vista Premium</td>
</tr>
<tr class="darkGreen">
<td class="label" bgcolor="#fafafa">Wymiary (szer. x wys. x głeb.)</td>
<td bgcolor="#fafafa">610.0 x 435.0 x 86.5 mm</td>
</tr>
<tr class="lightGreen">
<td class="label" bgcolor="#fafafa">Waga [kg]</td>
<td bgcolor="#fafafa">8,6 kg</td>
</tr>
</tbody>
</table>
<p><strong>T260HD jako monitor PC.</strong></p>
<p>Wszystkie tryby, które oferują domyślne ustawienia monitora nie pozwalają na pracę z monitorem. Aby rozpocząć pracę z tym sprzętem, konieczne jest przejście w tryb custom i dobranie sobie odpowiedniego kontrastu i jasności. Doskonały do oglądania filmów z peceta w rozdzielczości HD. Przeglądając Internet wielu użytkowników może odczuć <em>niepotrzebnie zmarnowanie</em> miejsce na stronach, które mają ustaloną szerokość przystosowaną do 1024 (<a href="/wp-content/uploads/screen-wide-column.jpg">paski po bokach</a>), natomiast przy stronach, które są rozciągnięte na całą szerokość i podzielone na tabele o sztywno określonych szerokościach kolumn, mogą pojawić się <a href="/wp-content/uploads/screen-wide-table.jpg">denerwujące pustki</a> (np na forach dyskusyjnych). Matryca TN jest idealna do pracy programisty, który chce poczuć przestrzeń. W sieci spotkałem się z opiniami, że monitora nie monża objąc wzrokiem, czemu muszę zdecydowanie zaprzeczyć. Siedzę od niego na odległość wyciągniętej ręki &#8211; jest idealny.</p>
<p><strong>Samsung jako TV.</strong></p>
<p>26 cali to stosunkowo niewiele jeżeli chodzi o standardy telewizora, jednak mi w zupełności wystarcza. Dużym minusem jest to, że sprzęt nie jest wyposażony w <a href="http://pl.wikipedia.org/wiki/Pivot">pivot</a>, jednakże do niezmienianej w pionie pozycji się w zupełności nadaje. Osobiście, aby korzystać z monitora jako TV, muszę obrócić go o 20 stopni w stronę łóżka i naturalnie oddalić się na przynajmniej trzykrotną odległość, niż pracuję na PC. Manewr ten nie jest denerwujący. Monitor oferuję pełną gamę opcji, jak zwykły TV: teletekst, programowanie kilkuset kanałów. 3W głośniki pozostawiają wiele do życzenia, ale Samsung jest wyposażony w 5 outputów audio, do oglądania telewizji korzystam z moich głośników Logitech <a href="http://www.logitech.com/index.cfm/products/details/GB/EN,CRID=2177,CONTENTID=9067">X-530</a>.</p>
<p><strong>Outputy i obudowa.</strong></p>
<p>Monitor posiada 2 outputy <a href="http://pl.wikipedia.org/wiki/HDMI">HDMI</a>, standardowo <a href="http://pl.wikipedia.org/wiki/D-Sub">D-Sub</a> i <a href="DVI-D">DVI-D</a> (złącze cyfrowe), <a href="http://pl.wikipedia.org/wiki/Component_video">Component</a> i <a href="http://pl.wikipedia.org/wiki/Scart">Scart</a> (eurozłącze). Jeżeli chodzi o audio, wyposażony jest w 5 outputów standardowo dla konfiguracji 5.1. Obudowa prezentuje wysoką klasę wykonania i estetykę. Błyszcząca, czarno-bordowa (wiśniowa) to ostatnio modny design linii produkcyjnej Samsunga. Bardzo wygodnie ulokowane przyciski na monitorze (niewidoczne, na prawej krawędzi). Wygląd pilota &#8211; standardowy, posiada poprzeczne podpórki, co czyni go stabilnym.</p>
<p><strong>Ogólne wrażenie.</strong></p>
<p>Duży :) ale nie za, więc pozytywnie. Na koniec mała galeria screenshootów, jak prezentuje się praca na monitorze:</p>

<a href='http://athlan.pl/samsung-t260hd-26-cali/t260hd/' title='t260hd'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/t260hd-150x150.jpg" class="attachment-thumbnail" alt="Zdjęcie monotra." title="t260hd" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/t260hd_dimmension/' title='t260hd_dimmension'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/t260hd_dimmension-150x150.jpg" class="attachment-thumbnail" alt="Wymiary monitora." title="t260hd_dimmension" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/notepadplus/' title='notepadplus'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/notepadplus-150x150.jpg" class="attachment-thumbnail" alt="Praca programisty na dużej rozdzielczości - wszystko się mieści." title="notepadplus" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/desktop/' title='desktop'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/desktop-150x150.jpg" class="attachment-thumbnail" alt="Pulpit w szerokości 1920." title="desktop" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/logon/' title='logon'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/logon-150x150.jpg" class="attachment-thumbnail" alt="Ekran logowania do systemu Windows." title="logon" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/photoshop/' title='photoshop'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/photoshop-150x150.jpg" class="attachment-thumbnail" alt="Wygodna praca w photoshopie." title="photoshop" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/wordpress/' title='wordpress'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/wordpress-150x150.jpg" class="attachment-thumbnail" alt="Praca na WordPress&#039;ie." title="wordpress" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/screen-wide-column/' title='screen-wide-column'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/screen-wide-column-150x150.jpg" class="attachment-thumbnail" alt="Puste boki na stronach o stałej szerokości." title="screen-wide-column" /></a>
<a href='http://athlan.pl/samsung-t260hd-26-cali/screen-wide-table/' title='screen-wide-table'><img width="150" height="150" src="http://athlan.pl/wp-content/uploads/screen-wide-table-150x150.jpg" class="attachment-thumbnail" alt="Denerwujące rozciągnięte tabele na forach dyskusyjncyh." title="screen-wide-table" /></a>

]]></content:encoded>
			<wfw:commentRss>http://athlan.pl/samsung-t260hd-26-cali/feed/</wfw:commentRss>
		<slash:comments>12</slash:comments>
		</item>
	</channel>
</rss>
