Code Monkey home page Code Monkey logo

ribs's Introduction

RIBs โ†’ Appyx

This project is in maintenance mode. Bugfixes can and will happen, but no major development is expected.

Appyx is the successor of this project.

It's conceptually analogous to RIBs, and is much more powerful. We also offer interop layers with RIBs to support a gradual migration.

Check it out!

RIBs

Version Build Status License

Documentation

See here

ribs's People

Contributors

antonshilov avatar artman avatar attwellbrian avatar cherryperry avatar edrew08 avatar fmontesino avatar gaelmarhic avatar gergelyorosz avatar idyatlov avatar jarinosuke avatar jlmd avatar kovalevandrey avatar kovpas avatar lachlanmckee avatar lukaville avatar makaroffandrey avatar manuel-martos avatar mapm14 avatar mmartosdev avatar msridhar avatar neakor avatar neugartf avatar rendecano avatar rhoadster91 avatar samups avatar sbarow avatar shikasd avatar vladcipariu91 avatar yuanlu-0 avatar zsoltk avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

ribs's Issues

Template generator plugin only works in IntelliJ IDEA

Looks like Google changed Android plugin API in the latest Android Studio so it crashes with no such method error:

java.lang.NoSuchMethodError: org.jetbrains.android.facet.AndroidFacet.getAndroidModel()Lcom/android/tools/idea/model/AndroidModel;
 at com.badoo.ribs.plugin.action.SourceSetDirectoriesProvider.<init>(SourceSetDirectoriesProvider.kt:25)
 at com.badoo.ribs.plugin.action.GenerateTemplateAction.onGenerateClicked(GenerateTemplateAction.kt:58)
 at com.badoo.ribs.plugin.action.dialog.GenerateRibDialog.doOKAction(GenerateRibDialog.kt:95)
 at com.intellij.openapi.ui.DialogWrapper$OkAction.doAction(DialogWrapper.java:1880)
 at com.intellij.openapi.ui.DialogWrapper$DialogWrapperAction.actionPerformed(DialogWrapper.java:1840)
 at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
 at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2348)
 at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
 at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
 at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252)
 at java.awt.Component.processMouseEvent(Component.java:6548)
 at javax.swing.JComponent.processMouseEvent(JComponent.java:3325)
 at java.awt.Component.processEvent(Component.java:6313)
 at java.awt.Container.processEvent(Container.java:2237)
 at java.awt.Component.dispatchEventImpl(Component.java:4903)
 at java.awt.Container.dispatchEventImpl(Container.java:2295)
 at java.awt.Component.dispatchEvent(Component.java:4725)
 at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4889)
 at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4526)
 at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4467)
 at java.awt.Container.dispatchEventImpl(Container.java:2281)
 at java.awt.Window.dispatchEventImpl(Window.java:2746)
 at java.awt.Component.dispatchEvent(Component.java:4725)
 at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:764)
 at java.awt.EventQueue.access$500(EventQueue.java:98)
 at java.awt.EventQueue$3.run(EventQueue.java:715)
 at java.awt.EventQueue$3.run(EventQueue.java:709)
 at java.security.AccessController.doPrivileged(Native Method)
 at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
 at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:90)
 at java.awt.EventQueue$4.run(EventQueue.java:737)
 at java.awt.EventQueue$4.run(EventQueue.java:735)
 at java.security.AccessController.doPrivileged(Native Method)
 at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
 at java.awt.EventQueue.dispatchEvent(EventQueue.java:734)
 at com.intellij.ide.IdeEventQueue.defaultDispatchEvent(IdeEventQueue.java:817)
 at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:754)
 at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:394)
 at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
 at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
 at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:109)
 at java.awt.WaitDispatchSupport$2.run(WaitDispatchSupport.java:190)
 at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:235)
 at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:233)
 at java.security.AccessController.doPrivileged(Native Method)
 at java.awt.WaitDispatchSupport.enter(WaitDispatchSupport.java:233)
 at java.awt.Dialog.show(Dialog.java:1077)
 at com.intellij.openapi.ui.impl.DialogWrapperPeerImpl$MyDialog.show(DialogWrapperPeerImpl.java:698)
 at com.intellij.openapi.ui.impl.DialogWrapperPeerImpl.show(DialogWrapperPeerImpl.java:430)
 at com.intellij.openapi.ui.DialogWrapper.invokeShow(DialogWrapper.java:1690)
 at com.intellij.openapi.ui.DialogWrapper.show(DialogWrapper.java:1639)
 at com.badoo.ribs.plugin.action.GenerateTemplateAction.actionPerformed(GenerateTemplateAction.kt:43)
 at com.intellij.openapi.actionSystem.ex.ActionUtil$1.run(ActionUtil.java:255)
 at com.intellij.openapi.actio

