App switching between views - extjs

I'm trying to have an app switch between views, depending on whether a user is logged in or not. The app will try to load the main view first, and then in one of the controller's launch functions will swap to the login form if you are not logged in. This part isn't having any problems.
The problem is that when the user fills out the login form and logs in, the view does change to the main view, but it does not receive events (clicking the logout button does nothing.) I know this is not a problem with the view itself, because if the main view is loaded without switching to the login screen, it will detect clicking the logout button.
In one of my controllers:
launch: function() {
this.session = localStorage.getItem('session');
if(!this.session) {
Ext.Viewport.remove(Ext.Viewport.getActiveItem(), true);
Ext.Viewport.add(Ext.create('App.view.Login'));
}
},
And when the login happens, I switch to the main view like so (which includes the logout button)
Ext.Viewport.remove(Ext.Viewport.getActiveItem(), true);
Ext.Viewport.add(Ext.create('App.view.Main'));
Ext.Msg.alert('Logged In', 'Login successful.');

So I found the not obvious at all answer: when defining the events in the controller, I needed to add button before the identifiers, example:
config: {
refs: {
loginForm: 'loginForm',
logoutForm: 'logoutForm'
},
control: {
'button#loginButton' : {
tap: 'onLogin'
},
'button#logoutButton' : {
tap: 'onLogout'
}
}
},

Related

Creating backbone routes dynamically based on flags

I am trying to create backbone routes for a user dynamically , only if the logged in user has the permission to view that particular route.In my current implementation i have created the routes and call the corresponding routing function and in that function i will check , if the user has the required privilege, if not rerouted to a default page. Can i create the routes itself based on the condition so that i don't have to check every time whether user has the appropriate privileges.
var Workspace = Backbone.Router.extend({
routes: {
"help": "help",
"search/:query": "search",
"search/:query/p:page": "search",
"default": "default"
},
help: function() {
if(!permission1){
router.navigate('default', true);
}
//write logic
},
search: function(query, page) {
if(!permission2){
router.navigate('default', true);
}
//write logic
},
//write logic for other routes
});
The solution to the problem i came up with after reading the backbone js documentation is as follows:
var GlobalRouter = Backbone.Router.extend({
initialize: function () {
this.route('*path','default',showDefault);
if (permission1) {
this.route('menu1', 'menu1', showMenu1);
}
if (permission2) {
this.route('menu2', 'menu2', renderMenu2);
}
if (permission3) {
this.route('menu3', 'menu3', renderMenu3);
}
}
});
Creating the routes likes this means that if a user does not have permission to view a certain route , there is no need for checking permission again as the routing will not happen as it is never created.

Make sure that back button won't navigate to signup page once signup was success?

In my ionic mobile app. I have signup page. Once a user's signup is success user will be navigated to profile page. Now what i want, once user is successfully signed up, users are not allowed to get back to signup page.
How can I make sure that back button won't navigate to signup page once signup was success ?
One solution I have is, to check for some condition every time signup page is loaded and based on that condition stay or navigate to other page. e.g.
if(userIsLoggedin()) {
$state.go('home')
}
Create a factory to store data
module.factory('DataStore', [function () {
var _local = {}, dataStore = {};
dataStore.setValue = function (field, value) {
_local[field] = value;
};
dataStore.getValue = function (field) {
return _local[field] || null;
};
return dataStore;
}])
Then once you validate that the user is registered you set the flag in DataStore
module.controller('registration', function(..., DataStore) {
...
//do all necessary logic
if(allGood) {
DataStore.setValue('RegistrationSuccessful', true);
}
});
Then anytime you can check from any other controller that imports DataStore
module.controller('home', function(..., DataStore) {
...
//do all necessary logic according to the code in your question
$scope.onbtnclick = function () {
if(DataStore.getValue('RegistrationSuccessful')) {
$state.go('home')
} else {
$state.go('registration');
}
};
});
You can do this by handling back button in ionic app. Check the app state on back button click if it's on profile page then do nothing so it will prevent default back event.
$ionicPlatform.registerBackButtonAction(function (event) {
if($state.current.name!="menu.profile" ){
$ionicHistory.goBack(-1);
}else{
// if state is profile then control will be here.
}
}, 100);
Put this code in app.js file.
Other suggestion: once user is register and login in to profile then he or she should be taken to profile page directly on app start.
you can do this in your register or verification function if user is not register then take it to signup page. and if user is logged in the take it to profile page.
Your solution looks good. I think you may also want to make sure you check the user session on the server side.

