I'm planning on an academics organizer application where you can add tabs much like you can add tabs in a browser, but it's in the context of the application. Each tab has its own history, route, navigation, etc.
I thought this would be trivial to implement with vue-router but thinking about it a little more I have no idea how to map router links to tabs that can change as routes are usually just set in stone.
I also thought about creating a separate router for each tab, but that also seems a bit funny. Can someone help me out?
EDIT: It's important to note that the application is not actually a web browser. I would just like browser-like tabs, but in the context of an academics-organizer-application-thing.
You probably don't need a router to do that you can simply use v-if and v-else on a specific property that sets the active tab
First idea.
It may be better to use some existed layout framework for tabs logic. For example Golden Layout
And when tab opens you can bootstrap into this tab vue.js app with vue-router in "abstract" mode.
For state managment you can use event bus or vuex. But it has to be the only one across the whole app.
Second idea.
If bootstrapping of several vue.js apps looks like overengineering, then you could create component which implements basic functions for history / navigation. This component have to wrap the content of each your tab.
Related
This question is about the correct way to create a general modal that using ReactJS, that will be used across multiple components in the application.
Apparently, we have two ways to manage a modal:
Looking at libraries as react-modal(https://github.com/reactjs/react-modal) that utilizes the state to control the modal with a visible property and a close method.
As this medium article (https://medium.com/#danparkk/react-modals-scalable-customizable-neat-components-f2088d60f3d3) utilizing a state manager as Redux, Flux, ...
What is the "correct way"? Rewriting a state to a modal everytime you use in the application, or making an action to change in the state of the application every time?
I am having an issue with navigation blocking in React.
I use React + Redux with React Router. I have been using the component in order to prevent navigation from incomplete forms within React. This works fine as long as the navigation is actually within React. What it doesn't block, however, is navigation via URL entry, or clicking on an external hyperlink.
Is there an accepted method in React for handling external hyperlinks and blocking navigation outside of React?
You didn't provide any code here, so I'm trying to guess. If I understand you correctly, you are able to manage you internal redirects thought the React app via react-router without any issues.
As per your statement:
What it doesn't block, however, is navigation via URL entry, or clicking on an external hyperlink.
Let's tackle both questions. First can't prevent a user from going to the navigation bar and enter a new URL, that done by design on the browsers side, it would be bad for the user, and of course invasive!
But regarding your second question about clicking on a link that will send you outside your domain or application, you can do something about it.
You have multiple options here, I will give you three:
First: Use history.block
You can block or better said, ask the user to acknowledge the transition to another page by using history.block
As an example from the history docs:
const unblock = history.block('Are you sure you want to leave this page?')
Second: Use history.push instead of href
Just don't use anchor elements href, but rely on the history of react-router.
You can read more about it here: react-router/history
But basically you can wire your redirection using the push method from history, which will look something like:
onClick() {
//code to control if you want to redirect or not
history.push('http://yoururl.com');
}
Third: Use Redirect component with conditional rendering
Then you have other options like for example using conditional rendering combined with Redirect components, but the other approach would be enough to solve your problem.
I think you are looking for Blocking Transitions under the history api for React Router.
As per the example on react router history github page:
You can register a simple prompt message that will be shown to the user before they navigate away from the current page.
const unblock = history.block('Are you sure you want to leave this page?')
Detailed info at https://github.com/ReactTraining/history#properties
I am trying to create Twitter like profile layout in React Native. Although many apps use this pattern. My current JSX setup is something like this.
Header (profile)
ViewPagerNav (custom)
ViewPager
Tab with ListView
Tab with ListView
Problem is that only bottom part scrolls. I have seen this problem for many React Native apps. Is there a solution for this?
How should my render view look like to g full get page scrolling?
There is actually a really good example of this in the F8 app. The 3 files you want to look at are here:
https://github.com/fbsamples/f8app/blob/master/js/tabs/schedule/MyScheduleView.js
https://github.com/fbsamples/f8app/blob/master/js/common/ListContainer.js
https://github.com/fbsamples/f8app/blob/master/js/common/PureListView.js
If you want to see how it works in the app it is the My F8 tab.
The basic idea is that the ListContainer keeps track of the scroll position via the handleScroll function. It passes handleScroll to all of its children renaming the function to onScroll.
The PureListView a it takes that onScroll property via the object spread operator {...this.props} and passes it into the ListView.
That is all just to keep track of the scroll. If you look in MyScheduleView.js you can see how it is mostly implemented.
Hope that helps.
I'm making a game using JavaScript, currently I'm using window.location = "somepage.html" to perform navigation but I'm not sure if that is the correct way to do it. As I said in the title I've choosed Blank App Template so I do not have any navigator.js or something like.
Can you guys tell me the best way to do it?
Although you can use window.location to perform navigation, I'm sure you've already noticed a few of the downsides:
The transition between pages goes through a black screen, which is an artifact of how the underlying HTML rendering engine works.
You lose your script context between pages, e.g. you don't have any shared variables or namespaces, unless you use HTML5 session storage (or WinRT app data).
It's hard to wire up back buttons, e.g. you have to make sure each destination page knows what page navigated to it, and then maintain a back stack in session storage.
It's for these reasons that WinJS + navigator.js created a way to do "pages" via DOM replacement, which is the same strategy used by "single page web apps." That is, you have a div in default.html within which you load an unload DOM fragments to give the appearance of page navigation, while you don't actually ever leave the original script context of default.html. As a result, all of your in-memory variables persist across all page navigations.
The mechanics work like this: WinJS.Navigation provides an API to manage navigation and a backstack. By itself, however, all it really does is manage a backstack array and fire navigation-related events. To do the DOM replacement, something has to be listening to those events.
Those listeners are what navigator.js implements, so that's a piece of code that you can pull into any project for this purpose. Navigator.js also implements a custom control called the PageControlNavigator (usually Application.PageControlNavigator) is what implements the listeners.
That leave the mechanics of how you define your "pages." This is what the WinJS.UI.Pages API is for, and navigator.js assumes that you've defined your pages in this way. (Technically speaking, you can define your own page mechanisms for this, perhaps using the low-level WinJS.UI.Fragments API or even implementing your own from scratch. But WinJS.UI.Pages came about because everyone who approached this problem basically came up with the same solution, so the WinJS team provided one implementation that everyone can use.)
Put together then:
You define each page as an instance of WinJS.UI.Pages.PageControl, where each page is identified by its HTML file (which can load its own JS and CSS files). The JS file contains implementations of a page's methods like ready, in which you can do initialization work. You can then build out any other object structure you want.
In default.html, define a single div for the "host container" for the page rendering. This is an instance of the PageControlNavigator class that's defined in navigator.js. In its data-win-options you specify "{home: }" for the initial page that's loaded.
Whenever you want to switch to another page, call WinJS.Navigation.navigate with the identifier for the target page (namely the path to its .html file). In response, it will fire some navigating events.
In response, the PageControlNavigator's handlers for those events will load the target page's HTML into the DOM, within its div in default.html. It will then unload the previous page's DOM. When all of this gets rendered, you see a page transition--and a smooth one because we can animate the content in and out rather than go through a black screen.
In this process, the previous page control's unload method is called, and the init/load/processed/ready methods of the new page control are called.
It's not too hard to convert a blank app template into a nav template project--move your default.html/.css/.js content into a page control structure, add navigator.js to default.html (and your project), and put a PageControlNavigator into default.html. I suggest that you create a project from the nav app template for reference. Given the explanation above, you should be able to understand the structure.
For more details, refer to Chapter 3 of my free ebook, Programming Windows Store Apps with HTML, CSS, and JavaScript, Second Edition, where I talk about app anatomy and page navigation with plenty of code examples.
I'm working on a Backbone.js web application with a few different views. Let's say we have the AudioPlayer view at the top of the page that should be persistent and play audio while the rest of the page content changes. The rest of the page content should be able to be switched on demand (with the Router updating the url via navigate).
I'm looking for the correct way to hide/remove FirstView, insert a SecondView, and then hide/remove SecondView and insert/show FirstView again when the user clicks the "back" button.
I've been told that views should be removed when they are not shown to avoid memory leaks. If this is true, what's the proper way to re-create the view again, as its associated view.el has been destroyed during the remove process? Or is there a more logical way to do this?
This is the way I do it:
extend Backbone.View with a method called open that will append the view to the DOM as well as set a flag on the view that is now open, and a similar close property
make all views properties on a common views property of your app
create a method called clearViews on the app that will close all open views except the view names passed in
Here is a gist (in coffeescript) of what I've been using. Feel free to copy.
https://gist.github.com/4597528
So after extending Backbone in this way, lets suppose you want to create and open a new view in a Backbone route after closing all open views except the top nav bar, which app.views.topNav points to. You can say:
app.clearViews('topNav');
app.views.myNewView = new MyView;
app.render().open('body'); // or some other container
There are some great view and layout managers out there for larger projects like Marionette by Derick Baily and LayoutManager by Tim Branyen, but they seemed like overkill for my smaller projects.
I currently do this in several of my apps, and it is accomplished with a tabbed interface. You can see an example of those interface here:
Twitter Bootstrap
Zurb Foundation
jQueryUI
I use a backbone router to watch the url. This let's me keep deep-linking/bookmarking for users, but I usually have the view events trigger tab changes.
For my purpose I have a mult-tabbed app which has a chat window, image gallery window, and collaborative editing windows.