nSystem.ex.ActionUtil.performActionDumbAware(ActionUtil.java:272)
 at com.intellij.ui.popup.ActionPopupStep.performAction(ActionPopupStep.java:203)
 at com.intellij.ui.popup.ActionPopupStep.performAction(ActionPopupStep.java:191)
 at com.intellij.ui.popup.ActionPopupStep.lambda$onChosen$2(ActionPopupStep.java:185)
 at com.intellij.openapi.application.TransactionGuardImpl.performUserActivity(TransactionGuardImpl.java:195)
 at com.intellij.ui.popup.AbstractPopup.lambda$dispose$8(AbstractPopup.java:1417)
 at com.intellij.util.ui.UIUtil.invokeLaterIfNeeded(UIUtil.java:3094)
 at com.intellij.ide.IdeEventQueue.ifFocusEventsInTheQueue(IdeEventQueue.java:182)
 at com.intellij.ide.IdeEventQueue.executeWhenAllFocusEventsLeftTheQueue(IdeEventQueue.java:138)
 at com.intellij.openapi.wm.impl.FocusManagerImpl.doWhenFocusSettlesDown(FocusManagerImpl.java:190)
 at com.intellij.openapi.wm.impl.IdeFocusManagerImpl.doWhenFocusSettlesDown(IdeFocusManagerImpl.java:58)
 at com.intellij.ui.popup.AbstractPopup.dispose(AbstractPopup.java:1411)
 at com.intellij.ui.popup.WizardPopup.dispose(WizardPopup.java:160)
 at com.intellij.ui.popup.list.ListPopupImpl.dispose(ListPopupImpl.java:307)
 at com.intellij.ui.popup.PopupFactoryImpl$ActionGroupPopup.dispose(PopupFactoryImpl.java:289)
 at com.intellij.openapi.util.Disposer$1.execute(Disposer.java:48)
 at com.intellij.openapi.util.Disposer$1.execute(Disposer.java:44)
 at com.intellij.openapi.util.objectTree.ObjectNode$1.execute(ObjectNode.java:138)
 at com.intellij.openapi.util.objectTree.ObjectNode$1.execute(ObjectNode.java:107)
 at com.intellij.openapi.util.objectTree.ObjectTree.executeActionWithRecursiveGuard(ObjectTree.java:182)
 at com.intellij.openapi.util.objectTree.ObjectNode.execute(ObjectNode.java:107)
 at com.intellij.openapi.util.objectTree.ObjectTree.executeAll(ObjectTree.java:151)
 at com.intellij.openapi.util.Disposer.dispose(Disposer.java:129)
 at com.intellij.openapi.util.Disposer.dispose(Disposer.java:125)
 at com.intellij.ui.popup.WizardPopup.disposeAllParents(WizardPopup.java:263)
 at com.intellij.ui.popup.list.ListPopupImpl.handleNextStep(ListPopupImpl.java:442)
 at com.intellij.ui.popup.list.ListPopupImpl._handleSelect(ListPopupImpl.java:396)
 at com.intellij.ui.popup.list.ListPopupImpl.handleSelect(ListPopupImpl.java:342)
 at com.intellij.ui.popup.PopupFactoryImpl$ActionGroupPopup.handleSelect(PopupFactoryImpl.java:309)
 at com.intellij.ui.popup.list.ListPopupImpl$MyMouseListener.mouseReleased(ListPopupImpl.java:501)
 at java.awt.AWTEventMulticaster.mouseReleased(AWTEventMulticaster.java:290)
 at java.awt.Component.processMouseEvent(Component.java:6548)
 at javax.swing.JComponent.processMouseEvent(JComponent.java:3325)
 at com.intellij.ui.popup.list.ListPopupImpl$MyList.processMouseEvent(ListPopupImpl.java:552)
 at java.awt.Component.processEvent(Component.java:6313)
 at java.awt.Container.processEvent(Container.java:2237)
 at java.awt.Component.dispatchEventImpl(Component.java:4903)
 at java.awt.Container.dispatchEventImpl(Container.java:2295)
 at java.awt.Component.dispatchEvent(Component.java:4725)
 at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4889)
 at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4526)
 at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4467)
 at java.awt.Container.dispatchEventImpl(Container.java:2281)
 at java.awt.Window.dispatchEventImpl(Window.java:2746)
 at java.awt.Component.dispatchEvent(Component.java:4725)
 at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:764)
 at java.awt.EventQueue.access$500(EventQueue.java:98)
 at java.awt.EventQueue$3.run(EventQueue.java:715)
 at java.awt.EventQueue$3.run(EventQueue.java:709)
 at java.security.AccessController.doPrivileged(Native Method)
 at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
 at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:90)
 at java.awt.EventQueue$4.run(EventQueue.java:737)
 at java.awt.EventQueue$4.run(EventQueue.java:735)