select a one of the containers from panel in extjs

Extjs 4.1.1(a), In my project, there is a panel (with Id #monthCalendar) which has 42 containers inside it in a View. I am trying to create a controller for that view. Here the controllers action is to show "hello" message whenever I click on any of the container inside the panel. I tried the following which is not showing any kind of error in chrome console.
In my controller:
onLaunch: function(){
Ext.each(Ext.ComponentQuery.query('#monthCalendar container'),function(container){
container.on('click',function(){
alert("hello");
},container,{element: 'el'})
})
}
This one should work
Ext.each(Ext.ComponentQuery.query('#monthCalendar container'),function(c){
c.on({ click: {fn: function(){ alert("hello"); },scope: this, element:'el' }})
})
It seems the containers inside the panel were not redered when the click event was called.(though, the containers were visible on the page. I don't know what possibly the bug is?) So, instead of using onLaunch, I used init template in which I called the render event (indirectly called the click event) and this worked.
init: function(){
this.control({
'#monthCalendar container': {
render: this.onContainerRendered
}
})
},
onContainerClicked: function() {
alert('The container was clicked');
},
onContainerRendered: function(container) {
container.on('click',this.onContainerClicked,container,{element: 'el'})
},
Working Fiddle

Getting form from click event in Controller in ExtJS?

I am extending the example given in http://docs.sencha.com/architect/2-0/#!/guide/views_forms_extjs to use a more MVC centric approach. So in service of that I want to move the on click handler from the view to a newly create controller.
I have the click even working fine, but I have no idea how to operate on the form from the context of the controller (the view was using this.getForm()).
Here is what I have so far,
Ext.define('LoginExample.controller.LoginController', {
extend: 'Ext.app.Controller',
onLoginButtonClick: function(button, e, options) {
console.log('button clicked');
if (this.getForm().isValid()) {
this.getForm().submit({
url: 'login.php',
success: function(form, action) {
Ext.Msg.alert('Login Successful!');
},
failure: function(form, action) {
Ext.Msg.alert('Login Failed!');
}
});
}
},
init: function() {
this.control({
"#loginButton": {
click: this.onLoginButtonClick
}
});
}
});
Obviously the this in the context of onLoginButtonClick is no longer the view and is instead the controller.
Given the parameters given to me, (Ext.button.Button button, Event e, Object options), how do I get the submit on the appropriate form?
I should note this using ExtJS 4.
button.up('form');
will do the trick.
To get the BasicForm object to operate on, use
button.up('form').getForm()

What to be done to prevent the router URL being used directly on the address bar by user?

Have done some working samples using Backbone Router, but is there a way to protect the routes being used directly on the address bar? And also when the user press the back button on the browser, the routes doesn't get cleared and creates issues. What is the best solution for this?
I think I see what you're saying - you want to force the user to enter your site through a certain (home) page. Is that correct?
This is useful, for example, when you're building a mobile-optimized-web-app, and you always want users to enter through a splash screen. What I'll do is set a 'legitEntrance' property to my router, and check for it on every route, as so:
APP.Router = Backbone.Router.extend({
legitEntrance: false,
// Just a helper function
setLegitEntrance: function() {
this.legitEntrance = true;
},
// Send the user back to the home page
kickUser: function() {
this.navigate("home", {trigger:true});
},
routes : {
...
},
// Example router function: Home page
routeToHome: function() {
this.setLegitEntrance();
var homeView = APP.HomeView.extend({ ... });
homeView.render();
},
// Example router function: some other internal page
routeToSomeOtherInternalPage: function() {
if(!this.legitEntrance) {
this.kickUser();
return;
}
var someOtherInternalView = APP.SomeOtherInternalView.extend({
...
});
someOtherInternalView.render();
}
....
});
I'm sure this code could be cleaned up some, but you get the general idea. Hope it helps.

Resources