Pages
-
Categories
-
Tags
8088 amici annotation api basic benchmark blacknwhite bug captioning charset charts cinema css dilbert dokuwiki drag&drop film firebug firefox foto funny gomorra google hack ie javascript javscript jgcharts jpaging jquery linux php php pattern plugins proxy resize saviano thablesorter togglepanel tutorial ubuntu ui websense ycodaslider youtube
programming
real life
-
RSS Feeds
comodoclick
LINKS:
FUNZIONALITA’:
- Aggiunge la classe “hover” ai td di una certa riga di tabella (tr > td) sull’evento hover del tr
- Aggiunge la classe “selected” ai td di una certa riga di tabella (tr > td) sull’evento click del td
- Aggiunge la classe “selected” ai td di una certa riga di tabella al click sui controlli form checkbox e radio (di conseguenza anche al click sulle label) presenti sulla riga stessa
- Nel caso di input:radio la classe selected viene prima cancellata dalle altre righe e poi applicata alla riga “selezionata”
AUTOLOAD
Per attivarlo basta includere gli scripts (jquery, comodoclick) e aggiungere la classe comodoclick ad una tabella.
<script src="jquery-1.3.2.min.js" type="text/javascript"></script>
<script src="comodoclick.js" type="text/javascript"></script>
<table class="comodoclick">
CSS
Personalizzare a piacere queste classi css:
table.comodoclick tr td.hover {background-color:red;}
table.comodoclick tr td.selected {background-color:green;}
CODE
Il plugin con qualche nota:
/*
* Copyright (c) 2008 Massimiliano Balestrieri
*
* @requires jQuery v1.3.2
*
* Copyright (c) 2008 Massimiliano Balestrieri
* Examples and docs at: http://maxb.net/blog/
* Licensed GPL licenses:
* http://www.gnu.org/licenses/gpl.html
*/
;
(function($){
function ComodoClick(){
return this.each(function(){
var that = this;
jQuery("tr", this).hover(function(){
jQuery("td", this).addClass("hover");
}, function(){
jQuery("td", this).removeClass("hover");
});
jQuery("tr", this).click(function(e){
var _target = e.target || e.srcElement;
var _tag = _target.tagName.toString().toLowerCase();
//prendo solo il click sul td
//se ci fossero tag di tipo blocco dentro il td sarebbe un problema
//se invece clicco su una input o su una label gestisco tutto con l'evento -> VEDI SOTTO
if (_tag === 'td') {
var _tr = jQuery(this);
_highlight_row(_tr, true);
}
//return false;
});
//vedi sotto A
jQuery("tr", this).find("input:checkbox, input:radio").bind("click", function(){
var _tr = jQuery(this).parents("tr");
_highlight_row(_tr, true);
});
//vedi sotto B
jQuery("tr", this).find("input:checkbox").bind("checked", function(){
var _tr = jQuery(this).parents("tr");
_highlight_row(_tr, false);
});
var _highlight_row = function(_tr, flag){
//il flag è per selezionare la checkbox/radio forzatamente
//checkbox gestisce la "multiselezione"
var _checkbox = jQuery("input:checkbox", _tr).length > 0;
//nel caso dei radio cancello le altre colorazioni
if (!_checkbox) {
jQuery("td", that).removeClass("selected");
jQuery("tr", that).removeClass("selected");
jQuery("td", _tr).addClass("selected");
_tr.addClass("selected");
if (flag) {
jQuery("input:radio", _tr).attr("checked", "checked");
}
}
else {
var _selected = _tr.is(".selected");
if (_selected) {
jQuery("td", _tr).removeClass("selected");
_tr.removeClass("selected");
jQuery("input:checkbox", _tr).attr("checked", "");
}
else {
jQuery("td", _tr).addClass("selected");
_tr.addClass("selected");
jQuery("input:checkbox", _tr).attr("checked", "checked");
}
}
};
//A: triggero click per colorare la riga
jQuery("input:radio:checked", that).trigger("click");
//B: triggero checked -> se usassi il click la checkbox si deselezionerebbe
jQuery("input:checkbox:checked", that).trigger("checked");
});
}
$.fn.comodoclick = ComodoClick;
//AUTOLOAD
$(document).ready(function(){
$('table.comodoclick').comodoclick();
});
})(jQuery);
Tagged javascript, jquery, plugins, table
WsCrud - esempio di webservice con nusoap/php
LINK DEMO:
ISTRUZIONI:
- Estrarre il pacchetto (htdocs del vostro webserver)
- configurare il file config/config.php
define('DB_HOST', '');//esempio localhost
define('DB_USER', '');//esempio wscrud
define('DB_NAME', '');//esempio wscrud
define('DB_PWD', '');//esempio wscrud
define('WSDL', '');//esempio http://maxb.net/scripts/wscrud/?wsdl
- creare il database e importare il dump presente in config/db.sql
LIBRERIE DA SCARICARE A PARTE:
Una volta scaricate ed estratte le librerie dovranno essere inserite nella directory libs come nell’immagine.
Non sono un grande esperto di servizi. Mi è capitato di farne e di usufruirne.
Questa volta ho deciso di estrapolare dall’ultimo lavoro una sorta di scheletro.
Il servizio spiegato:
Inclusioni di librerie:
require_once(dirname(__FILE__) . '/libs/adodb_lite/adodb.inc.php');
require_once(dirname(__FILE__) . '/libs/nusoap-0.7.3/lib/nusoap.php');
require_once(dirname(__FILE__) . '/config/config.php');
require_once(dirname(__FILE__) . '/includes/exception.php');
require_once(dirname(__FILE__) . '/includes/application.php');
require_once(dirname(__FILE__) . '/includes/conn.php');
require_once(dirname(__FILE__) . '/includes/db.php');
Inizializzazione server (vedere il config per capire le costanti):
$server = new nusoap_server();
$server->configureWSDL(APP_NAME_SPACE,APP_TARGET_NAME_SPACE);
$server->wsdl->schemaTargetNamespace = APP_TARGET_NAME_SPACE;
Tipi complessi registrati:
$server->wsdl->addComplexType(
'record',
'complexType',
'struct',
'all',
'',
array(
'id' => array('name'=>'id','type'=>'xsd:int'),
'text' => array('name'=>'text','type'=>'xsd:string'),
)
);
$server->wsdl->addComplexType(
'array_of_record',
'complexType',
'array',
'',
'SOAP-ENC:Array',
array(),
array(array('ref'=>'SOAP-ENC:arrayType','wsdl:arrayType'=>'tns:record[]')),
'tns:record'
);
I metodi esposti:
$server->register(
'put_record',
array('text'=>'xsd:string'),
array('id'=>'xsd:int'),
APP_URN,
APP_URN . '#put_record',
'rpc',
'encoded',
''
);
function put_record($text){
try{
$app = new MyApplication();
return $app->dao->put_record($text);
}catch(Exception $e){
return new soap_fault($e->getCode(), 'server', $e->getMessage());
}
}
$server->register(
'search_record',
array(
'id'=>'xsd:int',
'text'=>'xsd:string',
),
array('return'=>'tns:array_of_record'),
APP_URN,
APP_URN . '#search_record',
'rpc',
'encoded',
''
);
function search_record($id, $text){
try{
$app = new MyApplication();
return $app->dao->search_record($id, $text);
}catch(Exception $e){
return new soap_fault($e->getCode(), 'server', $e->getMessage());
}
}
$server->register(
'get_record',
array('id'=>'xsd:int'),
array('return'=>'tns:record'),
APP_URN,
APP_URN . '#get_record',
'rpc',
'encoded',
''
);
function get_record($id){
try{
$app = new MyApplication();
return $app->dao->get_record($id);
}catch(Exception $e){
return new soap_fault($e->getCode(), 'server', $e->getMessage());
}
}
$server->register(
'delete_record',
array('id'=>'xsd:int'),
array('return'=>'xsd:boolean'),
APP_URN,
APP_URN . '#delete_record',
'rpc',
'encoded',
''
);
function delete_record($id){
try{
$app = new MyApplication();
return $app->dao->delete_record($id);
}catch(Exception $e){
return new soap_fault($e->getCode(), 'server', $e->getMessage());
}
}
$server->register(
'update_record',
array('id'=>'xsd:int', 'text' => 'xsd:string'),
array('return'=>'xsd:boolean'),
APP_URN,
APP_URN . '#update_record',
'rpc',
'encoded',
''
);
function update_record($id, $text){
try{
$app = new MyApplication();
return $app->dao->update_record($id, $text);
}catch(Exception $e){
return new soap_fault($e->getCode(), 'server', $e->getMessage());
}
}
L’output del “server”:
$HTTP_RAW_POST_DATA = isset($HTTP_RAW_POST_DATA) ? $HTTP_RAW_POST_DATA : file_get_contents("php://input");
$server->service($HTTP_RAW_POST_DATA);
Attenzione a quel file_get_contents(”php://input”);
Ho sclerato parecchio per far girare questo servizio sul mio hosting.
IL CLIENT
L’esempio del client VERAMENTE basico senza librerie senza divisioni.
GREZZO. Anche l’html. Giusto il form e il meta per la codifica di invio dei dati.
require_once(dirname(__FILE__) . '/../config/config.php');
error_reporting(E_ALL);
function get_client(){
require_once(dirname(__FILE__) . '/../libs/nusoap-0.7.3/lib/nusoap.php');
$url = WSDL;
$client = new nusoap_client( $url, true );
return $client;
}
$client = get_client();
$args = array();
$records = $client->call( 'search_record', $args );
if(isset($_POST['save'])){
$_POST['text'] = stripslashes($_POST['text']);
$client = get_client();
if($_POST['id'] == 0){
$args = array( 'text' => $_POST['text']);
$result = $client->call( 'put_record', $args );
}else{
$args = array( 'id' => $_POST['id'], 'text' => $_POST['text']);
$result = $client->call( 'update_record', $args );
}
header('Location:?do=index');
}
$do = isset($_GET['do']) ? $_GET['do'] : false;
$data = array('id' => 0, 'text' => '');
switch($do){
case 'edit':
$client = get_client();
$args = array( 'id' => $_GET['id']);
$data = $client->call( 'get_record', $args );
break;
case 'delete':
$client = get_client();
$args = array( 'id' => $_GET['id']);
$result = $client->call( 'delete_record', $args );
header('Location:?do=index');
break;
}
<meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
<form method="post" action="#">
<p><textarea name="text" id="text"><?php echo $data['text']?></textarea></p>
<p>
<input type="hidden" name="id" id="id" value="<?php echo $data['id'] ?>" />
<input type="submit" name="save" id="save" value="save" />
</p>
</form>
<table>
<thead>
<tr>
<th>ID</th>
<th>TEXT</th>
<th>ACTIONS</th>
<tr>
</thead>
<?php if(isset($records[0])){ ?>
<tbody>
<?php foreach($records as $k => $v){ ?>
<tr>
<td><?php echo $v['id']?></td>
<td><?php echo $v['text']?></td>
<td>
<a href="?do=edit&id=<?php echo $v['id']?>">edit</a>
<a href="?do=delete&id=<?php echo $v['id']?>">del</a>
</td>
<tr>
<?php } ?>
</tbody>
<?php } ?>
<table>
All’interno della directory client troverete due client nativi (estensione soap del php5) : client2.php e client3.php.
Su questo hosting non girano.
Provateli se volete. client3.php usa il metodo “ufficiale” per chiamare i metodi remoti. NON FUNZIONA!
Tagged nusoap, php, soap, webservice, ws
Jaunty Jackalope & Aptana
C’è un problema tra Aptana e le ultime 2 versioni di ubuntu: XulRunner.
Ubuntu non ha mantenuto nei repository XulRunner di Firefox 2.
Io ho seguito queste istruzioni.
- scaricare xulrunner-1.8.1.3
- estrarre il tar.gz
- spostare il contenuto estratto in /usr/lib (sudo mv xulrunner-1.8.1.3 /usr/lib/)
- installare via synaptic/apt java 1.6 (sun)
- creare un file sh eseguibile nella directory di aptana e usare l’sh per lanciare l’ide
#!/bin/bash
MOZILLA_FIVE_HOME=/usr/lib/xulrunner-1.8.1.3
if [ $LD_LIBRARY_PATH ]; then
LD_LIBRARY_PATH=$MOZILLA_FIVE_HOME:$LD_LIBRARY_PATH
else
LD_LIBRARY_PATH=$MOZILLA_FIVE_HOME
fi
JAVA_HOME=/usr/lib/jvm/java-6-sun
export MOZILLA_FIVE__HOME
export LD_LIBRARY_PATH
export JAVA_HOME
echo $MOZILLA_FIVE_HOME $JAVA_HOME $LD_LIBRARY_PATH
/opt/aptana/AptanaStudio -vm /usr/lib/jvm/java-6-sun/jre/bin/java
Tagged aptana, jaunty, ubuntu, xulrunner
Jaunty Jackalope - Nvidia Separate X-screen & Gnome
Ieri ho installato Jaunty, la “lepre cornuta”.
Tutto bene. Ho installato da zero su una partizione vuota. Ho configurato il sistema e installato tutta una serie di applicazioni che mi servono per lavoro (vmware, sqldeveloper, skype, java, eclipse, lampp, filezilla).
Per vmware ho seguito le istruzioni per ubuntu 8.10, soprattutto queste.
Miglioramenti evidenti non ne ho visti. L’icona di “wait” è tornata quella standard. Nella 8.10 ogni volta che il sistema entrava in stato di wait il cursore prendeva la forma di “infinito” scentrata rispetto al cursore col risultato che invece di aprire una certa applicazione ne aprivi un altra (o peggio).
Altra miglioria: il sistema di “focus” con doppio monitor. Prima bastava spostare il mouse su un monitor per spostare il focus. Ora devi cliccare. Per me era un bug non certo una funzionalità.
A parte questo il sistema è identico. Magagne comprese. Presenta lo stesso problema sul doppio monitor. Quando lanci un applicazione dal monitor secondario (driver nvidia, configurazione separate X-screen) l’applicazione parte sul monitor 1.
Ho risolto usando uno script “ponte”.
Ho creato un file eseguibile nella mia home
touch /home/max/bin/display.sh
chmod +x /home/max/bin/display.sh
Il ponte fa solamente questo:
#!/bin/bash
DISPLAY=":0.1" $1
A questo punto è stato sufficiente precedere nel launcher il ponte.
Tasto destro -> Proprietà -> Comando
DA
/opt/eclipse-3.3.1.1/eclipse
A
/home/max/bin/display.sh /opt/eclipse-3.3.1.1/eclipse
E così per tutti i launchers del monitor secondario (nautilus, kate, gedit, gnome-terminal).
Per concludere… rimango un nostalgico di kde3.
Maledetta Trolltech!
MyPearLogComposite
Pubblico una classe per effettuare il log composito con PEAR::Log.
In sviluppo il log potrà essere usato in maniera abbondante (entrata/uscita dei metodi ad esempio). Questo causerà frequenti accessi al file di log.
In produzione la maschera impostata nello switch eviterà l’accesso al file per i log di tipo PEAR_LOG_DEBUG (valore di default) ma manterrà i log di tipo ERROR e i log di tipo EMERG.
In più per il log di tipo EMERG verrà inviata una mail. Il metodo _rotate della classe garantirà una rotazione del file al raggiungimento di N bytes (vedi costante LOG_SIZE_ROTATION).
set_include_path(dirname(__FILE__) .'/lib/PEAR-1.7.2/:'.get_include_path());
require_once(dirname(__FILE__) . '/lib/PEAR-1.7.2/PEAR.php');
require_once(dirname(__FILE__) . '/lib/Log-1.11.3/Log.php');
require_once(dirname(__FILE__) . '/lib/Mail-1.2.0b1/Mail.php');
$env = 1;
switch($env){
case 0://development
define('MASK_ERROR', PEAR_LOG_DEBUG);
break;
case 1://production
define('MASK_ERROR', PEAR_LOG_ERR);
break;
}
define('APPLICATION_NAME', 'mylog');
define('MAIL_MASK_ERROR', PEAR_LOG_EMERG);
define('MAIL_WEBMASTER', 'MAILTO');
define('MAIL_FROM', 'MAILFROM');
define('LOG_FILE', dirname(__FILE__) . '/logs/'.APPLICATION_NAME.'.txt');
define('LOG_SIZE_ROTATION',1000000);
class MyPearLogComposite{
public $logger;
public function __construct(){
$this->_check_rotate();
$conf = array('mode' => 0600, 'timeFormat' => '%X %x');
$file = &Log::singleton('file', LOG_FILE, APPLICATION_NAME , $conf);
$mask = Log::MAX(MASK_ERROR);
$file->setMask($mask);
$conf = array('from' => MAIL_FROM,'subject' => APPLICATION_NAME . ' Important log events');
$mail = &Log::singleton('mail', MAIL_WEBMASTER, APPLICATION_NAME, $conf);
$mask = Log::MAX(MAIL_MASK_ERROR);
$mail->setMask($mask);
$this->logger = &Log::singleton('composite');
$this->logger->addChild($file);
$this->logger->addChild($mail);
}
private function _check_rotate(){
$size = @filesize(LOG_FILE);
if($size > LOG_SIZE_ROTATION)
$this->_rotate();
}
private function _rotate(){
$file = LOG_FILE . '.' . date('Y-m-d');
rename(LOG_FILE, $file);
}
}
$log = new MyPearLogComposite();
$log->logger->log('log something');
$log->logger->log('log log');
$log->logger->log('log error', PEAR_LOG_ERR);
$log->logger->log('emergency', PEAR_LOG_EMERG);
//in development
//log file:
/*
12:32:30 24/04/2009 mylog [info] log something
12:32:30 24/04/2009 mylog [info] log log
12:32:30 24/04/2009 mylog [error] log error
12:32:30 24/04/2009 mylog [emergency] emergency
*/
//mail:
/*
To: MAILTO
Subject: mylog Important log events
From: MAILFROM
User-Agent: PEAR Log Package
Apr 24 12:40:25 mylog [emergency] emergency
*/
//in production
//log file:
/*
12:42:25 04/24/09 mylog [error] log error
12:42:25 04/24/09 mylog [emergency] emergency
*/
//mail:
/*
To: MAILTO
Subject: mylog Important log events
From: MAILFROM
User-Agent: PEAR Log Package
Apr 24 12:42:25 mylog [emergency] emergency
*/
Tagged log, pear, php, snippets
Redditi 2006
Risulta che:
- il 35% degli italiani dichiara meno di 10mila euro lordi (quanti ristoratori?)
- 800mila italiani dichiarano più di 70mila euro annui
- 68mila italiani dichiarano più di 200mila euro lordi
- in italia ci sono 65mila barche sopra i 17 metri
- nel 2006 sono state immatricolate 200mila auto di lusso
Audio estratto dal programma radiofonico di Sebastiano Barisoni (radio24) Focus Economia
Audio clip: Adobe Flash Player (version 9 or above) is required to play this audio clip. Download the latest version here. You also need to have JavaScript enabled in your browser.
Javascript non intrusivo
… spiegato per negazioni.
Questo non è javascript non intrusivo.
<div class="linkFinali">
<script type="text/javascript">
//<![CDATA[
document.write("<a href=\"javascript:history.back();\" onkeypress=\"if(event.keyCode != 9){doSomething();}\" rel=\"prev\">indietro<\/a>");
//]]>
</script>
<noscript><div class="inline"> </div></noscript>
</div>
Tagged antipattern, javascript
Traceroute maxb.net
Ultimamente ho problemi nel raggiungere il mio blog.
Facendo un traceroute a volte capita questo:
9 gi9-6.ccr01.mil01.atlas.cogentco.com (130.117.15.89) 19.124 ms 18.811 ms *
10 te2-2.ccr01.str01.atlas.cogentco.com (130.117.3.17) 34.789 ms te3-8.ccr01.str01.atlas.cogentco.com (154.54.1.237) 41.030 ms te3-2.ccr01.str01.atlas.cogentco.com (130.117.1.113) 36.981 ms
11 * * *
12 * * *
13 te3-2.mpd01.ymq02.atlas.cogentco.com (154.54.0.70) 115.984 ms te4-2.mpd01.ymq02.atlas.cogentco.com (154.54.6.141) 116.149 ms te3-2.mpd01.ymq02.atlas.cogentco.com (154.54.0.70) 116.159 ms
14 te4-7.mpd01.yyz02.atlas.cogentco.com (154.54.25.25) 130.363 ms 132.890 ms 124.229 ms
15 netfirms.demarc.cogentco.com (38.99.210.114) 131.964 ms 129.519 ms 143.212 ms
16 * * *
17 * * *
18 * * *
19 * * *
20 * * *
21 * * *
22 * * *
23 * * *
24 * * *
25 * * *
26 * * *
27 * * *
28 * * *
29 * * *
30 * * *
Altre volte è tutto ok.
9 gi9-6.ccr01.mil01.atlas.cogentco.com (130.117.15.89) 16.954 ms 18.554 ms 15.981 ms
10 te3-2.ccr01.str01.atlas.cogentco.com (130.117.1.113) 26.014 ms te2-2.ccr01.str01.atlas.cogentco.com (130.117.3.17) 30.126 ms 33.005 ms
11 te3-2.mpd02.fra03.atlas.cogentco.com (130.117.3.81) 31.784 ms te4-2.mpd02.fra03.atlas.cogentco.com (130.117.0.193) 26.132 ms *
12 te3-1.ccr01.ams03.atlas.cogentco.com (130.117.2.202) 33.461 ms * 35.235 ms
13 te3-2.mpd01.ymq02.atlas.cogentco.com (154.54.0.70) 118.013 ms te4-2.mpd01.ymq02.atlas.cogentco.com (154.54.6.141) 122.766 ms te3-2.mpd01.ymq02.atlas.cogentco.com (154.54.0.70) 131.790 ms
14 te4-7.mpd01.yyz02.atlas.cogentco.com (154.54.25.25) 137.883 ms te8-6.mpd01.yyz02.atlas.cogentco.com (154.54.7.213) 133.390 ms te4-7.mpd01.yyz02.atlas.cogentco.com (154.54.25.25) 125.833 ms
15 netfirms.demarc.cogentco.com (38.99.210.114) 133.323 ms 132.206 ms 134.207 ms
16 w-213.netfirms.com (38.113.185.213) 132.826 ms 126.348 ms 135.912 ms
17 w-213.netfirms.com (38.113.185.213) 127.923 ms 129.281 ms 127.148 ms
Tagged traceroute
IE: resize timer
Se volete collegare qualcosa all’evento resize (su IE) vi conviene usare sempre questo snippet di codice (jQuery):
var _resize_timer = null;
$(window).bind('resize', function(ev) {
if (_resize_timer) clearTimeout(_resize_timer);
_resize_timer = setTimeout(function(){
//CODE
}, 100);
});
invece del semplice (e funzionante codice)
$(window).bind('resize', function(ev) {
//CODE
});
Provate voi stessi a ridimensionare la finestra (IE) :
http://maxb.net/scripts/ieresize/resize-ie.html
http://maxb.net/scripts/ieresize/resize.html