at java.security.AccessController.doPrivileged(Native Method)
 at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
 at java.awt.EventQueue.dispatchEvent(EventQueue.java:734)
 at com.intellij.ide.IdeEventQueue.defaultDispatchEvent(IdeEventQueue.java:817)
 at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:754)
 at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:394)
 at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
 at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
 at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
 at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
 at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
 at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)```

Extract BackStackFeature

No need to delegate calls through Router. BackStackFeature could be directly manipulated by Interactor, making Router leaner.

Add tests for Node lifecycles

Dimensions to be tested in each case:

  • permanent parts / nodes in the back stack / nodes in latest back stack position
  • view-parented / non-view-parented nodes
  • nodes in content-type / overlay-type configurations / content-type before overlay

Ambient customisations

Explore an ambient scope tree mechanism for overriding customisations (similar to Compose ambients). This would allow removing boilerplate from Builder client code.

Navigation broken after closing overlay dialog

The bug has been found on 6aec382.

Step to reproduce:

  1. Open app-example app
  2. Click on "overlay dialog"
  3. Press system back button
  4. Change tab to "Foo" or "Hello"

Actual result:
image

Expected result: the chosen tab without overlapping.

Remove exception from RequestCodeBasedEventStreamImpl

We cannot make sure that it's indeed wrong to receive e.g. activity result with request code that no RIB is listening for.

Case 1: framework error
Id was not restored correctly, RIB is listening with new id, result is delivered for old id) - this should be backed up and proven with tests, rather than throwing an exception runtime.

Case 2: client code error
Activity start / permission request was launched without subscribing to results - this should be raised via warning.

Case 3: no error
External activity was launched with request code not generated by us, we should not care about these

IntelliJ plugin / chained rename RIB action messes up

Steps:

  1. Rename RIB to Name1
  2. Rename RIB to Name2

Issues:

  • physical directory is renamed, but package declarations are not (incl. in xml), they are stuck reflecting to Name1
  • reference to generated DaggerComponent is stuck reflecting Name1

router.push keeps all views attached

Hello there!

I have an issue where router.push just stacks views on top of each other and you even can click through the views.

Not sure if it is desired behavior, but I expected it to work similar to fragment manager: when you push, current view gets detached and new view is attached. When you press "Back", previous view gets attached with restored state.

Here is the repo to reproduce: https://github.com/timopl/ribs-push

Thanks!

Update template generator

For now we have template generator plugin for rib 0.8.0. But we need to update it because for example Interactor still pass router to the constructor, but it does not needed anymore.

Add a link to the next chapter

At the end of each tutorial part, there is a "You can advance to the next tutorial" section but it does not have a link to the next tutorial.

Wrong class name in tutorial #4

In the tutorial #4 text mentons the class HelloWorld.Configuration, but the actual class name is HelloWorld.Config

class HelloWorldInteractor(
    savedInstanceState: Bundle?,
    private val user: User,
    private val config: HelloWorld.Configuration,
    private val input: ObservableSource<HelloWorld.Input>, // add this
    private val output: Consumer<HelloWorld.Output>,
    router: Router<Configuration, Nothing, Content, Nothing, HelloWorldView>
) 

Support multiple Overlays

Currently only one Overlay is supported correctly.

Expectations:

  • Push: all overlays above last content configuration should be cleaned up as well
  • Pop: last content + all overlays to be restored in correct order
  • Replace: all overlays above last content configuration should be cleaned up as well before replacing content configuration

Probably should wait for #27 to make it easier.

Handle any activity result in rib

How to listen for ActivityResultEvent of third party libraries?? Example: I have create a RIB for Facebook Login Button (LoginButton from Facebook SDK), click on button works fine, but when Facebook login procedure finishes, ActivityResult is not forwarded to the RIB and I get an an error in Logcat E/RIBs: There's no one listening for request code event! requestCode: 64206, resolved group: 64192, resolved code: 14, event: ActivityResultEvent(requestCode=14, resultCode=0, data=Intent { (has extras) })

Improve template generator

Feature ideas:

  • new command line tool
  • takes arguments for file path & rib name
  • finds public interface of rib, reads package name from it
  • iterates through all files, replaces package name and rib name with tokens
  • outputs generated templates to target directory inside intellij plugin module, name taken from argument
  • intellij plugin can then be recompiled to include all such target directories containing templates
  • plugin instead of checkboxes and if branches inside generation would just display a select box of included template directory names

Cyclic dependency in tutorial #4

Hello everyone!

I'm not sure if this is an issue or intended behavior but anyway.
I'm not using Dagger 2 in my project so I've tried to follow the tutorials using manual DI and found an interesting thing. In tutorial #4 where communication between RIBs illustrated, there is a cyclic dependency:

ParentIntercator --(needs)--> ParentRouter --(needs)--> ChildBuilder --(needs)--> OutputConsumer --(declared_in)--> ParentInteractor

It builds & works fine because ChildBuilder gets constructed without asking for its dependencies. However, if you try to ask them in constructor, app will crash in runtime.

Deeplink support

Hey guys! Thanks for the work you're doing!

I have a question about Deeplinking. I've heard that the Workflow / Steps set up from the original repo is not going to work in Badoo version of Ribs. Is it a correct sentence? Can you give some direction on how to implement it? And I guess that might be a good idea to create a separate Tutorial page for that somewhere in the future.

https://github.com/uber/RIBs/wiki/Android-Tutorial-4

Extract ConfigurationFeature

No need to delegate calls through Router. ConfigurationFeature could be directly manipulated in special cases when there's no back stack (e.g. RecyclerView hosting), making Router leaner.

Make Router optional

In simple cases, leaf nodes do not need Routers, and have a single default configuration.

Create test utils module for unit tests

Currently, we have rib-base-test that contains espresso/instrumentation test dependencies.
We need to create a module that contains utility classes that can be used in local unit tests.

For example, see TestNode.kt
Also, we can add test implementations of Rib.Dependency dependencies

Add a instructions to clone the project repo

Tutorial 1 starts with instructions to open the "tutorial 1" module. The writer assumes that the reader has already cloned the repo, but it was not mentioned anywhere before in the tutorials. So it would be better if there was an initial step to clone the repo.

Roadmap 1.0

Features

  • Automatic routing based on configurations
  • Routing back stack
  • Tree structure persistence to Bundle (automatic)
  • Back stack persistence to Bundle (automatic)
  • Support for Android lifecycle
  • Template generator plugin with live code
  • Instrumentation test helpers to test RIBs in isolation
  • Android request code based result handling delivered to initiating RIB
  • Support for Activity launching
  • Support for permission requesting
  • Overlay configurations
  • Ability to show dialogs
  • Ability to host a RIB in a dialog
  • Ability to provide scoped customisations to RIBs
  • Proper DI for Views
  • SavedInstanceState in constructor to avoid invalid temporary state until attach
  • Support for workflows
  • Full-screen portals (content or overlay)
  • View plugins
  • AndroidX
  • Router made optional
  • Ability to host RIBs as RecyclerView elements
  • Support for transitions
  • SingleTop back stack operation
  • BuildContext
  • Back stack operations extensible by client code
  • API cleanup
  • All Node components as plugins
  • Node Connectors
  • Abstract RoutingSource

Pre-release phase

  • General cleanup
  • Documentation (code)
  • Debug plugin per RIB to a drawer
  • General audit (code)
  • General audit (tests)

Helping adoption

  • Tutorial / wiki coverage for missing parts
  • Best practices
  • Nice example app

Lifecycle events can be missing

Let's consider next situation.
You added container RIB with Screen1Rib.
Than during work with this RIB you decided to replace it to another Screen2Rib inside same container.
Screen2Rib will not receive onStart and onResume events because of this code:

fun onAttach(savedInstanceState: Bundle?) {
    tag = savedInstanceState?.getString(KEY_TAG) ?: tag
    lifecycleRelay.accept(ACTIVE)
    ribLifecycleRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE)
    onAttach(ribLifecycleRegistry, savedInstanceState)
}

I think when you attaching/replacing RIB you should receive lifecycleEvents.

Move disposables from Interactor to Node

There's nothing specific about Interactor why it should be there. Node is responsible for triggering lifecycle events. Feature is no longer created in Interactor but in Builder, so it should be easy to make this change.

Create vanilla flavour (app-example)

No Dagger, no MVICore Feature, no Binder, no RxJava.

A reduced set of app-example (or another app demonstrating basic functionality) is acceptable, no need to reimplement the whole playground.

RIBs generator throws exception in Android Studio 3.6

java.lang.NoSuchMethodError: org.jetbrains.android.facet.AndroidFacet.getManifest()Lorg/jetbrains/android/dom/manifest/Manifest;
    at com.badoo.ribs.plugin.action.GenerateTemplateAction.onGenerateClicked(GenerateTemplateAction.kt:59)
    at com.badoo.ribs.plugin.generator.dialog.GenerateRibDialog.doOKAction(GenerateRibDialog.kt:106)
    at com.intellij.openapi.ui.DialogWrapper$OkAction.doAction(DialogWrapper.java:1861)
    at com.intellij.openapi.ui.DialogWrapper$DialogWrapperAction.actionPerformed(DialogWrapper.java:1821)
    at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
    at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2348)
    at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
    at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
    at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252)
    at java.awt.Component.processMouseEvent(Component.java:6550)
    at javax.swing.JComponent.processMouseEvent(JComponent.java:3325)
    at java.awt.Component.processEvent(Component.java:6315)
    at java.awt.Container.processEvent(Container.java:2239)
    at java.awt.Component.dispatchEventImpl(Component.java:4899)
    at java.awt.Container.dispatchEventImpl(Container.java:2297)
    at java.awt.Component.dispatchEvent(Component.java:4721)
    at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4904)
    at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4535)
    at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4476)
    at java.awt.Container.dispatchEventImpl(Container.java:2283)
    at java.awt.Window.dispatchEventImpl(Window.java:2746)
    at java.awt.Component.dispatchEvent(Component.java:4721)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:766)
    at java.awt.EventQueue.access$500(EventQueue.java:98)
    at java.awt.EventQueue$3.run(EventQueue.java:715)
    at java.awt.EventQueue$3.run(EventQueue.java:709)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:74)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:84)
    at java.awt.EventQueue$4.run(EventQueue.java:739)
    at java.awt.EventQueue$4.run(EventQueue.java:737)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:74)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:736)
    at com.intellij.ide.IdeEventQueue.defaultDispatchEvent(IdeEventQueue.java:817)
    at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:762)
    at com.intellij.ide.IdeEventQueue.lambda$dispatchEvent$8(IdeEventQueue.java:405)
    at com.intellij.openapi.progress.impl.CoreProgressManager.computePrioritized(CoreProgressManager.java:693)
    at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:404)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:205)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:109)
    at java.awt.WaitDispatchSupport$2.run(WaitDispatchSupport.java:190)
    at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:235)
    at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:233)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.awt.WaitDispatchSupport.enter(WaitDispatchSupport.java:233)
    at java.awt.Dialog.show(Dialog.java:1077)
    at com.intellij.openapi.ui.impl.DialogWrapperPeerImpl$MyDialog.show(DialogWrapperPeerImpl.java:707)
    at com.intellij.openapi.ui.impl.DialogWrapperPeerImpl.show(DialogWrapperPeerImpl.java:432)
    at com.intellij.openapi.ui.DialogWrapper.doShow(DialogWrapper.java:1685)
    at com.intellij.openapi.ui.DialogWrapper.show(DialogWrapper.java:1644)
    at com.badoo.ribs.plugin.action.GenerateTemplateAction.actionPerformed(GenerateTemplateAction.kt:48)
    at com.intellij.openapi.actionSystem.ex.ActionUtil$1.run(ActionUtil.java:265)
    at com.intellij.openapi.actionSystem.ex.ActionUtil.performActionDumbAware(ActionUtil.java:282)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem$ActionTransmitter.lambda$actionPerformed$0(ActionMenuItem.java:292)
    at com.intellij.openapi.wm.impl.FocusManagerImpl.runOnOwnContext(FocusManagerImpl.java:265)
    at com.intellij.openapi.wm.impl.IdeFocusManagerImpl.runOnOwnContext(IdeFocusManagerImpl.java:107)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem$ActionTransmitter.actionPerformed(ActionMenuItem.java:282)
    at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem.lambda$fireActionPerformed$0(ActionMenuItem.java:111)
    at com.intellij.openapi.application.TransactionGuardImpl.runSyncTransaction(TransactionGuardImpl.java:82)
    at com.intellij.openapi.application.TransactionGuardImpl.lambda$submitTransaction$1(TransactionGuardImpl.java:106)
    at com.intellij.openapi.application.TransactionGuardImpl.submitTransaction(TransactionGuardImpl.java:115)
    at com.intellij.openapi.application.TransactionGuard.submitTransaction(TransactionGuard.java:121)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem.fireActionPerformed(ActionMenuItem.java:111)
    at com.intellij.ui.plaf.beg.BegMenuItemUI.doClick(BegMenuItemUI.java:524)
    at com.intellij.ui.plaf.beg.BegMenuItemUI.access$300(BegMenuItemUI.java:35)
    at com.intellij.ui.plaf.beg.BegMenuItemUI$MyMouseInputHandler.mouseReleased(BegMenuItemUI.java:546)
    at java.awt.Component.processMouseEvent(Component.java:6550)
    at javax.swing.JComponent.processMouseEvent(JComponent.java:3325)
    at java.awt.Component.processEvent(Component.java:6315)
    at java.awt.Container.processEvent(Container.java:2239)
    at java.awt.Component.dispatchEventImpl(Component.java:4899)
    at java.awt.Container.dispatchEventImpl(Container.java:2297)
    at java.awt.Component.dispatchEvent(Component.java:4721)
    at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4904)
    at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4535)
    at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4476)
    at java.awt.Container.dispatchEventImpl(Container.java:2283)
    at java.awt.Window.dispatchEventImpl(Window.java:2746)
    at java.awt.Component.dispatchEvent(Component.java:4721)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:766)
    at java.awt.EventQueue.access$500(EventQueue.java:98)
    at java.awt.EventQueue$3.run(EventQueue.java:715)
    at java.awt.EventQueue$3.run(EventQueue.java:709)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:74)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:84)
    at java.awt.EventQueue$4.run(EventQueue.java:739)
    at java.awt.EventQueue$4.run(EventQueue.java:737)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:74)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:736)
    at com.intellij.ide.IdeEventQueue.defaultDispatchEvent(IdeEventQueue.java:817)
    at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:762)
    at com.intellij.ide.IdeEventQueue.lambda$dispatchEvent$8(IdeEventQueue.java:405)
    at com.intellij.openapi.progress.impl.CoreProgressManager.computePrioritized(CoreProgressManager.java:704)
    at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:404)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:205)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
    at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)

Create Android "res" directory if it doesn't exist in Android module

Currently, plugin throws an exception if res directory is not created in the module:

java.lang.IllegalStateException: Resources directory not found
    at com.badoo.ribs.plugin.generator.SourceSetDirectoriesProvider.findDirectory(SourceSetDirectoriesProvider.kt:40)
    at com.badoo.ribs.plugin.generator.SourceSetDirectoriesProvider.getDirectory(SourceSetDirectoriesProvider.kt:29)
    at com.badoo.ribs.plugin.generator.SourceSetDirectoriesProvider.getDirectory$default(SourceSetDirectoriesProvider.kt:28)
    at com.badoo.ribs.plugin.generator.TemplateWriter$writeFiles$1.accept(TemplateWriter.kt:20)
    at com.badoo.ribs.plugin.generator.TemplateWriter$writeFiles$1.accept(TemplateWriter.kt:13)
    at java.util.LinkedHashMap.forEach(LinkedHashMap.java:684)
    at com.badoo.ribs.plugin.generator.TemplateWriter.writeFiles(TemplateWriter.kt:19)
    at com.badoo.ribs.plugin.action.GenerateTemplateAction$onGenerateClicked$1$1.run(GenerateTemplateAction.kt:78)
    at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:220)
    at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:178)
    at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:168)
    at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:154)
    at com.badoo.ribs.plugin.action.GenerateTemplateAction$onGenerateClicked$1.run(GenerateTemplateAction.kt:77)
    at com.intellij.openapi.application.impl.ApplicationImpl.runWriteAction(ApplicationImpl.java:1057)
    at com.badoo.ribs.plugin.action.GenerateTemplateAction.onGenerateClicked(GenerateTemplateAction.kt:76)
    at com.badoo.ribs.plugin.generator.dialog.GenerateRibDialog.doOKAction(GenerateRibDialog.kt:106)
    at com.intellij.openapi.ui.DialogWrapper$OkAction.doAction(DialogWrapper.java:1871)
    at com.intellij.openapi.ui.DialogWrapper$DialogWrapperAction.actionPerformed(DialogWrapper.java:1831)
    at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
    at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2348)
    at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
    at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
    at javax.swing.AbstractButton.doClick(AbstractButton.java:376)
    at javax.swing.plaf.basic.BasicRootPaneUI$Actions.actionPerformed(BasicRootPaneUI.java:208)
    at javax.swing.SwingUtilities.notifyAction(SwingUtilities.java:1663)
    at javax.swing.JComponent.processKeyBinding(JComponent.java:2883)
    at javax.swing.KeyboardManager.fireBinding(KeyboardManager.java:307)
    at javax.swing.KeyboardManager.fireKeyboardAction(KeyboardManager.java:250)
    at javax.swing.JComponent.processKeyBindingsForAllComponents(JComponent.java:2975)
    at javax.swing.JComponent.processKeyBindings(JComponent.java:2967)
    at javax.swing.JComponent.processKeyEvent(JComponent.java:2846)
    at java.awt.Component.processEvent(Component.java:6325)
    at java.awt.Container.processEvent(Container.java:2237)
    at java.awt.Component.dispatchEventImpl(Component.java:4903)
    at java.awt.Container.dispatchEventImpl(Container.java:2295)
    at java.awt.Component.dispatchEvent(Component.java:4725)
    at java.awt.KeyboardFocusManager.redispatchEvent(KeyboardFocusManager.java:1954)
    at java.awt.DefaultKeyboardFocusManager.dispatchKeyEvent(DefaultKeyboardFocusManager.java:806)
    at java.awt.DefaultKeyboardFocusManager.preDispatchKeyEvent(DefaultKeyboardFocusManager.java:1074)
    at java.awt.DefaultKeyboardFocusManager.typeAheadAssertions(DefaultKeyboardFocusManager.java:945)
    at java.awt.DefaultKeyboardFocusManager.dispatchEvent(DefaultKeyboardFocusManager.java:771)
    at com.intellij.ide.IdeKeyboardFocusManager.dispatchEvent(IdeKeyboardFocusManager.java:27)
    at java.awt.Component.dispatchEventImpl(Component.java:4774)
    at java.awt.Container.dispatchEventImpl(Container.java:2295)
    at java.awt.Window.dispatchEventImpl(Window.java:2746)
    at java.awt.Component.dispatchEvent(Component.java:4725)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:764)
    at java.awt.EventQueue.access$500(EventQueue.java:98)
    at java.awt.EventQueue$3.run(EventQueue.java:715)
    at java.awt.EventQueue$3.run(EventQueue.java:709)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:90)
    at java.awt.EventQueue$4.run(EventQueue.java:737)
    at java.awt.EventQueue$4.run(EventQueue.java:735)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:734)
    at com.intellij.ide.IdeEventQueue.defaultDispatchEvent(IdeEventQueue.java:755)
    at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:682)
    at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:391)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:109)
    at java.awt.WaitDispatchSupport$2.run(WaitDispatchSupport.java:190)
    at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:235)
    at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:233)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.awt.WaitDispatchSupport.enter(WaitDispatchSupport.java:233)
    at java.awt.Dialog.show(Dialog.java:1077)
    at com.intellij.openapi.ui.impl.DialogWrapperPeerImpl$MyDialog.show(DialogWrapperPeerImpl.java:698)
    at com.intellij.openapi.ui.impl.DialogWrapperPeerImpl.show(DialogWrapperPeerImpl.java:430)
    at com.intellij.openapi.ui.DialogWrapper.invokeShow(DialogWrapper.java:1681)
    at com.intellij.openapi.ui.DialogWrapper.show(DialogWrapper.java:1630)
    at com.badoo.ribs.plugin.action.GenerateTemplateAction.actionPerformed(GenerateTemplateAction.kt:48)
    at com.intellij.openapi.actionSystem.ex.ActionUtil$1.run(ActionUtil.java:258)
    at com.intellij.openapi.actionSystem.ex.ActionUtil.performActionDumbAware(ActionUtil.java:275)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem$ActionTransmitter.lambda$actionPerformed$0(ActionMenuItem.java:287)
    at com.intellij.openapi.wm.impl.FocusManagerImpl.runOnOwnContext(FocusManagerImpl.java:283)
    at com.intellij.openapi.wm.impl.IdeFocusManagerImpl.runOnOwnContext(IdeFocusManagerImpl.java:106)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem$ActionTransmitter.actionPerformed(ActionMenuItem.java:277)
    at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem.lambda$fireActionPerformed$0(ActionMenuItem.java:111)
    at com.intellij.openapi.application.TransactionGuardImpl.runSyncTransaction(TransactionGuardImpl.java:88)
    at com.intellij.openapi.application.TransactionGuardImpl.lambda$submitTransaction$1(TransactionGuardImpl.java:111)
    at com.intellij.openapi.application.TransactionGuardImpl.submitTransaction(TransactionGuardImpl.java:120)
    at com.intellij.openapi.application.TransactionGuard.submitTransaction(TransactionGuard.java:122)
    at com.intellij.openapi.actionSystem.impl.ActionMenuItem.fireActionPerformed(ActionMenuItem.java:111)
    at com.intellij.ui.plaf.beg.BegMenuItemUI.doClick(BegMenuItemUI.java:524)
    at com.intellij.ui.plaf.beg.BegMenuItemUI.access$300(BegMenuItemUI.java:35)
    at com.intellij.ui.plaf.beg.BegMenuItemUI$MyMouseInputHandler.mouseReleased(BegMenuItemUI.java:546)
    at java.awt.Component.processMouseEvent(Component.java:6548)
    at javax.swing.JComponent.processMouseEvent(JComponent.java:3325)
    at java.awt.Component.processEvent(Component.java:6313)
    at java.awt.Container.processEvent(Container.java:2237)
    at java.awt.Component.dispatchEventImpl(Component.java:4903)
    at java.awt.Container.dispatchEventImpl(Container.java:2295)
    at java.awt.Component.dispatchEvent(Component.java:4725)
    at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4889)
    at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4526)
    at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4467)
    at java.awt.Container.dispatchEventImpl(Container.java:2281)
    at java.awt.Window.dispatchEventImpl(Window.java:2746)
    at java.awt.Component.dispatchEvent(Component.java:4725)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:764)
    at java.awt.EventQueue.access$500(EventQueue.java:98)
    at java.awt.EventQueue$3.run(EventQueue.java:715)
    at java.awt.EventQueue$3.run(EventQueue.java:709)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:90)
    at java.awt.EventQueue$4.run(EventQueue.java:737)
    at java.awt.EventQueue$4.run(EventQueue.java:735)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:80)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:734)
    at com.intellij.ide.IdeEventQueue.defaultDispatchEvent(IdeEventQueue.java:755)
    at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:700)
    at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:391)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
    at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.