- Requirements
- Installation
- Usage
- 1. The simple content-dialog
- 2. The ajax-dialog
- 3. The iframe-dialog
- 4. The EJuiDlgsColumn
- 5. Fancybox
- Resources
- Changelog
Render buttons/links/icons to display a CJuiDialog with a content / ajax-response / iframe with a single line of code.
Replace the standard CButtonColumn with the EJuiDlgsColumn of this extension to open the view and update action in a dialog like explained in the wiki articles (see Resources).
Easy using of the jQuery fancybox plugin. Works inside a ajax-enviroment.
Requirements ¶
Developed with Yii 1.1.10
Installation ¶
Extract the zip file into protected/extensions.
Register the components in the import section of config/main.php
// autoloading model and component classes
'import'=>array(
...
'ext.quickdlgs.*',
),
Usage ¶
Use the static methods from the EQuickDlgs class in a view to render buttons/links/icons to open a dialog. Take a look at the methods/parameters in the source of EQuickDlgs.php.
1. The simple content-dialog ¶
For example this can be used to display a 'More info' or 'Help' button in a form.
EQuickDlgs::contentButton(
array(
'content' => 'This is the help text', //$this->renderPartial('_help',array(),true),
'dialogTitle' => 'Help',
'dialogWidth' => 200,
'dialogHeight' => 300,
'openButtonText' => 'Help me',
'closeButtonText' => 'Close', //comment to remove the close button from the dialog
)
);
Use EQuickDlgs::contentLink, EQuickDlgs::contentIcon and EQuickDlgs::contentPopup the same way.
Note: ¶
All the content of the dialog will be loaded together with the page. Use an ajax-button, if you want to load the dialogcontent on the first button-click.
2. The ajax-dialog ¶
A icon for the view action of the current or another controller. You have to specify the 'controllerRoute' and the 'actionParams'
EQuickDlgs::ajaxIcon(
Yii::app()->baseUrl .'images/view.png',
array(
'controllerRoute' => 'view', //'member/view'
'actionParams' => array('id'=>$model->id), //array('id'=>$model->member->id),
'dialogTitle' => 'Detailview',
'dialogWidth' => 800,
'dialogHeight' => 600,
'openButtonText' => 'View record',
'closeButtonText' => 'Close',
)
);
If you 'reuse' a default controller view action inside a dialog, the full page (with header, menu ...) will be displayed. You have to 'renderPartial' instead of 'render'.
You simply have to replace the controller->render with EQuickDlgs::render. This will check if the request comes from a dialog. So it will work the standard way or within a dialog.
public function actionView($id)
{
EQuickDlgs::render('view',array('model'=>$this->loadModel($id)));
//$this->render('view',array('model'=>$this->loadModel($id)));
}
Note: ¶
You will have problems if you show list, create, update, admin action views inside an ajax-dialog, because the javascript (pagination ...) will not work as expected.
You can use an iframe-dialog instead of the ajax for that purpose.
Other ajax functions: EQuickDlgs::ajaxLink, EQuickDlgs::ajaxButton, EQuickDlgs::ajaxPopup
3. The iframe-dialog ¶
A remote url as iframe-dialog:
EQuickDlgs::iframePopup(
array(
'url' => 'http://www.yiiframework.com',
'dialogWidth' => 1024,
'dialogHeight' => 768,
'hideTitleBar' => true,
'closeButtonText' => 'Close',
);
If you want to place a 'Create' button in a admin-view above the CGridView:
EQuickDlgs::iframeButton(
array(
'controllerRoute' => 'create',
'dialogTitle' => 'Create item',
'dialogWidth' => 800,
'dialogHeight' => 600,
'openButtonText' => 'Create new',
'closeButtonText' => 'Close',
'closeOnAction' => true, //important to invoke the close action in the actionCreate
'refreshGridId' => 'group-grid', //the grid with this id will be refreshed after closing
)
);
In this case you have to make a few changes to the actionCreate method of the controller, because the dialog should be closed after saving the record.
The content should be rendered into a 'iframe' layout, because the application header, menu ... should not be visible, but the css/js-files should be present.
Edit and modify the default iframe-layout-file 'ext.quickdlgs.layouts.iframe' for your needs.
Like above, the EQuickDlgs::render method will do the rest.
public function actionCreate()
{
....
if(model->save())
{
//close the dialog and update the grid instead of redirect if called by the create-dialog
EQuickDlgs::checkDialogJsScript();
$this->redirect(array('admin'));
}
//check if the iframe layout (or renderPartial) has to be used
EQuickDlgs::render('create',array('model'=>$model));
//$this->render('create',array('model'=>$model));
}
Other iframe functions: EQuickDlgs::iframeLink, EQuickDlgs::iframeIcon
4. The EJuiDlgsColumn ¶
This buttoncolumn can be used as replacement for the standard CButtonColumn. It overrides the 'view' and 'update' buttons, the 'delete' or other custom buttons will work like inside the CButtonColumn.
'id'=>'group-grid',
'dataProvider'=>$model->search(),
'columns'=>array(
'id',
'name',
....
),
array(
'class'=>'EJuiDlgsColumn',
//configure like CButtonColumns:
//but some properties (buttons.view.url,buttons.view.id, buttons.view.ajax, buttons.update.click ...) will be set by the component
//'template'=>'{view}',
'viewButtonImageUrl'=>Yii::Yii::app()->baseUrl .'images/dialogview.png',
'buttons'=>array(
'view' => array(
'label'=> 'ajax dialog view',
),
'delete' => array(
'label'=> 'someLabel',
),
),
//---------- additional config for the dialogs starts here -------------
//if you want to use a custom dialog config: default is 'ext.quickdlgs.juimodal'
//'viewDialogConfig' => 'ext.quickdlgs.mycustomjuiattributes'
//don't override the CButtonColumn view button
//'viewDialogEnabled' = false,
//the attributes for the EAjaxJuiDlg widget: use like the 'attributes' param from EQuickDlgs::ajaxButton above
'viewDialog'=>array(
//'controllerRoute' => 'view', //=default
//'actionParams' => array('id' => '$data->primaryKey'), //=default
'dialogTitle' => 'View detail',
'hideTitleBar' => true,
//'dialogWidth' => 800, //use the value from the dialog config
//'dialogHeight' => 600,
),
//the attributes for the EFrameJuiDlg widget. use like the 'attributes' param from EQuickDlgs::iframeButton
'updateDialog'=>array(
//'controllerRoute' => 'update', //=default
//'actionParams' => array('id' => '$data->primaryKey'), //=default
'dialogTitle' => 'View detail',
'dialogWidth' => 1024, //override the value from the dialog config
'dialogHeight' => 600,
),
),
),
See the code of the EJuiDlgsColumn for more options.
As a descandant of the CButtonColumn all other attributes/possibilities are the same.
The default attributes are generated from the file 'ext.quickdlgs.config.juimodal'. You can change this by setting the property 'viewDialogConfig'.
Important: ¶
The button 'view' will open an ajax-dialog, the 'update' an iframe-dialog. So you have the change the code of the actionView and the actionCreate like above.
public function actionView($id)
{
EQuickDlgs::render('view',array('model'=>$this->loadModel($id)));
//$this->render('view',array('model'=>$this->loadModel($id)));
}
public function actionUpdate($id)
{
....
if(model->save())
{
//close the dialog and update the grid instead of redirect if called by the update-dialog
EQuickDlgs::checkDialogJsScript();
$this->redirect(array('admin','id'=>$model->id));
}
//check if the iframe layout (or renderPartial) has to be used
EQuickDlgs::render('update',array('model'=>$model));
//$this->render('update',array('model'=>$model));
}
The EJuiDlgsColumn does all the coding explained in the wiki-articles.
Tip: You can add an additional buttoncolum to list the records of a related model.
Assume you have a 'function actionList($parentId)' in a MemberController with a view that uses CListView and the records are filtered by the 'parendId'.
Because of the js-code in the view (CListView with pagination...) you should use the iframe-dialog of the 'update' button (not the ajax of the view button).
$this->widget('zii.widgets.grid.CGridView', array(
'id'=>'mygrid',
'dataProvider'=>$model->search(),
'columns'=>array(
'id',
'name',
...
array(
'class'=>'EJuiDlgsColumn', //all default for the view, update
),
array(
'class'=>'EJuiDlgsColumn',
'template'=>'{update}',
'updateButtonImageUrl'=>Yii::Yii::app()->baseUrl .'images/viewdetaildialog.png',
'updateDialog'=>array(
'controllerRoute' => 'members/list',
'actionParams' => array('parentId'=>'$data->id'),
'dialogTitle' => 'View detail',
'dialogWidth' => 1024, //override the value from the dialog config
'dialogHeight' => 600,
),
),
),
5. Fancybox ¶
Use the EFancybox widget and place the items inside beginWidget and endWidget.
$widget=$this->beginWidget('ext.quickdlgs.EFancybox');
$widget->image($smallImageUrl,$largeImageUrl); //show a image-fancybox
$widget->content('Some text','Lorem ipsum dolor sit amet, consectetur adipiscing elit',array('title'=>'This is the title')); //show content in a fancybox
$widget->url('A fancy ajax content',$this->createUrl('fancycontent')); //ajax content
$widget->url('Yii','http://www.yiiframework.com',array(),true); //iframe content
$this->endWidget();
Set the fancybox options by setting 'imageOptions', 'contentOptions' and/or 'urlOptions'
$widget=$this->beginWidget('ext.quickdlgs.EFancybox',
array(
'easing'=>true,
'imageOptions' => array(
'overlayColor' => '#000',
'overlayOpacity' => 0.9,
'transitionIn' => 'elastic',
'transitionOut' => 'elastic',
'speedIn' => 600,
'speedOut' => 200,
),
);
$widget->image($smallImageUrl1,$largeImageUrl1);
$widget->image($smallImageUrl2,$largeImageUrl2);
...
$this->endWidget();
The Fancybox widget supports ajax, that means it can be used inside a ajax-environment. IMPORTANT: In this case you have to set the property directOutput=true or Yii::app()->request->isAjaxRequest.
Album example with a CListView:
Your 'album' view
$items = array();
$items[] = array('imgUrlSmall'=>...,'imgUrlLarge'=>..);
$items[] = array('imgUrlSmall'=>...,'imgUrlLarge'=>..);
...
$dataProvider = new CArrayDataProvider($items, array(
'keyField'=>'imgUrlSmall',
'pagination'=>array(
'pageSize'=>5,
),
));
$fancyWidget=$this->beginWidget('ext.quickdlgs.EFancybox',array(
'directOutput'=>Yii::app()->request->isAjaxRequest, //important because of ajax pager
'imageOptions'=>array(
'width'=>1024,
'height'=>576,
)
));
$this->widget('zii.widgets.CListView', array(
'dataProvider'=>$dataProvider,
'itemView'=>'_album',
'viewData' => array('fancyWidget'=>$fancyWidget),
));
$this->endWidget();
Your _album view
...
$fancyWidget->image($data['imgUrlSmall'],$data['imgUrlLarge']);
...
Resources ¶
Changelog ¶
v2.0:
- Added fancybox widget: EFancybox.php (MIT License)
- Included fancybox-1.3.4 (v2+ is only free for personal use)
v1.2:
- Fallback for link-tag when javascript is disabled
- contentwrapper visibility is false, set visible on open
- New attribute 'hideTitleBar' //default = false (sometimes ui dialog looks better)
- New EQuickDlgs::contentPopup,EQuickDlgs::iframePopup,EQuickDlgs::ajaxPopup with autoopen=true
v1.1: Changed EJuiDlgsColumn.php
- some bugfixes (thanks to c@cba for his comment)
- Changed the properties of EJuiDlgsColumn (not compatible with v1.0).
Removed 'viewDialogHeight', .... Added 'viewDialog', 'updateDialog' instead to assign all dialog attributes like EQuickDlgs::ajaxButton / EQuickDlgs::iframeButton.
It's more flexible and you can add 'dialogAttributes' with theme/themeurl... too.
Very good
Not tested yet, but seems very promising
Thanks for the ext
=)
Fabulous
Thanks a lot for this extension!
It is simply fabulous. Thubms up up up...
Button Column in CGridView
Hi Joblo,
I'm using the
EJuiDlgsColumn
in my CGridview.Previously I had a customized 'Delete' Button in my CButtonColumn like this:
'buttons'=>array( 'delete' => array( 'label'=> 'someLabel', 'click' => 'someJsFunction', 'url' => 'someUrl', ), )
When I switched to using EJuiDlgsColumn, these options were not recognized (the 'Delete' button behaved in the default Yii-way).
Changing the first line of the
init()
function in EJuiDlgsColumn.php like the following solved my problem://$this->buttons=array(); // previous line $this->initDefaultButtons(); // new line
Thanks again for the extension.
Best regards...
version 1.1
c@cba, thanks for this hint.
I have found some more bugs in v1.0 :-(
In v1.1 I did change the properties from EJuiDlgsColumn for more flexibility, not compatible with v1.0.
Hope upgrading its not to much work for those who are using this component.
Nice
I have tested it but need a way to not show the content in case javascript is disable where can I include something like the code below.
<div style="display:none;"></div>
Thanks for the hard work.
display: none
You can set the property 'contentWrapperHtmlOptions'=>array(style=>'display:none')
in the config/juimodal.php or in the attributes when calling EQuickdlgs::xxx
Best regards
Thanks uncommenting line 332 worked
Thanks uncommenting line 332 worked.
Now one more help when the javascript is disabled how can we let the url open the request content normal as ordinary url incase the dialog fails.
In one of my files I had implemented like this so that when js is enabled the dialog open and if js is disabled the url will point to the respective page normal way.
Thanks.
echo CHtml::link('view', array('user/view'), array('onclick' => "js:$('#dialogid').dialog('open'); return false;"));
@bonnie: link fallback when javascript is disabled
Change the generation of the link code in EBaseJuiDlg::renderButton to
public function renderButton($config) { ... elseif ($type == 'link') { $url = method_exists($this,'getActionUrl') ? $this->getActionUrl() : '#'; echo CHtml::link($text, $url, $buttonHtmlOptions); } else throw new CException('invalid buttontype: ' . $type); }
Thanks for the hint, I will do this in the next release.
But don't uncomment line 332, the EJuiDlgsColumn will not work.
I have changed my answer below...
Forum topic
Please use this forum topic to discuss this extension.
Problem with URL
There seems to be bug in code in EAjaxJuiDlg.php(line 82) and EFrameJuiDlg.php(line 80)
There should be code like as
$paramChar = strpos($url,'?') === false ? '?' : '&'; $url .=$paramChar . http_build_query($this->urlParams);
instead of
$url .='?'. http_build_query($this->urlParams);
small cosmetixc fixes
Worked fine in Chrome, but
added in extensions config/juimodal.php to fix height for IE8 and firefox:
'contentWrapperHtmlOptions' => array('style'=>'height: 100%;'),
added in EFrameJuiDlg.php to show no border for IE8
line 123: 'frameborder' => 0,
I wish I cud give 2 thumbs up
:)
it is possible work with bootstrap now
some people may know that the bootstrap may have some conflicts to the jqueryUi . but now the another bootstrap extension come to us Yii-Booster , and this extension introduce the small set of jqueryUi components to bootstrap see JqueryUi in Bootstrap
AfterAjaxUpdate,
What should i do, if the CListView doing ajax update, quickdlgs popup doesnt works. i must refresh page to make popup works again. please help me, what should i do.
@khafmi
Don't reload page with ajax where you defined your dialog:
in view file:
// used by grid button EQuickDlgs::iframeButton( array( 'id' => 'my-awsome', 'renderOpenButton' => false, // <----------------- 'controllerRoute' => 'awsome', 'dialogTitle' => 'My Awsome Thing', //'dialogWidth' => 800, //'dialogHeight' => 800, 'closeOnAction' => true, //important to invoke the close action in the actionCreate ) ); // grid column definition (or in any other ajax use the click part) array( 'class' => 'EJuiDlgsColumn', 'template' => '{mybutton}', 'buttons' => array( 'assign' => array( 'label' => 'Hover text', 'imageUrl' => Yii::app()->baseUrl.'/images/awsome.png', 'url' => 'Yii::app()->createUrl("/product/awsome", array("id"=>$data->id))', 'click' => "function(){ $('#my-awsome-frame').attr('src',$(this).attr('href')+(($(this).attr('href').indexOf('?') >= 0)?'&':'?')+'qdsClass=EFrameJuiDlg&qdsDialogId=my-awsome-dlg&qdsContentWrapperId=my-awsome-content&qdsIFrameId=my-awsome-frame&qdsCloseDialog=1');$('#my-awsome-content').show();$('#my-awsome-dlg').dialog('open');return false; }", ), ), ),
@imre or anybody else, please help me
please help me, click this link below, please please help me any one T_T
something went wrong with my dialog (quickdlgs)
My thread, Help meeee..
Ajax
I have solved the ajax-problem in the Fancybox feature.
But in the moment it seems to be nearly impossible to do the same with a CJuiDialog without hacking the core.
I started a topic here
EJuiDlgsColumn dialog didn't close (fixed?)
When using EJuiDlgsColumn to create a dialog, I couldn't get the dialog to close automatically until I changed line 426 from
$url .= '"?' . http_build_query($params) . '"';
to
$url .= '"&' . http_build_query($params) . '"';
I couldn't get it to work as expected otherwise.
This problem is similar to #8800: Problem with URL but I didn't make the same change to account for not having the url provided.
@jward
Check
http://www.yiiframework.com/extension/quickdlgs/#c8800
@PeRoChAk
That's the same comment I referenced in my comment but the solution hasn't worked it's way into the extension yet. There are now at least two places this solution is needed.
urlparams
Is it right, that you you didn't set the urlManager->urlFormat to 'path'?
The problem is, that it depends on the settings of the Yii urlManager (and maybe the rules) if I have to add more urlparams as '?....' or '&....'.
If the urlManager is set to 'urlFormat'=>'path' then a '?' is needed otherwise a '&'.
To fit both urlManager settings, a possible solution in the EJuiDlgsColumn::createButtonUrl could be:
$paramChar = Yii::app()->urlManager->urlFormat=='path' ? '?' : '&'; $url .= '"'.$paramChar . http_build_query($params) . '"';
Does this work for you?
iframe height has some problem
in some browsers the height="100%" do not work . blow is what i v modified (EFrameJuiDlg::renderDialogContent) :
if(isset($this->iframeHtmlOptions['height'])){ $defaultOptions = array('width' => '100%', 'src' => $src, 'id' => $this->getFrameId()); }else{ $defaultOptions = array('width' => '100%','height' => '100%', 'src' => $src, 'id' => $this->getFrameId()); } $htmlOptions = array_merge($this->iframeHtmlOptions, $defaultOptions);
or for simple just do it this way :
$htmlOptions = array_merge(array('width' => '100%', 'height' => '100%', 'src' => $src, 'id' => $this->getFrameId()),$this->iframeHtmlOptions);
exchange the the order of defaultOptions and the iframeHtmlOptions
after do this we can explicity specify the "height" for the iframe using iframeHtmlOptions attribute !
Great Extention, Thank you Joblo
I like it, thanks.
Great Yii and team contribution!
set dialogTitle to a model attribute
I want to set the attribute dialogTitle to the content of a data field, similar to
'actionParams' => array('id' => '$data->primaryKey')
I tried something but I could not solve it.
set background-color
How can I set CSS properties like
for the dialog box?
Button html Options
To assign html option s to buttons use the openButtonHtmlOptions attribute like
EQuickDlgs::iframeButton( array( 'controllerRoute' => '/participant/new/', 'dialogTitle' => 'Add Participant to '.$model->Name, 'dialogWidth' => 500, 'dialogHeight' => 800, 'openButtonHtmlOptions'=>array( 'class'=>'gold-button' ), 'iframeHtmlOptions' => array( 'class'=>'image-add', ), 'openButtonText' => '+ Add Participant', 'closeOnAction' => true, 'refreshGridId' => 'participants-grid', ) );
Hello. Someone Knows some extension like this for Yii 2? Thanks
If you have any questions, please ask in the forum instead.
Signup or Login in order to comment.