<?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>nova blog &#187; PHP</title>
	<atom:link href="http://blog.tlsys.hu/cimke/php/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.tlsys.hu</link>
	<description></description>
	<lastBuildDate>Mon, 17 Oct 2011 19:44:41 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Symfony IV. rész &#8211; egy form embedder plugin</title>
		<link>http://blog.tlsys.hu/symfony_form_embedder_plugin/</link>
		<comments>http://blog.tlsys.hu/symfony_form_embedder_plugin/#comments</comments>
		<pubDate>Sun, 20 Feb 2011 08:43:41 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Symfony]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://blog.tlsys.hu/?p=483</guid>
		<description><![CDATA[
			
			
			
			
			
			
			Tweet
						
						
			Ebben a bejegyzésemben az előző bejegyzésemben bemutatott form beágyazási technika alapján készített plugint tenném közzé.

A plugin célja, hogy egyszerűsítsen a symfony beágyazási technikáján. Az egyszerűsítés viszont nem minden esetben jobb. Tehát ott érdemes használni, ahol nem visszük túlzásba a beágyazást.   Ha túlságosan egyedi formára kívánjuk hozni, akkor előfordulhat hogy rengeteg módosítás helyett, célszerűbb [...]]]></description>
			<content:encoded><![CDATA[<div class="bottomcontainerBox" style="border:1px solid #808080;background-color:#F0F4F9;">
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fblog.tlsys.hu%2Fsymfony_form_embedder_plugin%2F&amp;layout=button_count&amp;show_faces=false&amp;width=85&amp;action=like&amp;font=verdana&amp;colorscheme=light&amp;height=21" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width=85px; height:21px;" allowTransparency="true"></iframe></div>
			<div style="float:left; width:80px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<g:plusone size="medium" href="http://blog.tlsys.hu/symfony_form_embedder_plugin/"></g:plusone>
			</div>
			<div style="float:left; width:95px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<a href="http://twitter.com/share" class="twitter-share-button" data-url="http://blog.tlsys.hu/symfony_form_embedder_plugin/"  data-text="Symfony IV. rész &#8211; egy form embedder plugin" data-count="horizontal">Tweet</a>
			</div><div style="float:left; width:105px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script type="in/share" data-url="http://blog.tlsys.hu/symfony_form_embedder_plugin/" data-counter="right"></script></div>			
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script src="http://www.stumbleupon.com/hostedbadge.php?s=1&amp;r=http://blog.tlsys.hu/symfony_form_embedder_plugin/"></script></div>			
			</div><div style="clear:both"></div><div style="padding-bottom:4px;"></div><p>Ebben a bejegyzésemben az <a href="symfony_embedded_form/">előző bejegyzésemben</a> bemutatott form beágyazási technika alapján készített plugint tenném közzé.<br />
<span id="more-483"></span><br />
A plugin célja, hogy egyszerűsítsen a symfony beágyazási technikáján. Az egyszerűsítés viszont nem minden esetben jobb. Tehát ott érdemes használni, ahol nem visszük túlzásba a beágyazást. <img src='http://blog.tlsys.hu/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' />  Ha túlságosan egyedi formára kívánjuk hozni, akkor előfordulhat hogy rengeteg módosítás helyett, célszerűbb teljesen tiszta lapról indulni. Akkor pedig az előző bejegyzésem nagyobb segítség, mint ez a plugin.<br />
<strong>A plugin használatának nagyon fontos feltétele, hogy a kapcsolt táblák 1:N kapcsolatban legyenek az adatbázis szerint is. Tehát a beágyazandó táblában legyen meg az idegen kulcs!</strong></p>
<p>Hozzávalók:<br />
<a href="http://blog.tlsys.hu/wp-content/uploads/2011/02/tlsysEmbedderHelperPlugin.tar.gz">A plugin itt található</a><br />
<a href="http://www.symfony-project.org/plugins/sfJqueryReloadedPlugin">sfJqueryReloadedPlugin</a><br />
<a href="http://book.cakephp.org/hu/view/3/A-Kézikönyv#!/hu/view/640/Set">CakePHP set osztálya</a>, <a href="http://blog.tlsys.hu/wp-content/uploads/2011/02/set.zip">a symfonysított verziót ide tettem fel</a>.</p>
<p>A plugin telepítése:</p>
<ol>
<li>
Miután létrehoztuk a projektünket, a plugin könyvtárba csomagoljuk ki plugint
</li>
<li>
Engedélyezzük a az apps/config/settings.yml fájlban:</p>
<pre class="brush: php; title: ; notranslate">
all:
  enabled_modules:        [default, tlsysEmbedderHelper, stb]
</pre>
<p>Erre azért van szükség, mert az ajaxos hívást kiszolgáló action a pluginba került. Így azt sem kell állandóan újra és újra megírni.
</li>
<li>
A lib/form/BaseFormPropel.class.php származtatása a pluginnban talalhato tlsysEmbedderFormból </p>
<pre class="brush: php; title: ; notranslate">
abstract class BaseFormPropel extends tlsysEmbedderForm
</pre>
</li>
<li>
A szükséges formokkban értéket kell adni a $tlsysEmbeddedForms protected változónak. Egy példa az előző bejegyzésemben található OsztalyFormra.</p>
<pre class="brush: php; title: ; notranslate">
class OsztalyForm extends BaseOsztalyForm
{
  # meg kell adni a beágyazni szándékozott osztály nevét, egyes és többesszámban
  # a többesszám az, ahogy a propel hivatkozik rá
  protected $tlsysEmbeddedForms = array(array('singular'=&gt;'Tanulo', 'plural'=&gt;'Tanulos'));
  public function configure()
  {
  }
}
</pre>
</li>
</ol>
<p>Ezzel a 4 lépéssel ugyanazt értük el, mint az előző bejegyzésemben található litániával.</p>
<p><a href="http://blog.tlsys.hu/wp-content/uploads/2011/02/sandbox-tlsysEmbedderHelperPlugin.tar.gz">A bemutató alkalmazás innen tölthető le</a></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.tlsys.hu/symfony_form_embedder_plugin/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Symfony III. rész – beágyazott form</title>
		<link>http://blog.tlsys.hu/symfony_embedded_form/</link>
		<comments>http://blog.tlsys.hu/symfony_embedded_form/#comments</comments>
		<pubDate>Mon, 14 Feb 2011 18:52:25 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Symfony]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://blog.tlsys.hu/?p=461</guid>
		<description><![CDATA[
			
			
			
			
			
			
			Tweet
						
						
			A symfony beágyazott (embedded) form megoldásáról szóló kis szösszenet kerül ide.
A segítségével két, master-detail kapcsolatban álló tábla egyidejű módosítását lehet megvalósítani.

Itt is az első leírásban létrehozott sandbox projektünket fogjuk átszerkeszteni.
Tehát állítsuk be a config könyvtárban lévő adatbázisokhoz tartozó fájlokat (propel.ini és databases.yml) az előzőleg létrehozott sandbox adatbázisra. Majd szerkesszük meg a config/schema.yml fájlt:

propel:
  _attributes:
 [...]]]></description>
			<content:encoded><![CDATA[<div class="bottomcontainerBox" style="border:1px solid #808080;background-color:#F0F4F9;">
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fblog.tlsys.hu%2Fsymfony_embedded_form%2F&amp;layout=button_count&amp;show_faces=false&amp;width=85&amp;action=like&amp;font=verdana&amp;colorscheme=light&amp;height=21" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width=85px; height:21px;" allowTransparency="true"></iframe></div>
			<div style="float:left; width:80px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<g:plusone size="medium" href="http://blog.tlsys.hu/symfony_embedded_form/"></g:plusone>
			</div>
			<div style="float:left; width:95px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<a href="http://twitter.com/share" class="twitter-share-button" data-url="http://blog.tlsys.hu/symfony_embedded_form/"  data-text="Symfony III. rész – beágyazott form" data-count="horizontal">Tweet</a>
			</div><div style="float:left; width:105px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script type="in/share" data-url="http://blog.tlsys.hu/symfony_embedded_form/" data-counter="right"></script></div>			
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script src="http://www.stumbleupon.com/hostedbadge.php?s=1&amp;r=http://blog.tlsys.hu/symfony_embedded_form/"></script></div>			
			</div><div style="clear:both"></div><div style="padding-bottom:4px;"></div><p>A symfony beágyazott (embedded) form megoldásáról szóló kis szösszenet kerül ide.<br />
A segítségével két, master-detail kapcsolatban álló tábla egyidejű módosítását lehet megvalósítani.<br />
<span id="more-461"></span></p>
<p>Itt is az <a href="http://blog.tlsys.hu/symfony-propel-ubuntu-telepit/">első leírásban</a> létrehozott sandbox projektünket fogjuk átszerkeszteni.</p>
<p>Tehát állítsuk be a config könyvtárban lévő adatbázisokhoz tartozó fájlokat (propel.ini és databases.yml) az előzőleg létrehozott sandbox adatbázisra. Majd szerkesszük meg a config/schema.yml fájlt:</p>
<pre class="brush: sql; title: ; notranslate">
propel:
  _attributes:
    package: lib.model
    defaultIdMethod: native
  osztaly:
    _attributes: { phpName: Osztaly }
    id: { phpName: Id, type: INTEGER, size: '11', primaryKey: true, autoIncrement: true, required: true }
    kod: { phpName: Kod, type: CHAR, size: '1', required: true }
    evfolyam: { phpName: Evfolyam, type: INTEGER, size: '11', required: true }
  tanulo:
    _attributes: { phpName: Tanulo }
    id: { phpName: Id, type: INTEGER, size: '11', primaryKey: true, autoIncrement: true, required: true }
    name: { phpName: Name, type: VARCHAR, size: '255', required: true }
    szuletes: { phpName: Szuletes, type: DATE, required: true }
    osztaly_id: { phpName: OsztalyId, type: INTEGER, size: '11', required: false, foreignTable: osztaly, foreignReference: id, onDelete: CASCADE, onUpdate: CASCADE }
    _indexes: { category_id: [osztaly_id] }
</pre>
<p>Majd futtassuk le az alábbi parancsokat is:</p>
<pre class="brush: bash; title: ; notranslate">
# hozzuk létre a formokat, filtereket, modeleket, és a táblákat is generáljuk le
# a kérdésre, miszerint kívánjuk-e hogy felülírja az adatbázisunkat válaszoljunk igennel (Y)
./symfony propel:build-all
# és a két táblánkhoz tartozó admin felületet készítsük el:
./symfony propel:generate-admin frontend osztaly
./symfony propel:generate-admin frontend tanulo
</pre>
<p>Szükségünk lesz egy pluginra, a <a href="http://www.symfony-project.org/plugins/sfJqueryReloadedPlugin">sfJqueryReloadedPlugin</a>ra. A telepítése nem túl bonyolult. Ha az összes plugint engedélyeztük (a config/ProjectConfiguration.class.php fájlban), akkor elég bemásolni a plugin könyvtárba. Mivel a letöltött tömörített fájlban mindenféle kódszámot ír a könyvtárnév végére, így a könnyebb elérhetőség miatt használjuk inkább a sfJqueryReloadedPlugin könyvtárnevet.</p>
<p>A lib/model/Osztaly.php fájlt pedig egészítsük ki az alábbi metódussal</p>
<pre class="brush: php; title: ; notranslate">
public function __toString()
{
  return $this-&gt;evfolyam.'/'.$this-&gt;kod;
}
</pre>
<p>Az apps/frontend/config/routing.yml fájlt is módosítsuk, hogy az osztályok listája jelenjen meg alapértelmezetten.</p>
<pre class="brush: php; title: ; notranslate">
homepage:
  url:   /
  param: { module: osztaly, action: index }
</pre>
<p>Ezzel az alap projektünk elkészült. Lehet listázni, új osztályt felvinni és módosítani. Azonban az osztályhoz még nem tudunk tanulót rögzíteni. Ehhez módosítsuk a lib/form/OsztalyForm.class.php fájlt.<br />
Ez egy hosszabb lélegzetvétel lesz, mert nem aprózom el <img src='http://blog.tlsys.hu/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </p>
<pre class="brush: php; title: ; notranslate">
class OsztalyForm extends BaseOsztalyForm
{
   /**
   * a form konfiguralasa
   * hozzaadjuk a tanulokat a formhoz
   * hozzadjuk a hozzaadas gombot (Uj) letrehozo widgetet is.
   */
   public function configure()
  {
    parent::setup();
    $context = sfContext::getInstance();
    $this-&gt;loadHelpers($context);

    $tanulok = $this-&gt;getObject()-&gt;getTanulos();

    //Egy ures formba eltaroljuk az embeddelt TanuloFormokat
    $this-&gt;embedForm('tanulos', new sfForm());
    $count = 0;
    foreach ($tanulok as $tanulo) {
      $this-&gt;addTanulo($count, $tanulo);
      $count ++;
    }

    // a hozzaadas gomb mint egy uj mezo kerul a formunkba
    $this-&gt;widgetSchema['addEmbedform'] = new embedderFormWidget(array(
        'url'=&gt;url_for('osztaly/getEmbedForm'),
        'html_element' =&gt; &quot;.sf_admin_form_field_tanulos table:first&quot;,
        ));
    $this-&gt;widgetSchema-&gt;setLabel('addEmbedform', false);
  }

  /**
   * kulonbozo helperek betoltese
   * Url helper az ajax hivashoz hasznalando helyes url megadasahoz
   * jQueryReloadedPlugin jQuery helpere
   * es a jQuery UI plugin javascript betoltese
   *
   * @param sfContext $context
   */
  public function loadHelpers($context)
  {
    $context-&gt;getConfiguration()-&gt;loadHelpers(array('jQuery','Tag','Url'));
    $context-&gt;getResponse()-&gt;addStyleSheet(sfConfig::get('sf_jquery_web_dir', '/sfJqueryReloadedPlugin') . &quot;/css/ui-lightness/jquery-ui-1.8.2.custom.css&quot;);
    jq_add_plugins_by_name(array('ui'));
  }

  /**
   * A torles link a Tanulo mellett
   *
   * @param string $index
   * @return string
   */
  public function getEmbedFormLabel($index)
  {
    return jq_link_to_function(
      '&lt;span class=&quot;ui-icon ui-icon-trash&quot;&gt;&lt;/span&gt;',
      &quot;jQuery(this).parents('tr:first').remove(); jQuery('#osztaly_tanulos_&quot;.$index.&quot;_id').remove();&quot;,
      array('confirm' =&gt; 'Sure???'));
  }

  /**
   * A Tanulo hozzaadasa az Osztalyhoz
   *
   * Erre akkor is szuksegunk lesz, amikor egy uj tanulot veszunk fel
   *
   * @param string $num
   * @param Tanulo $tanulo
   */
  public function addTanulo($num, $tanulo = null)
  {
    if (!$tanulo)
    {
      $tanulo = new Tanulo();
    }
    $tanulo-&gt;setOsztaly($this-&gt;getObject());
    $form = new TanuloForm($tanulo);
    $form-&gt;getWidgetSchema()-&gt;offsetUnset('osztaly_id');
    $this-&gt;embeddedForms['tanulos']-&gt;embedForm($num, $form);

    // torles link
    $label = $this-&gt;getEmbedFormLabel($num);
    $this-&gt;embeddedForms['tanulos']-&gt;widgetSchema-&gt;setLabel($num,$label);

    $this-&gt;embedForm('tanulos', $this-&gt;embeddedForms['tanulos']);
  }

  /**
   *
   * Ha rogziteskor uj tanulot vettunk fel, akkor adjuk hozza az osztalyhoz
   * Ha pedig toroltunk akkor tavolitsuk el a formbol
   */
  public function bind(array $taintedValues = null, array $taintedFiles = null)
  {
    if (isset($taintedValues['tanulos']))
    {
      foreach($taintedValues['tanulos'] as $key =&gt; $tanulo)
      {
        if (!isset($this['tanulos'][$key]))
        {
          $this-&gt;addTanulo($key);
        }
      }
    }

    foreach ($this-&gt;embeddedForms['tanulos'] as $key=&gt;$form)
    {
      if (!isset($taintedValues['tanulos'][$key]) &amp;&amp; $key&lt;&gt;'_csrf_token')
      {
        $this-&gt;getWidgetSchema()-&gt;offsetGet('tanulos')-&gt;offsetUnset($key);
        $this-&gt;getValidatorSchema()-&gt;offsetGet('tanulos')-&gt;offsetUnset($key);
        unset(
          $taintedValues['tanulos'][$key],
          $taintedFiles['tanulos'][$key]);
      }
    }

    parent::bind($taintedValues, $taintedFiles);
  }

  /**
   * Tanulonak beallitjuk az osztalyat
   *
   * Amikor egy uj osztallyal egyutt viszunk fel egy tanulot, akkor
   * meg kell adnunk a tanulonak is, hogy melyik osztalyba tartozik.
   * Raadasul eltavolitottuk a tanulo from osztaly_id mezojet, így minden
   * egyeb esetben is szukseg van erre.
   *
   */
  public function saveEmbeddedForms($con = null, $forms = null)
  {
    $oszaly = $this-&gt;getObject();
    if ($forms)
    {
      foreach ($forms as $form)
      {
        if ($form instanceof sfFormObject)
        {
          $form-&gt;getObject()-&gt;setOsztaly($oszaly);
        }
      }
    }   

    return parent::saveEmbeddedForms($con, $forms);
  }

  /**
   * Ezt az osztalyfuggvenyt bovitjuk. A kikeressuk a postolt adatokbol a  tanulok
   * azonositojat (id). Amelyik tanulo azonositoja nincs benne a kapott eredmenyben,
   * toroljuk az osztalybol.
   */
  public function updateObjectEmbeddedForms ($values, $forms = null)
  {
    // $values['tanulos'][][id] elemeket, ahol id&gt;0
    $ids = set::extract('/tanulos[id&gt;0]/id', $values);
    if (!$forms)
    {
      $c = new Criteria();
      $c-&gt;add(TanuloPeer::OSZTALY_ID, $this-&gt;getObject()-&gt;getId());
      $c-&gt;add(TanuloPeer::ID, $ids, Criteria::NOT_IN);
      TanuloPeer::doDelete($c);
    }
    return parent::updateObjectEmbeddedForms ($values, $forms);
  }
}
</pre>
<p>Három dolgot használtunk fel a formban, amit még el kell készítenünk. </p>
<p>Egy widget, ami létrehozza a tanuló hozzáadása linket. Ezt embedderFormWidget néven neveztem el és a lib/widget mappába tegyük. Ez a mappa még nem létezik, létre kell hozni. Ebbe hozuk létre a embedderFormWidget.class.php fájlt:</p>
<pre class="brush: php; title: ; notranslate">
&lt;?php
/**
 * @author     nova
 * @version    1.0.0
 */
class embedderFormWidget extends sfWidgetForm
{
  /**
   * Configures the current widget.
   *
   * Available options:
   *
   * @param string html_element - az elem, amihez hozzafuzunk
   * @param string url - az ajay keres url-je
   *
   * @see sfWidgetForm
   */
  protected function configure($options = array(), $attributes = array())
  {
    $this-&gt;addOption('html_element');
    $this-&gt;addOption('url');
    parent::configure($options, $attributes);
  }

  /**
   * @param  string $name        The element name
   * @param  string $value       The date displayed in this widget
   * @param  array  $attributes  An array of HTML attributes to be merged with the default HTML attributes
   * @param  array  $errors      An array of errors for the field
   *
   * @return string An HTML tag string
   *
   * @see sfWidgetForm
   */
  public function render($name, $value = null, $attributes = array(), $errors = array())
  {
    $attributes = $this-&gt;getAttributes();
    $html =jq_link_to_function(
        '&lt;span class=&quot;ui-icon ui-icon-circle-plus fright&quot;&gt;&lt;/span&gt;&lt;span class=&quot;fright&quot;&gt;Új&lt;/span&gt;',
        &quot;jQuery.get('&quot;.$this-&gt;getOption('url').&quot;',function(data){
            jQuery('&quot;.$this-&gt;getOption('html_element').&quot;').append(data);
        });&quot;,
        $attributes);
    return $html;
  }
}
</pre>
<p>Aztán gondoskodnuk kell az ajax hívás válaszáról a szerver oldalon. Módosítsuk az apps/fronntedn/modules/osztaly/actions/actions.class.php fájlt az alábbi metódussal:</p>
<pre class="brush: php; title: ; notranslate">
  /**
   * Visszaad egy új sort (widgetet) a tanulo formhoz
   *
   * @param sfWebRequest $request
   */
  public function executeGetEmbedForm(sfWebRequest $request)
  {
    $form = $this-&gt;configuration-&gt;getForm();
    $num = 'tmp_'.time();
    $form-&gt;addTanulo($num);

    return $this-&gt;renderText($form-&gt;getWidget('tanulos')-&gt;getWidget($num)-&gt;render($num));
  }
</pre>
<p>Ezen kívül még felhasználtam egy konkurens MVC rendszerben található igencsak hasznos osztályt, a<br />
<a href="http://book.cakephp.org/hu/view/3/A-Kézikönyv#!/hu/view/640/Set">CakePHP set osztályát</a><br />
Ezt persze módosítanom kellett, hogy szeresse a Symfony is. <a href="http://blog.tlsys.hu/wp-content/uploads/2011/02/set.zip">Ide tettem fel</a>.</p>
<p>Letölthetővé tettem a teljes projektet is, <a href="http://blog.tlsys.hu/wp-content/uploads/2011/02/sandbox.tar.gz">innen</a>.</p>
<p>Sajnos annyi energiám nem volt hogy lépésről lépésre építsem fel a projektet, remélem így is hasznosnak találja, aki elolvassa. Nekem meg jó jegyzet <img src='http://blog.tlsys.hu/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.tlsys.hu/symfony_embedded_form/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Az ember mindig tanul&#8230;</title>
		<link>http://blog.tlsys.hu/az-ember-mindig-tanul/</link>
		<comments>http://blog.tlsys.hu/az-ember-mindig-tanul/#comments</comments>
		<pubDate>Wed, 07 Apr 2010 19:43:28 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Nincs kategorizálva]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://blog.tlsys.hu/?p=303</guid>
		<description><![CDATA[
			
			
			
			
			
			
			Tweet
						
						
			Már jó pár éve foglalkozom PHP-vel, de még mindig van ami meglepetésként ér(t).
Ilyen például hogy a header parancs nem irányít át azonnal, hanem csak a teljes action lista lefutása után teszi.
header("Location: index.php");
echo 'hehe ez még kiíródik, csak nem látod';
die();
echo 'hehe, de ez már nem';

]]></description>
			<content:encoded><![CDATA[<div class="bottomcontainerBox" style="border:1px solid #808080;background-color:#F0F4F9;">
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fblog.tlsys.hu%2Faz-ember-mindig-tanul%2F&amp;layout=button_count&amp;show_faces=false&amp;width=85&amp;action=like&amp;font=verdana&amp;colorscheme=light&amp;height=21" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width=85px; height:21px;" allowTransparency="true"></iframe></div>
			<div style="float:left; width:80px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<g:plusone size="medium" href="http://blog.tlsys.hu/az-ember-mindig-tanul/"></g:plusone>
			</div>
			<div style="float:left; width:95px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<a href="http://twitter.com/share" class="twitter-share-button" data-url="http://blog.tlsys.hu/az-ember-mindig-tanul/"  data-text="Az ember mindig tanul&#8230;" data-count="horizontal">Tweet</a>
			</div><div style="float:left; width:105px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script type="in/share" data-url="http://blog.tlsys.hu/az-ember-mindig-tanul/" data-counter="right"></script></div>			
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script src="http://www.stumbleupon.com/hostedbadge.php?s=1&amp;r=http://blog.tlsys.hu/az-ember-mindig-tanul/"></script></div>			
			</div><div style="clear:both"></div><div style="padding-bottom:4px;"></div><p>Már jó pár éve foglalkozom PHP-vel, de még mindig van ami meglepetésként ér(t).<br />
<span id="more-303"></span>Ilyen például hogy a header parancs nem irányít át azonnal, hanem csak a teljes action lista lefutása után teszi.<br />
<code>header("Location: index.php");<br />
echo 'hehe ez még kiíródik, csak nem látod';<br />
die();<br />
echo 'hehe, de ez már nem';<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.tlsys.hu/az-ember-mindig-tanul/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Symfony parancsok</title>
		<link>http://blog.tlsys.hu/symfony-parancsok/</link>
		<comments>http://blog.tlsys.hu/symfony-parancsok/#comments</comments>
		<pubDate>Fri, 12 Feb 2010 10:20:45 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Symfony]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://blog.tlsys.hu/?p=175</guid>
		<description><![CDATA[
			
			
			
			
			
			
			Tweet
						
						
			amiket sokat kerestem, hogy többet ne kelljen   

//sfGuardUser ID:
sfContext::getInstance()-&#62;getUser()-&#62;getGuardUser()-&#62;getId()

//Hogyan alakitsuk egy objetum name tulajdonságát id 'formátumura':
get_id_from_name($name)

// form formázása (&#60;p&#62; stílus):
// http://www.thatsquality.com/articles/7-days-of-symfony-1-1-forms-widgets-and-validators-day7
$formatter = $this-&#62;getWidgetSchema()-&#62;getFormFormatter();
$formatter-&#62;setErrorRowFormat('%errors%');
$formatter-&#62;setErrorListFormatInARow(&#34;%errors%\n&#34;);
$formatter-&#62;setErrorRowFormatInARow(&#34;&#60;p class='error-message'&#62;%error%&#60;/p&#62;&#34;);
$formatter-&#62;setRowFormat(&#34;%error%&#60;p&#62;%label%%field%%help%%hidden_fields%&#60;/p&#62;\n&#34;);
// ez alapból nem hívodik meg. De ha a formatter használja, pl: embeddformnál:
$formatter-&#62;setDecoratorFormat('&#60;table class=&#34;tgTextSlot&#34;&#62;%content%&#60;/table&#62;');

// hogyan adjunk egy form elemnek classt:
// formban :
$this-&#62;WidgetSchema['name']-&#62;setAttribute('class', 'classname');
// templateben 1:
echo $form-&#62;render(array('name' =&#62; array('class' =&#62; 'classname'), [...]]]></description>
			<content:encoded><![CDATA[<div class="bottomcontainerBox" style="border:1px solid #808080;background-color:#F0F4F9;">
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fblog.tlsys.hu%2Fsymfony-parancsok%2F&amp;layout=button_count&amp;show_faces=false&amp;width=85&amp;action=like&amp;font=verdana&amp;colorscheme=light&amp;height=21" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width=85px; height:21px;" allowTransparency="true"></iframe></div>
			<div style="float:left; width:80px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<g:plusone size="medium" href="http://blog.tlsys.hu/symfony-parancsok/"></g:plusone>
			</div>
			<div style="float:left; width:95px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<a href="http://twitter.com/share" class="twitter-share-button" data-url="http://blog.tlsys.hu/symfony-parancsok/"  data-text="Symfony parancsok" data-count="horizontal">Tweet</a>
			</div><div style="float:left; width:105px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script type="in/share" data-url="http://blog.tlsys.hu/symfony-parancsok/" data-counter="right"></script></div>			
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script src="http://www.stumbleupon.com/hostedbadge.php?s=1&amp;r=http://blog.tlsys.hu/symfony-parancsok/"></script></div>			
			</div><div style="clear:both"></div><div style="padding-bottom:4px;"></div><p>amiket sokat kerestem, hogy többet ne kelljen <img src='http://blog.tlsys.hu/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' />  <span id="more-175"></span></p>
<pre class="brush: php; title: ; notranslate">
//sfGuardUser ID:
sfContext::getInstance()-&gt;getUser()-&gt;getGuardUser()-&gt;getId()

//Hogyan alakitsuk egy objetum name tulajdonságát id 'formátumura':
get_id_from_name($name)

// form formázása (&lt;p&gt; stílus):
// http://www.thatsquality.com/articles/7-days-of-symfony-1-1-forms-widgets-and-validators-day7
$formatter = $this-&gt;getWidgetSchema()-&gt;getFormFormatter();
$formatter-&gt;setErrorRowFormat('%errors%');
$formatter-&gt;setErrorListFormatInARow(&quot;%errors%\n&quot;);
$formatter-&gt;setErrorRowFormatInARow(&quot;&lt;p class='error-message'&gt;%error%&lt;/p&gt;&quot;);
$formatter-&gt;setRowFormat(&quot;%error%&lt;p&gt;%label%%field%%help%%hidden_fields%&lt;/p&gt;\n&quot;);
// ez alapból nem hívodik meg. De ha a formatter használja, pl: embeddformnál:
$formatter-&gt;setDecoratorFormat('&lt;table class=&quot;tgTextSlot&quot;&gt;%content%&lt;/table&gt;');

// hogyan adjunk egy form elemnek classt:
// formban :
$this-&gt;WidgetSchema['name']-&gt;setAttribute('class', 'classname');
// templateben 1:
echo $form-&gt;render(array('name' =&gt; array('class' =&gt; 'classname'), 'name2' =&gt; array('class'=&gt;'classname'))) ;
// templateben 2:
echo $form['name']-&gt;renderRow(array('class' =&gt; 'classname'));

//formban widget mozgatása:
$this-&gt;getWidgetSchema()-&gt;moveField('widget_name', sfWidgetFormSchema::AFTER, 'last_name');

//$this változóinak lekérdezése
$this-&gt;getVarHolder()-&gt;getAll()

//SF_ENVIRONMENT 1.2 alatt:
sfConfig::get('sf_environment')

// összes request paraméter lekérése
$this-&gt;getRequest()-&gt;getParameterHolder()-&gt;getAll();
sfContext::getInstance()-&gt;getRequest()-&gt;getParameterHolder()-&gt;getAll()

// egy bizonyos request paraméter lekérése
$this-&gt;getRequestParameter('parameter', false);
sfContext::getInstance()-&gt;getRequest()-&gt;getParameter('parameter');

// controllerben helper használata
sfLoader::loadHelpers(array('Tag', 'Url'));
sfContext::getInstance()-&gt;getConfiguration()-&gt;loadHelpers(array('Tag', 'Url'));

//i18N akárhol:
sfContext::getInstance()-&gt;getI18N()-&gt;__('Nincs kiválasztva')

i18N formban:
$this-&gt;getWidgetSchema()-&gt;getFormFormatter()-&gt;translate('szoveg');

// Ez inkább propel. A model osztályból, annak sql neve:
constant(get_class($this-&gt;getPeer()).'::TABLE_NAME')

// ajax link
echo link_to_remote('postolunk', array(
'update'    =&gt; 'a div id-ja amibe a visszatérő adatokat kapjuk',
'url'       =&gt; 'az ajaxos url',
'method'    =&gt; 'post',
//ez meghívja a validate javascript függvényt:
'condition' =&gt; &quot;validate(Form.serialize('formId'))&quot;,
//és a legfontosabb, így lehet a form adatait is elküldeni:
'submit'    =&gt; &quot;formId&quot;
))

// A form mezői:
$this-&gt;getWidgetSchema()-&gt;getPositions()

// egy form hibát dob, de az épp rejtett, akkor irassuk ki.
$this-&gt;form-&gt;getErrorSchema()
foreach($this-&gt;form-&gt;getErrorSchema()-&gt;getErrors() as $key =&gt; $error)
{
  echo '&lt;p&gt;' . $key . ': ' . $error . '&lt;/p&gt;';
}

// absolute url:
link_to(__('szöveg', array(), 'messages'), '@url', array('absolute'=&gt;true))
</pre>
<p>Callback validator</p>
<pre class="brush: php; title: ; notranslate">
class aForm extends aBaseForm
{
  public function configure()
  {
    parent::configure() ; //esetleg ez nem fontos
    $this-&gt;validatorSchema-&gt;setPostValidator(new sfValidatorCallback(array('callback' =&gt; array($this, 'fuggvenyneve'))));
  }

  public function fuggvenyneve(sfValidatorBase $validator, array $values)
  {
    // $values tartalmazza az összes adatot, feldolgozod és a $hibavan-nak ennek függvényében értéket adsz:
    if ($hibavan)
    {
      throw new sfValidatorError($validator, 'hibaüzenet');
    }

    return $values;
  }
}
</pre>
<p>Propel</p>
<pre class="brush: php; title: ; notranslate">
$c = new Criteria();
$c-&gt;addJoin(
    array(ReaderFavoritePeer::BOOK_ID,ReaderFavoritePeer::READER_ID),
    array(BookOpinionPeer::BOOK_ID,BookOpinionPeer::READER_ID))

// és irassuk is ki a criteriát SQL-ben
echo $criteria-&gt;toString(); 

// szerezzük meg az ID-kat egy táblából.
$c = new Criteria();
$c-&gt;addSelectColumn(MyClassPeer::ID);
$res = BasePeer::doSelect($c);
$Ids = $res-&gt;fetchAll(PDO::FETCH_COLUMN,0);

// SELECT  FROM `tabla` WHERE (tabla.mezo1='string1' OR (tabla.mezo1='string2' AND tabla.mezo2='0'))
$c = new Criteria();
$cr1 = $c-&gt;getNewCriterion(TablePeer::MEZO1, 'string1');
$cr2 = $c-&gt;getNewCriterion(TablePeer::MEZO1, 'string2');
$cr3 = $c-&gt;getNewCriterion(TablePeer::MEZO2, '0');
$cr2-&gt;addAnd($cr3);
$cr1-&gt;addOr($cr2);
$c-&gt;add($cr1);
$c-&gt;toString();
</pre>
<p>Task</p>
<pre class="brush: php; title: ; notranslate">
./symfony i18n:extract frontend hu --auto-save
./symfony i18n:extract frontend hu --display-new
</pre>
<p>Internationalization</p>
<pre class="brush: php; title: ; notranslate">
      //http://www.php.net/manual/en/function.strftime.php
      fb(format_date(time(), 'f'),'f');
      fb(format_date(time(), 'G'),'G');
      fb(format_date(time(), 'y'),'y');
      fb(format_date(time(), 'M'),'M');
      fb(format_date(time(), 'd'),'d');
      fb(format_date(time(), 'h'),'h');
      fb(format_date(time(), 'H'),'H');
      fb(format_date(time(), 'm'),'m');
      fb(format_date(time(), 's'),'s');
      fb(format_date(time(), 'E'),'E');
      fb(format_date(time(), 'D'),'D');
      fb(format_date(time(), 'F'),'F');
      fb(format_date(time(), 'W'),'W');
      fb(format_date(time(), 'w'),'w');
      fb(format_date(time(), 'a'),'a');
      fb(format_date(time(), 'k'),'k');
      fb(format_date(time(), 'K'),'K');
      fb(format_date(time(), 'z'),'z');
</pre>
<p>A smarty egyszerű <img src='http://blog.tlsys.hu/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </p>
<pre class="brush: php; title: ; notranslate">
        {assign var='createdat' value=$current_page-&gt;getCreatedAt()}
        {assign var='createdat' value=$createdat|strtotime}
        {capture assign='createdat'}
          {format_date date=$createdat format=&quot;D&quot;}
        {/capture}
        &lt;p class=&quot;date&quot;&gt;{$createdat}&lt;/p&gt;

        // Mert PHP-ban ennyi:
        &lt;?php echo format_date(strtotime($current_page-&gt;getCreatedAt())), 'D'); ?&gt;
</pre>
<p><a href="http://snipt.net/Tram/symfony-12-add-a-custom-filter-field-for-generated-admin/"><br />
Add a custom filter field for generated admin<br />
</a></p>
<pre class="brush: php; title: ; notranslate">
  public function configure() {

    $this-&gt;widgetSchema['title'] = new sfWidgetFormFilterInput();

    $this-&gt;validatorSchema['title'] = new sfValidatorPass(array('required' =&gt; false));
  }//configure

  public function getFields() {
    return array_merge(array(
        'title'=&gt; 'Title',
      ), parent::getFields()
    );
  } //getFields

  protected function addTitleColumnCriteria(Criteria $criteria, $field, $values) {

    // $values['text'] contains the field value, use it to change $criteria object

    // es. $criteria-&gt;add ('column', $values['text'])

  }//addTitleColumnCriteria
</pre>
<p>loggolás külön fájlba.</p>
<pre class="brush: php; title: ; notranslate">
    $text = var_export($this-&gt;getObject()-&gt;toArray(), true);
    $file = sfConfig::get('sf_log_dir').DIRECTORY_SEPARATOR.'debug.log';
    $dispatcher = sfContext::getInstance()-&gt;getEventDispatcher();
    $logger = new sfFileLogger($dispatcher, array('file' =&gt; $file) );
    $dispatcher-&gt;disconnect('application.log', array($logger, 'listenToLogEvent'));
    $logger-&gt;err($text);
    $logger-&gt;notice($text);
    $logger-&gt;info($text);
</pre>
<p>Doctrine:</p>
<pre class="brush: php; title: ; notranslate">
//kapcsolt táblák lekérdezése:
foreach (Doctrine_Core::getTable('CompanyLog')-&gt;getRelations() as $name =&gt; $relation)
{
  echo $name . &quot;:\n&quot;; echo &quot;Local - &quot; . $relation-&gt;getLocal() . &quot;\n&quot;; echo &quot;Foreign - &quot; . $relation-&gt;getForeign() . &quot;\n\n&quot;;
}
</pre>
<p><a href="http://stackoverflow.com/questions/3026961/render-each-choice-as-a-row-in-a-table-in-a-symfony-choice-widget">hogyan formázzunk egy sfWidgetFormChoice widgetet?</a></p>
<pre class="brush: php; title: ; notranslate">
// a widget
$this-&gt;widgetSchema ['my_widget'] = new sfWidgetFormChoice(array('multiple' =&gt; true, 'expanded' =&gt; true, 'choices' =&gt; my_choices, 'renderer_class' =&gt; 'sfWidgetFormSelectCheckbox', 'renderer_options' =&gt; array('formatter' =&gt; array('MyForm', 'MyFormatter'))));

$this-&gt;validatorSchema ['my_widget'] = new sfValidatorChoice(array('multiple' =&gt; true, 'choices' =&gt; array_keys(my_choices), 'required' =&gt; false));

// és a formban:
public static function MyFormatter($widget, $inputs) {
       $result = '&lt;table&gt;';
       foreach ($inputs as $input) {
          $result .= '&lt;tr&gt;&lt;td&gt;' . $input ['label'] . '   ' . $input ['input'] . '&lt;/td&gt;&lt;/tr&gt;';
        }
        $result .= '&lt;/table&gt;';
        return $result;
}
</pre>
<p>néha szükségünk lehet egy olyan widgetre, ami egy tömböt/listát tartalmaz.<br />
Én most egy két dimenziós tömböt fogok megjeleníteni:</p>
<pre class="brush: php; title: ; notranslate">

    protected function getWidgetFormSchemaForMyField($choices)
    {
      $widget = new sfWidgetFormSchema(array(
         'mezo1' =&gt;  new sfWidgetFormPlain(),
         'mezo2' =&gt;  new sfWidgetFormInputHidden(),
         'mezo3'   =&gt;  new sfWidgetFormChoice(array('choices'=&gt;$choices))
      ));

      // a mezők a táblázat egyes cellái lesznek, tehát egymás mellett lesznek:
      $widget-&gt;getFormFormatter()-&gt;setRowFormat('&lt;td&gt;%error%%field%%help%%hidden_fields%&lt;/td&gt;');
      return $widget;
    }

    public function configure()
    {
        ...
        // itt le kell kérni a rekordokat
        // a choices tömbnek is értéket kell adni

        $widgetrows = array();
        foreach ($records as $key=&gt;$record)
        {
          $widgetrows[$key] = $this-&gt;getWidgetFormSchemaForMyField($choices);
        }
        $widget = new sfWidgetFormSchema($widgetrows);
        $formatter = $widget-&gt;getFormFormatter();
        // a táblázat egyes sorai (a fenti három mező egy sorban, de azokból több sor lesz):
        $formatter-&gt;setRowFormat('&lt;tr&gt;%error%%field%%help%%hidden_fields%&lt;/tr&gt;');

        $this-&gt;widgetSchema['mezo'] = new sfWidgetFormSchema(array($widget));
        $formatter = $this-&gt;widgetSchema['mezo']-&gt;getFormFormatter();
        // bele kell tenni az egészet egy táblázatba:
        $formatter-&gt;setRowFormat('&lt;table&gt;%error%%field%%help%%hidden_fields%&lt;/table&gt;');

        ...
    }
</pre>
<p>Egy jó postvalidator leírás:<br />
<a href="http://blog.codeclarity.com/2010/03/09/conditional-validation-in-symfony-forms/"><br />
blog.codeclarity.com/2010/03/09/conditional-validation-in-symfony-forms/</a></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.tlsys.hu/symfony-parancsok/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Symfony widgetek</title>
		<link>http://blog.tlsys.hu/symfony-widgetek/</link>
		<comments>http://blog.tlsys.hu/symfony-widgetek/#comments</comments>
		<pubDate>Mon, 25 Jan 2010 14:16:32 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Symfony]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://blog.tlsys.hu/symfony-widgetek/</guid>
		<description><![CDATA[
			
			
			
			
			
			
			Tweet
						
						
			Symfony widgeteket fogok ide kirakni, néhol egy icipici kis magyarázattal.

datePicker:

class datePickerWidget extends sfWidgetFormInput
{

  public function configure($options = array(), $attributes = array())
  {
    $this-&#62;addOption('ifFormat', &#34;%Y-%m-%d&#34;);
    parent::configure($options, $attributes);
  }

  public function render($name, $value = null, $attributes = array(), $errors = array())
  {
    use_helper('Javascript', [...]]]></description>
			<content:encoded><![CDATA[<div class="bottomcontainerBox" style="border:1px solid #808080;background-color:#F0F4F9;">
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fblog.tlsys.hu%2Fsymfony-widgetek%2F&amp;layout=button_count&amp;show_faces=false&amp;width=85&amp;action=like&amp;font=verdana&amp;colorscheme=light&amp;height=21" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width=85px; height:21px;" allowTransparency="true"></iframe></div>
			<div style="float:left; width:80px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<g:plusone size="medium" href="http://blog.tlsys.hu/symfony-widgetek/"></g:plusone>
			</div>
			<div style="float:left; width:95px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<a href="http://twitter.com/share" class="twitter-share-button" data-url="http://blog.tlsys.hu/symfony-widgetek/"  data-text="Symfony widgetek" data-count="horizontal">Tweet</a>
			</div><div style="float:left; width:105px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script type="in/share" data-url="http://blog.tlsys.hu/symfony-widgetek/" data-counter="right"></script></div>			
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script src="http://www.stumbleupon.com/hostedbadge.php?s=1&amp;r=http://blog.tlsys.hu/symfony-widgetek/"></script></div>			
			</div><div style="clear:both"></div><div style="padding-bottom:4px;"></div><p>Symfony widgeteket fogok ide kirakni, néhol egy icipici kis magyarázattal.<br />
<span id="more-139"></span></p>
<p><strong>datePicker:</strong></p>
<pre class="brush: php; title: ; notranslate">
class datePickerWidget extends sfWidgetFormInput
{

  public function configure($options = array(), $attributes = array())
  {
    $this-&gt;addOption('ifFormat', &quot;%Y-%m-%d&quot;);
    parent::configure($options, $attributes);
  }

  public function render($name, $value = null, $attributes = array(), $errors = array())
  {
    use_helper('Javascript', 'wtCurrency');
    $response = sfContext::getInstance()-&gt;getResponse();
    $response-&gt;addStylesheet('/sf/calendar/calendar-system.css');
    $response-&gt;addJavascript('/sf/calendar/calendar.js');
    $response-&gt;addJavascript('/sf/calendar/lang/calendar-en.js');
    $response-&gt;addJavascript('/sf/calendar/calendar-setup.js');
    $response-&gt;addJavascript(sfConfig::get('sf_prototype_web_dir').'/js/prototype');

    $picker = javascript_tag(&quot;
      Calendar.setup(
      {
        inputField  : '&quot;.$this-&gt;generateId($name).&quot;',
        ifFormat    : '&quot;.$this-&gt;getOption('ifFormat').&quot;',
        button      : 'trigger',    // ID of the button
      })
    &quot;);
    return parent::render($name, $value, $attributes, $errors) . $picker;
  }
}
</pre>
<p><strong>Autocompliter:</strong><br />
<a href="http://www.symfony-project.org/plugins/sfExtraWidgetsPlugin/1_0_5">innen az eredeti</a></p>
<pre class="brush: php; title: ; notranslate">
class sfExtraWidgetFormInputAutocomplete extends sfWidgetFormInput
{
    public function configure($options = array(), $attributes = array())
    {
        $this-&gt;addRequiredOption('url');
        $this-&gt;addOption('param', 'autocomplete');
        $this-&gt;addOption('min_chars', 2);
        $this-&gt;addOption('afterUpdateElement','');
        parent::configure($options, $attributes);
    }

    public function render($name, $value = null, $attributes = array(), $errors = array())
    {
        $response = sfContext::getInstance()-&gt;getResponse();
        $response-&gt;addJavascript(sfConfig::get('sf_prototype_web_dir').'/js/prototype');
        $response-&gt;addJavascript(sfConfig::get('sf_prototype_web_dir').'/js/scriptaculous.js');
        sfLoader::loadHelpers(array('Javascript'));
        $response-&gt;addStylesheet('/sfExtraWidgetsPlugin/css/autocompleter.css');

        $autocompleteDiv = content_tag('div' , '', array('id' =&gt; $this-&gt;generateId($name) . '_autocomplete', 'class' =&gt; 'autocomplete'));

        $autocompleteJs = javascript_tag(
            &quot;function ac_update_&quot; . $this-&gt;generateId($name) . &quot;(text, li)
            {
                $('&quot; . $this-&gt;generateId($name) . &quot;').value = li.innerHTML;
                &quot;.$this-&gt;getOption('afterUpdateElement').&quot;
            }

            new Ajax.Autocompleter(
                '&quot; . $this-&gt;generateId($name) . &quot;',
                '&quot; . $this-&gt;generateId($name) . '_autocomplete' . &quot;',
                '&quot; . url_for($this-&gt;getOption('url')) . &quot;',
                {
                    paramName: '&quot; . $this-&gt;getOption('param') . &quot;',
                    indicator: 'indicator-&quot; . $this-&gt;generateId($name) . &quot;',
                    minChars: &quot; . $this-&gt;getOption('min_chars') . &quot;,
                    afterUpdateElement: ac_update_&quot; . $this-&gt;generateId($name) . &quot;
                });&quot;
            );

        return parent::render($name, $value, $attributes, $errors) .
        '&lt;span id=&quot;indicator-' . $this-&gt;generateId($name) . '&quot; style=&quot;display: none;&quot;&gt;&amp;nbsp;&amp;nbsp;&lt;img src=&quot;/sfExtraWidgetsPlugin/img/ajax-loader.gif&quot; align=&quot;absmiddle&quot; alt=&quot;Loading&quot; /&gt;&lt;/span&gt;' .
        $autocompleteDiv .
        $autocompleteJs;
    }
}
</pre>
<p>használata:<br />
widget:</p>
<pre class="brush: php; title: ; notranslate">
$this-&gt;widgetSchema['nevsearch']     = new sfExtraWidgetFormInputAutocomplete(array(
            'url'=&gt;'modul/action',
            'afterUpdateElement'=&gt;'afterUpdateElement_nevsearch(text, li)'));
// ezt a javascript függvényt létre kell hozni.
//vagy egyszerűen az eredti módszerrel:
$this-&gt;widgetSchema['projekt']   = new sfExtraWidgetFormInputAutocomplete(array('url'=&gt;'modul/action'));
</pre>
<p>actionSuccess.php</p>
<pre class="brush: php; title: ; notranslate">
&lt;ul&gt;
  &lt;?php foreach ($words as $value):?&gt;
    &lt;li id='&lt;?php echo $value?&gt;'&gt;&lt;?php echo $value?&gt;&lt;/li&gt;
  &lt;?php endforeach?&gt;
&lt;/ul&gt;
</pre>
<p><strong> checkbox</strong></p>
<pre class="brush: php; title: ; notranslate">$this-&gt;widgetSchema['checkbox'] = new sfWidgetFormInputCheckbox();
$this-&gt;validatorSchema['checkbox'] = new sfValidatorPass();</pre>
<p><strong> checkbox rejtett false értékkel</strong><br />
A&#8217; la cakephp. A lényeg hogy vizsgálhassuk a mező értékét, mert a symfonyban alapból nem jön semmi a post adatokkal, ha a checkbox nincs kiválasztva&#8230;</p>
<pre class="brush: php; title: ; notranslate">
class sfWidgetFormInputCheckboxExtend extends sfWidgetFormInputCheckbox
{
  public function render($name, $value = null, $attributes = array(), $errors = array())
  {
    $hidden = new sfWidgetFormInputHidden();
    $hidden = $hidden-&gt;render($name, 0, array('id'=&gt;false));

    $value = ($value == 0) ? null : $value;
    $attributes['value'] = 1;

    return $hidden.parent::render($name, $value, $attributes, $errors);
  }
}
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.tlsys.hu/symfony-widgetek/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Adatok exportálása csv fájlba</title>
		<link>http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/</link>
		<comments>http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/#comments</comments>
		<pubDate>Wed, 13 Jan 2010 14:15:40 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Symfony]]></category>
		<category><![CDATA[PHP]]></category>

		<guid isPermaLink="false">http://blog.tlsys.hu/?p=33</guid>
		<description><![CDATA[
			
			
			
			
			
			
			Tweet
						
						
			a eredeti hogyan:
Symfony Howto: Export tabular data to a csv file?
Ennek teljese kidolgozott változata található itt.
A mymodule/Csv az adatokat ;-vel elválasztva megjeleníti.
Action:

&#60;?php
class mymoduleActions extends autoMyActions
{
  public function executeCsv(sfWebRequest $request)
  {
    $this-&#62;pager = $this-&#62;getPager();
    $c=$this-&#62;pager-&#62;getCriteria();
    $c-&#62;setLimit(false);
    $this-&#62;rows=$this-&#62;pager-&#62;getResults();
     // [...]]]></description>
			<content:encoded><![CDATA[<div class="bottomcontainerBox" style="border:1px solid #808080;background-color:#F0F4F9;">
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<iframe src="http://www.facebook.com/plugins/like.php?href=http%3A%2F%2Fblog.tlsys.hu%2Fadatok-exportalasa-csv-fajlba%2F&amp;layout=button_count&amp;show_faces=false&amp;width=85&amp;action=like&amp;font=verdana&amp;colorscheme=light&amp;height=21" scrolling="no" frameborder="0" style="border:none; overflow:hidden; width=85px; height:21px;" allowTransparency="true"></iframe></div>
			<div style="float:left; width:80px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<g:plusone size="medium" href="http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/"></g:plusone>
			</div>
			<div style="float:left; width:95px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;">
			<a href="http://twitter.com/share" class="twitter-share-button" data-url="http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/"  data-text="Adatok exportálása csv fájlba" data-count="horizontal">Tweet</a>
			</div><div style="float:left; width:105px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script type="in/share" data-url="http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/" data-counter="right"></script></div>			
			<div style="float:left; width:85px;padding-right:10px; margin:4px 4px 4px 4px;height:30px;"><script src="http://www.stumbleupon.com/hostedbadge.php?s=1&amp;r=http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/"></script></div>			
			</div><div style="clear:both"></div><div style="padding-bottom:4px;"></div><p>a eredeti hogyan:<br />
<a href="http://trac.symfony-project.org/wiki/HowToExportTabularData#SymfonyHowto:Exporttabulardatatoacsvfile">Symfony Howto: Export tabular data to a csv file?</a><br />
Ennek teljese kidolgozott változata található itt.<br />
<span id="more-33"></span>A mymodule/Csv az adatokat ;-vel elválasztva megjeleníti.<br />
Action:</p>
<pre class="brush: php; title: ; notranslate">
&lt;?php
class mymoduleActions extends autoMyActions
{
  public function executeCsv(sfWebRequest $request)
  {
    $this-&gt;pager = $this-&gt;getPager();
    $c=$this-&gt;pager-&gt;getCriteria();
    $c-&gt;setLimit(false);
    $this-&gt;rows=$this-&gt;pager-&gt;getResults();
     // $response = $this-&gt;getResponse();
     // $response-&gt;setHttpHeader('Content-type', 'application/msexcel');
     // $response-&gt;setHttpHeader('Content-Disposition', 'attachment; filename=akarmi.csv');
  }
}
</pre>
<p>csvSuccess.php:</p>
<pre class="brush: php; title: ; notranslate">
&lt;?php
 use_helper('I18N');
 $rowBefore = '';
 $rowAfter  = &quot;\r\n&quot;;
 $cellBefore = '';
 $cellAfter = ';';
 $cellHeadBefore = '';
 $cellHeadAfter =';';
 echo $rowBefore;
 echo $cellHeadBefore.iconv('UTF-8', 'WINDOWS-1250', __('Head1')).$cellHeadAfter;
 echo $cellHeadBefore.iconv('UTF-8', 'WINDOWS-1250', __('Head1')).$cellHeadAfter;
 echo $rowAfter;
 foreach($rows as $row)
 {
   echo $rowBefore;
   echo $cellBefore.iconv('UTF-8', 'WINDOWS-1250', $row-&gt;getMezo1()).$cellAfter;
   echo $cellBefore.iconv('UTF-8', 'WINDOWS-1250', $row-&gt;getMezo2()).$cellAfter;
   echo $rowAfter;
 }
</pre>
<p>Ezután már csak a következőket kell beállítani:</p>
<ul>
<li>vigyünk fel egy új routing szabályt a routing.yml fájlba
<pre class="brush: plain; title: ; notranslate">
export_excel:
  url:    /export.csv
  param:  {module: myModule, action: csv}
</pre>
</li>
</ul>
<ul>
<li>Apache mod_rewrite esetén egy új szabályra van szükség az apache .htaccess fájlba a .csv fájlok elérése végett.
<pre class="brush: plain; title: ; notranslate">RewriteCond %{REQUEST_URI} !\.csv$</pre>
</li>
</ul>
<ul>
<li>A mymodule/config/view.yml fájlba vigyük fel az aléábbi sorokat:
<pre class="brush: plain; title: ; notranslate">
csvSuccess:
  has_layout: off
  http_metas:
    content-type: application/msexcel
    Content-Disposition: attachment; filename=mymodule_&lt;?php echo date('Ymd')?&gt;.csv</pre>
</li>
<li> vagy az actionben
<pre class="brush: php; title: ; notranslate">
      $response = $this-&gt;getResponse();
      $response-&gt;setHttpHeader('Content-type', 'application/msexcel');
      $response-&gt;setHttpHeader('Content-Disposition', 'attachment; filename=mymodule-'.date('Ymd').'.csv');
      $this-&gt;setLayout(false);
</pre>
</li>
</ul>
<p><a href="http://weblogs.asp.net/michu/archive/2004/06/15/155851.aspx">még egy fontos dolog:</a><br />
Vagyis ha a szokványos módon csak egy táblázatot teszünk ki és azt mondjuk hogy az egy Excel fájl, akkor néha szükség lehet egy cellában több sorra is, akkor a &lt;br&gt; az alábbi stílussal fog működni:</p>
<pre class="brush: php; title: ; notranslate">
br {mso-data-placement:same-cell;}
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.tlsys.hu/adatok-exportalasa-csv-fajlba/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

