Thursday, March 31, 2016

Initialising the TextToSpeech object on a worker thread

Leave a Comment

For years (literally), my application has suffered woes from poorly performing text to speech engines, in particular, the initialisation time when calling:

tts = new TextToSpeech(context, myOnInitListener); 

The above can cause the UI to lag and if you search for 'Text to Speech initialization slow' on SO, you'll find many posts. The embedded high quality IVONA voices used to be the worst culprit, but the Google TTS engine has now taken the prize.

Their most recent APK update, causes major lag on initialisation - No code necessary to test this, you can go to your Android Text to Speech settings and try switching between available engines, whilst pressing 'listen to a sample', the lag is demonstrated 'nicely'.

To try and combat this, I've implemented the following:

private volatile TextToSpeech tts;  AsyncTask.execute(new Runnable() {     @Override     public void run() {         tts = new TextToSpeech(context, volatileOnInitListener);     } }); 

This has completely cured the lag on initialisation, but I fear there may be side-effects to this that I've not considered? Can anyone think of any?

I'm puzzled also, as I had believed the the TextToSpeech Constructor was asynchronous and therefore moving this constructor to a worker thread should make no difference? If this implementation is the way forward, then why don't Google implement it in their TextToSpeechSettings?

Hope someone can clarify the above. Thanks in advance.

Edit - When I said the 'Constructor was asynchronous', I really was referring to the engine initialisation process it starts, and the eventual call to onInit

1 Answers

Answers 1

I had believed the the TextToSpeech Constructor was asynchronous

That is only partially true. A lot of the initialization is executed syncronously. Here is the Source

If this implementation is the way forward, then why don't Google implement it in their TextToSpeechSettings?

It seems like google seldomly checks how their code runs on mid and lowend devices, I guess the lag doesn't show on highend devices. (Another example of this happening can be seen in the current youtube app, for which I personally can confirm lag on a mid-spec device and no lag on a high-end device.) This is pure speculation as I am not affiliated to google.

I fear there may be side-effects to this that I've not considered? Can anyone think of any?

The only (obvious) sideeffect is that you can't use the tts engine syncronously, but have to wait for the asyncronous task to finish. But that is already the case anyway. The only thing you do is execute some code outside of the UI thread, which does not expect to be run on the UI thread. This should never be a problem. And even if there is a problem, you will only find it by testing it in an application.

In general you're good to go.

Read More

Layout like HotStar App

Leave a Comment

I have to create layout like HotStar App, but I am bit confuse that what would be the best way of doing this:

enter image description here

  1. Do I need multiple RecyclerViews or single RecyclerView is enough ?

  2. Do I need to call multiple JSONs or single JSON is enough to fetch data from server?

  3. How Do I use different - different layouts for You May Also Like and Must Watch Clips

8 Answers

Answers 1

With this you will be able to create same Look-And-Feel

1.- For upper menu tab, you have to layout TABS

2.- For detail section, please add CARDS

3.- Divider for your sections, use SUBHEADERS

Now, regarding your questions:

1. You can handle everything with just one single RecyclerViews

2. Best approach, is to get a separated JSON for each section, since you never know how big each section will be. That will help a lot with a better performance and clean code.

**

NEW UPDATE

**

Your Main Layout Activity

<?xml version="1.0" encoding="utf-8"?>     <RelativeLayout         xmlns:app="http://schemas.android.com/apk/res-auto"         xmlns:android="http://schemas.android.com/apk/res/android"         xmlns:tools="http://schemas.android.com/tools"         android:layout_width="match_parent"         android:layout_height="match_parent"         tools:context="com.alphasystech.hotvideos.MainActivity">          <android.support.design.widget.AppBarLayout             android:layout_width="match_parent"             android:layout_height="wrap_content"             android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">              <include                 android:layout_height="wrap_content"                 android:layout_width="match_parent"                 layout="@layout/toolbar_layout">              </include>              <android.support.design.widget.TabLayout                 android:layout_width="match_parent"                 android:layout_height="wrap_content"                 android:id="@+id/tabLayout"                 app:tabMode="fixed"                 app:tabGravity="fill"                 app:tabTextAppearance="@style/MyTabStyle">             </android.support.design.widget.TabLayout>          </android.support.design.widget.AppBarLayout>          <android.support.v4.view.ViewPager             android:layout_width="match_parent"             android:layout_height="match_parent"             android:id="@+id/viewPager">          </android.support.v4.view.ViewPager>      </RelativeLayout> 

Your Home Fragment Layout (Also you can clone this for MOVIES, SPORTS...)

<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".HomeFragment">  <!-- A RecyclerView with some commonly used attributes --> <android.support.v7.widget.RecyclerView     android:id="@+id/home_recyclerview"     android:scrollbars="vertical"     android:layout_width="wrap_content"     android:layout_height="wrap_content"/> 

Your Cards Layout for your Home Fragment(Also you can clone this for MOVIES, SPORTS...)

<?xml version="1.0" encoding="utf-8"?> <android.support.v7.widget.CardView     xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:card_view="http://schemas.android.com/apk/res-auto"     android:layout_width="match_parent"     android:layout_height="wrap_content"     android:id="@+id/card_view"     android:layout_margin="5dp"     card_view:cardBackgroundColor="#81C784"     card_view:cardCornerRadius="12dp"     card_view:cardElevation="3dp"     card_view:contentPadding="4dp" >      <RelativeLayout         android:layout_width="match_parent"         android:layout_height="wrap_content"         android:padding="16dp" >          <ImageView             android:layout_width="100dp"             android:layout_height="100dp"             android:id="@+id/item_image"             android:layout_alignParentLeft="true"             android:layout_alignParentTop="true"             android:layout_marginRight="16dp"             />          <TextView             android:layout_width="wrap_content"             android:layout_height="wrap_content"             android:id="@+id/item_title"             android:layout_toRightOf="@+id/item_image"             android:layout_alignParentTop="true"             android:textSize="30sp"             />          <TextView             android:layout_width="wrap_content"             android:layout_height="wrap_content"             android:id="@+id/item_detail"             android:layout_toRightOf="@+id/item_image"             android:layout_below="@+id/item_title"             />      </RelativeLayout> </android.support.v7.widget.CardView> 

Screenshot:

screenshot sample

I think, the above sample will give you a good direction :)

Answers 2

  1. Do I need multiple RecyclerViews or single RecyclerView is enough?

Single RecyclerView is enough.

  1. Do I need to call multiple JSONs or single JSON is enough to fetch data from server?

Single JSON response is enough.

  1. How Do I use different - different layouts for You May Also Like and Must Watch Clips

Make this part of UI as RecyclerView row.

RecyclerView row

This is the simplest solution if you known max number of items in row. Your model need to have each row data.

Row layout xml example:

<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:card_view="http://schemas.android.com/apk/res-auto"     android:layout_width="match_parent"     android:layout_height="match_parent"     android:background="#ddd"     android:orientation="vertical">      <LinearLayout         android:layout_width="match_parent"         android:layout_height="wrap_content"         android:orientation="horizontal">           <TextView             android:id="@+id/textView"             android:layout_width="wrap_content"             android:layout_height="wrap_content"             android:layout_marginLeft="16dp"             android:text="You May Also Like"             android:textAppearance="?android:attr/textAppearanceLarge"             android:textStyle="bold" />          <View             android:layout_width="0dp"             android:layout_height="0dp"             android:layout_weight="1" />          <Button             android:id="@+id/button"             android:layout_width="wrap_content"             android:layout_height="wrap_content"             android:layout_marginRight="16dp"             android:text="MORE" />     </LinearLayout>       <TableLayout         android:layout_width="match_parent"         android:layout_height="wrap_content"         android:layout_gravity="center_horizontal">           <TableRow             android:layout_width="match_parent"             android:layout_height="wrap_content">              <android.support.v7.widget.CardView                 android:id="@+id/item1_CV"                 android:layout_width="0dp"                 android:layout_height="wrap_content"                 android:layout_marginBottom="4dp"                 android:layout_marginLeft="8dp"                 android:layout_marginRight="4dp"                 android:layout_marginTop="8dp"                 android:layout_weight="1"                 card_view:cardCornerRadius="4dp">                  <RelativeLayout                     android:layout_width="match_parent"                     android:layout_height="wrap_content">                      <LinearLayout                         android:layout_width="match_parent"                         android:layout_height="wrap_content"                         android:layout_alignParentEnd="true"                         android:layout_alignParentLeft="true"                         android:layout_alignParentRight="true"                         android:layout_alignParentStart="true"                         android:layout_below="@+id/item1_image"                         android:background="#fff"                         android:orientation="vertical"                         android:padding="8dp">                          <TextView                             android:id="@+id/item1_title"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:text="Mere Rang Mein"                             android:textColor="#000"                             android:textSize="16sp" />                          <TextView                             android:id="@+id/item1_subTitle"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:singleLine="true"                             android:text="Romance, Hindi, Life OK"                             android:textAppearance="?android:attr/textAppearanceSmall"                             android:textSize="12sp" />                     </LinearLayout>                      <ImageView                         android:id="@+id/item1_image"                         android:layout_width="match_parent"                         android:layout_height="80dp"                         android:background="#FF78aa" />                 </RelativeLayout>             </android.support.v7.widget.CardView>               <android.support.v7.widget.CardView                 android:id="@+id/item2_CV"                 android:layout_width="0dp"                 android:layout_height="wrap_content"                 android:layout_marginBottom="4dp"                 android:layout_marginLeft="4dp"                 android:layout_marginRight="8dp"                 android:layout_marginTop="8dp"                 android:layout_weight="1"                 card_view:cardCornerRadius="4dp">                  <RelativeLayout                     android:layout_width="match_parent"                     android:layout_height="wrap_content">                      <LinearLayout                         android:layout_width="match_parent"                         android:layout_height="wrap_content"                         android:layout_alignParentEnd="true"                         android:layout_alignParentLeft="true"                         android:layout_alignParentRight="true"                         android:layout_alignParentStart="true"                         android:layout_below="@+id/item2_image"                         android:background="#fff"                         android:orientation="vertical"                         android:padding="8dp">                          <TextView                             android:id="@+id/item2_title"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:text="Mere Rang Mein"                             android:textColor="#000"                             android:textSize="16sp" />                          <TextView                             android:id="@+id/item2_subTitle"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:singleLine="true"                             android:text="Romance, Hindi, Life OK"                             android:textAppearance="?android:attr/textAppearanceSmall"                             android:textSize="12sp" />                     </LinearLayout>                      <ImageView                         android:id="@+id/item2_image"                         android:layout_width="match_parent"                         android:layout_height="80dp"                         android:background="#FF78aa" />                 </RelativeLayout>             </android.support.v7.widget.CardView>          </TableRow>          <TableRow             android:layout_width="match_parent"             android:layout_height="wrap_content">              <android.support.v7.widget.CardView                 android:id="@+id/item3_CV"                 android:layout_width="0dp"                 android:layout_height="wrap_content"                 android:layout_marginBottom="8dp"                 android:layout_marginLeft="8dp"                 android:layout_marginRight="4dp"                 android:layout_marginTop="4dp"                 android:layout_weight="1"                 card_view:cardCornerRadius="4dp">                  <RelativeLayout                     android:layout_width="match_parent"                     android:layout_height="wrap_content">                      <LinearLayout                         android:layout_width="match_parent"                         android:layout_height="wrap_content"                         android:layout_alignParentEnd="true"                         android:layout_alignParentLeft="true"                         android:layout_alignParentRight="true"                         android:layout_alignParentStart="true"                         android:layout_below="@+id/item3_image"                         android:background="#fff"                         android:orientation="vertical"                         android:padding="8dp">                          <TextView                             android:id="@+id/item3_title"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:text="Mere Rang Mein"                             android:textColor="#000"                             android:textSize="16sp" />                          <TextView                             android:id="@+id/item3_subTitle"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:singleLine="true"                             android:text="Romance, Hindi, Life OK"                             android:textAppearance="?android:attr/textAppearanceSmall"                             android:textSize="12sp" />                     </LinearLayout>                      <ImageView                         android:id="@+id/item3_image"                         android:layout_width="match_parent"                         android:layout_height="80dp"                         android:background="#FF78aa" />                 </RelativeLayout>             </android.support.v7.widget.CardView>               <android.support.v7.widget.CardView                 android:id="@+id/item4_CV"                 android:layout_width="0dp"                 android:layout_height="wrap_content"                 android:layout_marginBottom="8dp"                 android:layout_marginLeft="4dp"                 android:layout_marginRight="8dp"                 android:layout_marginTop="4dp"                 android:layout_weight="1"                 card_view:cardCornerRadius="4dp">                  <RelativeLayout                     android:layout_width="match_parent"                     android:layout_height="wrap_content">                      <LinearLayout                         android:layout_width="match_parent"                         android:layout_height="wrap_content"                         android:layout_alignParentEnd="true"                         android:layout_alignParentLeft="true"                         android:layout_alignParentRight="true"                         android:layout_alignParentStart="true"                         android:layout_below="@+id/item4_image"                         android:background="#fff"                         android:orientation="vertical"                         android:padding="8dp">                          <TextView                             android:id="@+id/item4_title"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:text="Mere Rang Mein"                             android:textColor="#000"                             android:textSize="16sp" />                          <TextView                             android:id="@+id/item4_subTitle"                             android:layout_width="wrap_content"                             android:layout_height="wrap_content"                             android:singleLine="true"                             android:text="Romance, Hindi, Life OK"                             android:textAppearance="?android:attr/textAppearanceSmall"                             android:textSize="12sp" />                     </LinearLayout>                      <ImageView                         android:id="@+id/item4_image"                         android:layout_width="match_parent"                         android:layout_height="80dp"                         android:background="#FF78aa" />                 </RelativeLayout>             </android.support.v7.widget.CardView>          </TableRow>     </TableLayout> </LinearLayout> 

Result: Row layout result

Answers 3

  1. Do I need multiple RecyclerViews or single RecyclerView is enough ?

Single Recyclerview with GridLayoutManager is enough for this purpose.

  1. Do I need to call multiple JSONs or single JSON is enough to fetch data from server?

Single JSON response will fulfill your job.

Answers 4

You can accomplish this just laying out first the TABS and display your CARDS inside of a ViewPager.

Something like this....

@Override     protected void onCreate(Bundle savedInstanceState) {         super.onCreate(savedInstanceState);         setContentView(R.layout.activity_main);         toolbar = (Toolbar)findViewById(R.id.toolBar);         setSupportActionBar(toolbar);         tabLayout = (TabLayout)findViewById(R.id.tabLayout);         viewPager = (ViewPager)findViewById(R.id.viewPager);          viewPagerAdapter = new ViewPagerAdapter(getSupportFragmentManager());         viewPagerAdapter.addFragments... 

Answers 5

    Do I need multiple RecyclerViews or single RecyclerView is enough? 

single RecyclerView.

    Do I need to call multiple JSONs or single JSON is enough to fetch data from server? 

single JSON data from server will do your job.

    How Do I use different - different layouts for You May Also Like and Must Watch Clips 

use recyclerview with multiple view type

public class MyAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {     class ViewHolder0 extends RecyclerView.ViewHolder {         ...     }      class ViewHolder2 extends RecyclerView.ViewHolder {         ...     }      @Override     public int getItemViewType(int position) {         // Just as an example, return 0 or 2 depending on position         // Note that unlike in ListView adapters, types don't have to be contiguous         return position % 2 * 2;     }      @Override     public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {          switch (viewType) {              case 0: return new ViewHolder0(...);              case 2: return new ViewHolder2(...);              ...          }     } } 

Use RecyclerView with header and normal item type

Answers 6

Use this as your layout

<?xml version="1.0" encoding="utf-8"?> <android.support.design.widget.CoordinatorLayout     xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:app="http://schemas.android.com/apk/res-auto"     xmlns:tools="http://schemas.android.com/tools"     android:id="@+id/coordinator"     android:layout_width="match_parent"     android:layout_height="match_parent">      <android.support.design.widget.AppBarLayout         android:id="@+id/appbar"         android:layout_width="match_parent"         android:layout_height="wrap_content"         android:tag="iv"         android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">          <android.support.v7.widget.Toolbar             android:id="@+id/toolbar"             android:layout_width="match_parent"             android:layout_height="?attr/actionBarSize"             android:background="@color/primary"             android:theme="@style/ToolbarStyle"             android:gravity="center_vertical"             app:popupTheme="@style/ThemeOverlay.AppCompat.Light"             app:layout_scrollFlags="scroll|enterAlways|snap"             style="@style/bold" />          <android.support.design.widget.TabLayout             android:id="@+id/tabs"             android:layout_width="match_parent"             android:layout_height="wrap_content"             android:theme="@style/TabLayoutStyle"             android:animateLayoutChanges="true"             app:tabMode="scrollable"             app:tabTextAppearance="@style/TabStyle"/>      </android.support.design.widget.AppBarLayout>      <android.support.v4.view.ViewPager         android:id="@+id/main_container"         android:layout_width="match_parent"         android:layout_height="match_parent"         android:layout_gravity="fill_vertical"         app:layout_behavior="@string/appbar_scrolling_view_behavior" />  </android.support.design.widget.CoordinatorLayout> 
  • The CoordinatorLayout+AppBarLayout will make the toolbar scroll up as you scroll your layout

  • Create a fragment for pages in your ViewPager and write a FragmentStatePagerAdapter for it

  • Don't forget to call tabLayout.setupWithViewPager(viewPager) to inflate the TabLayout

  • See this for an example project

  • Inside your fragment, use a RecyclerView with GridLayoutManager and spanCount 2

  • Inside your RecyclerView.Adapter implementation, use getItemViewType to specify number of view types you want. In the screenshot it looks like you only have 2 types (or 3 if you want the video tile to be a separate viewtype. Note that you can still use same layout for different view types, just hide/show the views you want in each view holder. This will reduce layout duplicacy). Read this to know how to make one.

  • Use CardView to make the the image card

  • Use Picasso, Glide, or Fresco to load images inside those Cards (Picasso and Glide are easier to use compared to Fresco but fresco is better with memory)

Do I need to call multiple JSONs or single JSON is enough to fetch data from server?

That completely depends on you, you can go either way, however getting all data in single request will make fetching faster.

PS: You can use GSON to parse your Json and keep yourself a little sane

Answers 7

I think you not need to use multiple recycler view or Layout

You can just make logic in recycler view on position of item. like if first item don't have play button and text view of time then you can just make by default its visibility gone and when you need that play button and time text view in that position you can make it visible.

for example you have video layout in second position then in get view method you get Position in that you can make logic of this to visible.

I have just create custom listview row for it now what ever you want you can do with this logic and no need to make multiple layout also.

Try this logic hope its help you

Answers 8

Do I need multiple RecyclerViews or single RecyclerView is enough ?

A single one is enough.

Do I need to call multiple JSONs or single JSON is enough to fetch data from server?

A single JSON is enough.

How Do I use different - different layouts for You May Also Like and Must Watch Clips

  • 1 single layout for the section headers, as they look the same
  • 1 layout for "You May Also Like" items
  • 1 layout for "Must Watch Clips" items, because they are different: they have the "minutes" label and the "play" button. You could use the same layout and hide these views when not needed, it's up to you

With the library SectionedRecyclerViewAdapter you can add different "sections" to your RecyclerView, each section can have its own header, like on the image below:

Grid Section with Header

You need to create your "section" classes:

class MustWatchClipsSection extends StatelessSection {      String title;     List<Clip> clipList;      public MustWatchClipsSection(String title, List<Clip> clipList) {         // call constructor with layout resources for this Section header, footer and items          super(R.layout.section_header, R.layout.section_footer,  R.layout.section_item);          this.title = title;         this.clipList = clipList;     }      @Override     public int getContentItemsTotal() {         return clipList.size(); // number of items of this section     }      @Override     public RecyclerView.ViewHolder getItemViewHolder(View view) {         // return a custom instance of ViewHolder for the items of this section         return new MyItemViewHolder(view);     }      @Override     public void onBindItemViewHolder(RecyclerView.ViewHolder holder, int position) {         MyItemViewHolder itemHolder = (MyItemViewHolder) holder;          // bind your view here         itemHolder.tvItem.setText(clipList.get(position).getName());     }      @Override     public RecyclerView.ViewHolder getHeaderViewHolder(View view) {         return new SimpleHeaderViewHolder(view);     }      @Override     public void onBindHeaderViewHolder(RecyclerView.ViewHolder holder) {         MyHeaderViewHolder headerHolder = (MyHeaderViewHolder) holder;          // bind your header view here         headerHolder.tvItem.setText(date);     } } 

Then you set up the RecyclerView with your sections:

// Create an instance of SectionedRecyclerViewAdapter  SectionedRecyclerViewAdapter sectionAdapter = new SectionedRecyclerViewAdapter();  MayAlsoLikeSection mySection1 = new MayAlsoLikeSection("You May Also Like", mediaList); MustWatchClipsSection mySection2 = new MustWatchClipsSection("Must Watch Clips", clipList);  // Add your Sections sectionAdapter.addSection(mySection1); sectionAdapter.addSection(mySection2);  // Set up your RecyclerView with the SectionedRecyclerViewAdapter RecyclerView recyclerView = (RecyclerView) findViewById(R.id.recyclerview); GridLayoutManager glm = new GridLayoutManager(getContext(), 2); glm.setSpanSizeLookup(new GridLayoutManager.SpanSizeLookup() {     @Override     public int getSpanSize(int position) {         switch(sectionAdapter.getSectionItemViewType(position)) {             case SectionedRecyclerViewAdapter.VIEW_TYPE_HEADER:                 return 2;             default:                 return 1;         }     } }); recyclerView.setLayoutManager(glm); recyclerView.setAdapter(sectionAdapter); 

You can see the full code here, layouts are also available in the repository.

Read More

Karma tests error “unable to init ocLazyLoad”

Leave a Comment

From the quickstart sb-admin-angular, I am trying to run the tests, but I get the error unable to init ocLazyLoad. (This is a Windows7 machine.)

The command I use to run the tests is:

$ grunt test --force 

I understand from this thread that I must make sure that the path to the ocLazyLoad script is added in karma.conf.js.

files: [   'bower_components/angular/angular.js',   'bower_components/angular-mocks/angular-mocks.js',   ...   'bower_components/oclazyload/dist/ocLazyLoad.min.js',   'app/scripts/**/*.js',   'test/mock/**/*.js',   'test/spec/**/*.js' ], 

I have also tried using Bower to reinstall ocLacyLoad, as suggested in the aforementioned thread. I was given a choice of versions and selected the first option:

Unable to find a suitable version for oclazyload, please choose one:     1) oclazyload#~0.5.2 which resolved to 0.5.2 and is required by sb-admin     2) oclazyload#^1.0.9 which resolved to 1.0.9 

What step am I missing or corrupting here, please?

2 Answers

Answers 1

I would update oclazyload in bower.json file to version 0.6.0 or higher. Some 0.5.x version introduced this bug and it is solved at 0.6.0 version on.

Current value on bower.json value of the example was 0.5.2 which you used, too.

References:

[1] https://github.com/ocombe/ocLazyLoad/issues/122 (issue in GitHub)

Answers 2

It looks like this is what you are experiencing:

This should be fixed in ocLazyLoad 0.6.0.

Read More

Align cell in center(horizontally) in UICollectionView

Leave a Comment

I am first time working with UICollectionView not sure how to do this. I am trying to create an app for tvOS and want to display the menu like airbnb tvos app. I have somehow tried to achieve that particular format didUpdateFocusInContext but the problem is about the first appearance because the first appearance takes place on default points i.e 0,0 of collection view which results in a mess. Heres my code what I have done so far.

func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {          if let cell = collectionView.dequeueReusableCellWithReuseIdentifier("cell", forIndexPath: indexPath) as? ShowCell {               menuData = dataArray[indexPath.row] as! NSDictionary               cell.configureCell(menuData.objectForKey("name") as! String)              return cell         }         else {             return ShowCell()         }     }  override func didUpdateFocusInContext(context: UIFocusUpdateContext, withAnimationCoordinator coordinator: UIFocusAnimationCoordinator) {          if let previousItem = context.previouslyFocusedView as? ShowCell {             UIView.animateWithDuration(0.2, animations: { () -> Void in                 previousItem.showImg.frame.size = self.originalCellSize             })         }         if let nextItem = context.nextFocusedView as? ShowCell {             UIView.animateWithDuration(0.2, animations: { () -> Void in                 nextItem.showImg.frame = CGRectMake(self.view.frame.width/2 - self.focusCellSize.width/2, 169.0 , self.focusCellSize.width, self.focusCellSize.height)              })         } 

This is the view which I want to achieve and I have achieved it but for later indexes means index after 1,2enter image description here

This is the starting behaviour when it appears for the first time and when I move the control to it it happens like this enter image description here

enter image description here

This is what i actually want, but i am struggling in getting my focused cell to the middle of the screen and similarly my previous and next on the either sides . I know i am giving frames coordinates explicitly which isn't correct this was just a test case i was running and nothing else but i couldn't find the way to do this

1 Answers

Answers 1

I'd control the focus and the collection content offset (scroll position) separately.

For the content offset you should set the section margins and the inter-item spacing so that you have one cell centred and the adjacent cells visible at the edges. You can get this setup and tested without showing any focus.

Now, the focus should be managed by the cell itself, not the collection view. Below is a (slightly large) example of a cell focus change animation. It uses cartography to change image view constraints and applies a transform to a label. You can do something similar depending on how you want the image and label to interact with each other.

Note that the below code also applies a motion effect transform similar to the stock supplied by apple when a UIImageView has focus and has adjustsImageWhenAncestorFocused set. If you don't want that you can simplify and shorten the code quite a bit.

override func didUpdateFocusInContext(context: UIFocusUpdateContext, withAnimationCoordinator coordinator: UIFocusAnimationCoordinator) {     super.didUpdateFocusInContext(context, withAnimationCoordinator: coordinator)      if (context.nextFocusedView == self) {         UIView.animateWithDuration(0.1,             animations: { () -> Void in                 self.imageConstraints = constrain(self.itemImageView, replace: self.imageConstraints!) {                     $0.top == $0.superview!.top                     $0.bottom == $0.superview!.bottom                     $0.leading == $0.superview!.leading                     $0.trailing == $0.superview!.trailing                 }                 self.itemLabel.transform = CGAffineTransformMakeTranslation(0, 60)                 self.itemLabel.layer.backgroundColor = UIColor.darkGrayColor().colorWithAlphaComponent(0).CGColor                  self.layer.shadowOpacity = 1                  self.layoutIfNeeded()             }, completion: nil)          let minMaxAngle = 10.0         let m34 = CGFloat(1.0 / -1250)         let angle = CGFloat(minMaxAngle * M_PI / 180.0)          var baseTransform = CATransform3DIdentity         baseTransform.m34 = m34          let rotateXmin = CATransform3DRotate(baseTransform, -1 * angle, 1.0, 0.0, 0.0);         let rotateXmax = CATransform3DRotate(baseTransform, angle, 1.0, 0.0, 0.0);         let rotateYmin = CATransform3DRotate(baseTransform, angle, 0.0, 1.0, 0.0);         let rotateYmax = CATransform3DRotate(baseTransform, -1 * angle, 0.0, 1.0, 0.0);          let verticalMotionEffect = UIInterpolatingMotionEffect(keyPath: "layer.transform",             type: .TiltAlongVerticalAxis)         verticalMotionEffect.minimumRelativeValue = NSValue(CATransform3D: rotateXmin)         verticalMotionEffect.maximumRelativeValue = NSValue(CATransform3D: rotateXmax)          let horizontalMotionEffect = UIInterpolatingMotionEffect(keyPath: "layer.transform",             type: .TiltAlongHorizontalAxis)         horizontalMotionEffect.minimumRelativeValue = NSValue(CATransform3D: rotateYmin)         horizontalMotionEffect.maximumRelativeValue = NSValue(CATransform3D: rotateYmax)          let group = UIMotionEffectGroup()         group.motionEffects = [horizontalMotionEffect, verticalMotionEffect]          self.addMotionEffect(group)      }     else {         UIView.animateWithDuration(0.3,             animations: { () -> Void in                 self.imageConstraints = constrain(self.itemImageView, replace: self.imageConstraints!) {                     $0.top == $0.superview!.top + 20                     $0.bottom == $0.superview!.bottom - 20                     $0.leading == $0.superview!.leading + 20                     $0.trailing == $0.superview!.trailing - 20                 }                 self.itemLabel.transform = CGAffineTransformIdentity                 self.itemLabel.layer.backgroundColor = UIColor.darkGrayColor().colorWithAlphaComponent(0.75).CGColor                  self.layer.shadowOpacity = 0                  self.layoutIfNeeded()             }, completion: nil)          for effect in self.motionEffects {             self.removeMotionEffect(effect)         }     } } 
Read More

How to identify a user on iOS?

Leave a Comment

I am using LibGDX and for the Android version of my game I use the "Get Accounts" permission to identify a user by their Gmail address.

Is their a similar way to identify a user for iOS?

3 Answers

Answers 1

According to the App Store Guidelines, you shouldn't get user's personal data without obtaining the user's prior permission. The only identifier you can use anonymously is identifierForVendor:

UIDevice.currentDevice().identifierForVendor?.UUIDString 

This identifier is common for all your apps on the user's device. If all the apps were deleted from the device, the identifier may change. More.

Answers 2

Your best bet is to use GameCenter on iOS for identifying the players this link provides a little more info on handling users with GameCenter: https://developer.apple.com/library/ios/documentation/NetworkingInternet/Conceptual/GameKit_Guide/Users/Users.html

Answers 3

According to Apple, you shouldn't identify your users, unless you have a good reason to do so.

Like @Marat said, what you are looking for is the UUID, but keep in mind that this value may change (for example, if the user delete your app and have none of your other apps).

A possible solution would be to keep the UUID value in the keychain, and that way you will always use the same value.

Edit: Since your app is a game, you can use Apple's GameCenter. This will identify the users for you.

https://developer.apple.com/game-center/

Read More

How Do I Set Up Visual Studio 2015 with SDL2 For Android, iOS, and Windows Development?

Leave a Comment

Visual Studio 2015 has integrated Android Emulator support. They even have a pre-made template to set up Windows Phone, Android, and iOS targets. It seems like there should be some way of setting up SDL 2.0 in the same solution to easily toggle between Android and Windows. I am really hoping for an existing template which includes SDL 2.0, or a tutorial on the subject.

Where am I at right now? I have a working code base which I've been maintaining in visual studio 2015 based on SDL 2.0, Quite some time back I ported it to Xcode on my mac manually and I was able to run in the emulator. I have not run on Android yet. The port in xcode has likely gone stale though as I've updated multiple libraries and it was three years ago.

My ideal answer to this question would result in a working Visual Studio 2015 project with SDL 2.0 configured for iOS, Android, and Windows. What I am looking for is a series of steps to create a template project that can be used as a starting point to get an OpenGL context initialized via SDL on Windows or the Android emulator.

This might be asking a lot, but I'm hoping someone has already done the work and can simply share it with the world here.

2 Answers

Answers 1

I searched a lot for you, unfortunately couldnt find a strict tutorial about what u exactly ask. I am sharing all things I found, I know it is not directly related to what you want but maybe can help:

include <SDL.h>     int main(int argc, char ** argv)     {         SDL_Init(SDL_INIT_VIDEO);         SDL_Quit();         return 0;     } 
  1. Go to http://www.libsdl.org/download-2.0.php and download SDL2-devel-2.0.4-VC.zip
  2. Open a folder under C namely SDL2, C:\SDL2, and extract the libraries inside the zip file to this folder.
  3. Open an empty c++ project in vs2015, go to its properties page and add ;C:\SDL2\include to the end of Configuration Properties -> Include Directories
  4. Again in properties page (same as 3), Go to Linker -> General and write C:\SDL2\lib\x86 to Additional Library Directories (x64 if u are using 64bit OS).
  5. Go to Linker -> Input on the same page and write SDL2.lib; SDL2main.lib instead what writing on Additional Dependencies.
  6. GO to Linker -> System and write Windows (/SUBSYSTEM:WINDOWS) to the SubSystem.
  7. Add main.cpp under Source folder in your project and its code will be the one at the top of this message. Run this code. If you use VS2013, your work would be done, but now u will receive some errors.

TO FIX:

  1. Go to https://buildbot.libsdl.org/sdl-builds/sdl-visualstudio/ and download the latest one at the bottom.
  2. Extract the libs inside the folder C:\SDL2
  3. Make sure you wrote C:\SDL2\lib\x86 under Linker -> General because x64 does not work for this task!
  4. Run the program again. If you receive an error: Go to C:\SDL2\lib\x86 and grab SDL2.dll and put it in your project’s Debug folder
  5. In your project’s properties, go to the Debugging section and change the value of Working Directory from $(ProjectDir) to $(SolutionDir)$(Configuration)\

This is how we install SDL2 to VS2015

Ref: http://gigi.nullneuron.net/gigilabs/setting-up-sdl2-with-visual-studio-2015/

This site might be useful as well: https://wiki.libsdl.org/Installation

Answers 2

An alternative is to develop apps with Unity(3D)/ LibGDX(2D) and not SDL, or get the assembly of your final SDL project and run it as a dll (as assembly so you can run it in the Android OS, for example).

Compiler options for SDL are just like for any usual SDL IDE (CodeBlocks).

Read More

Show BASE64 video with node/express

Leave a Comment

So, bit of an odd problem. I have a bunch of media files saved as base64 strings in mongo, some are images, some are videos.

I made an API for getting the media files:

app.get('/api/media/:media_id', function (req, res) {     media.findById(req.params.media_id)         .exec(function (err, media) {             if (err) {                 res.send(err);             }              var file = new Buffer(media.file, 'base64');             res.writeHead(200, {'Content-Type': media.type, 'Content-Transfer-Encoding': 'BASE64', 'Content-Length': file.length});             res.end(file);         }); }); 

Now, images have no problems. They load just fine, both directly from the API, and when I call the API from a front-end (for example <img src="/api/media/23498423">)

THE PROBLEM

If I fetch a video from a front-end, like the images - but with a video- or object-tag:

<video src="/api/media/3424525" controls></video> 

there's no problem, but if I load the video in a browser directly from the API:

http://localhost:8080/api/media/3424525 

the server process crashes, no errors. It simply just freezes up. And we're not talking about huge video files - it's a 1.5MB video.

The media type in the header for all the videos I'm testing with is video/mp4. Oh, and just to be clear: if I do the same with images, everything works perfectly.

EDIT:

Okay, so as suggested by @idbehold and @zeeshan I took a look at gridfs and gridfs-stream, and for the purpose of my app, this certainly is what I should have used in the first place. However, after implementing gridfs in my app, the problem still persists.

app.get('/api/media/:media_id', function (req, res) {     gfs.findOne({ _id: req.params.media_id }, function (err, file) {         if (err) {             return res.status(400).send(err);         }         if (!file) {             return res.status(404).send('');         }          res.set('Content-Type', file.contentType);         res.set('Content-Disposition', 'inline; filename="' + file.filename + '"');          var readstream = gfs.createReadStream({             _id: file._id         });          readstream.on("error", function (err) {             console.log("Got an error while processing stream: ", err.message);             res.end();         });          readstream.pipe(res);     }); }); 

When I call the media file (be it image or video) from a front-end, within a HTML tag, everything works out fine. But if I load a video (again, smallish videos from 1.5mb to max 6mb total size) directly in the browser, the server process freezes. To be a bit more clear: I am testing on windows, and the server app (server.js) is run in console. The console and the process it is running is what freezes. I cannot load any more pages/views in the node app, and I cannot even stop/kill/shutdown the node app or the console.

3 Answers

Answers 1

Streaming videos directly to/from GridFS using gridfs-stream either with mongodb-native db instance or mongoose.

var mongo = require('mongodb'),     Grid = require('gridfs-stream'),     db = new mongo.Db('yourDatabaseName', new mongo.Server("127.0.0.1", 27017)),     gfs = Grid(db, mongo);  //store app.post('/video', function (req, res) {     req.pipe(gfs.createWriteStream({         filename: 'file_name_here'     }));     res.send("Success!"); });  //get app.get('/video/:vid', function (req, res) {     gfs.createReadStream({         _id: req.params.vid // or provide filename: 'file_name_here'     }).pipe(res); }); 

for complete files and running project:

Clone node-cheat direct_upload_gridfs, run node app followed by npm install express mongodb gridfs-stream.

Answers 2

Truly an odd problem...
I could be way off, but it's worth a shot:

One of the differences when opening a url directly from the browser is that the browser will also try to fetch http://localhost:8080/favicon.ico (while trying to find the tab icon). Maybe the problem is not related to your video code, but rather to some other route, trying to handle the /favicon.ico request?

Have you tried using wget or curl?

Answers 3

I don't know the answer, maybe this is could be dumb suggest, but what is the browser are you using? Maybe something from Microsoft causes the problem...

Read More

Hadoop: …be replicated to 0 nodes instead of minReplication (=1). There are 1 datanode(s) running and no node(s) are excluded in this operation

Leave a Comment

I'm getting the following error when attempting to write to HDFS as part of my multi-threaded application

could only be replicated to 0 nodes instead of minReplication (=1).  There are 1 datanode(s) running and no node(s) are excluded in this operation. 

I've tried the top-rated answer here around reformatting but this doesn't work for me: HDFS error: could only be replicated to 0 nodes, instead of 1

What is happening is this:

  1. My application consists of 2 threads each one configured with their own Spring Data PartitionTextFileWriter
  2. Thread 1 is the first to process data and this can successfully write to HDFS
  3. However, once Thread 2 starts to process data I get this error when it attempts to flush to a file

Thread 1 and 2 will not be writing to the same file, although they do share a parent directory at the root of my directory tree.

There are no problems with disk space on my server.

I also see this in my name-node logs, but not sure what it means:

2016-03-15 11:23:12,149 WARN org.apache.hadoop.hdfs.server.blockmanagement.BlockPlacementPolicy: Failed to place enough replicas, still in need of 1 to reach 1 (unavailableStorages=[], storagePolicy=BlockStoragePolicy{HOT:7, storageTypes=[DISK], creationFallbacks=[], replicationFallbacks=[ARCHIVE]}, newBlock=true) For more information, please enable DEBUG log level on org.apache.hadoop.hdfs.server.blockmanagement.BlockPlacementPolicy 2016-03-15 11:23:12,150 WARN org.apache.hadoop.hdfs.protocol.BlockStoragePolicy: Failed to place enough replicas: expected size is 1 but only 0 storage types can be selected (replication=1, selected=[], unavailable=[DISK], removed=[DISK], policy=BlockStoragePolicy{HOT:7, storageTypes=[DISK], creationFallbacks=[], replicationFallbacks=[ARCHIVE]}) 2016-03-15 11:23:12,150 WARN org.apache.hadoop.hdfs.server.blockmanagement.BlockPlacementPolicy: Failed to place enough replicas, still in need of 1 to reach 1 (unavailableStorages=[DISK], storagePolicy=BlockStoragePolicy{HOT:7, storageTypes=[DISK], creationFallbacks=[], replicationFallbacks=[ARCHIVE]}, newBlock=true) All required storage types are unavailable:  unavailableStorages=[DISK], storagePolicy=BlockStoragePolicy{HOT:7, storageTypes=[DISK], creationFallbacks=[], replicationFallbacks=[ARCHIVE]} 2016-03-15 11:23:12,151 INFO org.apache.hadoop.ipc.Server: IPC Server handler 8 on 9000, call org.apache.hadoop.hdfs.protocol.ClientProtocol.addBlock from 10.104.247.78:52004 Call#61 Retry#0 java.io.IOException: File /metrics/abc/myfile could only be replicated to 0 nodes instead of [2016-03-15 13:34:16,663] INFO [Group Metadata Manager on Broker 0]: Removed 0 expired offsets in 1 milliseconds. (kafka.coordinator.GroupMetadataManager) 

What could be the cause of this error?

Thanks

1 Answers

Answers 1

This error is caused by the block replication system of HDFS since it could not manage to make any copies of a specific block within the focused file. Common reasons of that:

  1. Only a NameNode instance is running and it's not in safe-mode
  2. There is no DataNode instances up and running, or some are dead. (Check the servers)
  3. Namenode and Datanode instances are both running, but they cannot communicate with each other, which means There is connectivity issue between DataNode and NameNode instances.
  4. Running DataNode instances are not able to talk to the server because of some networking of hadoop-based issues (check logs that include datanode info)
  5. There is no hard disk space specified in configured data directories for DataNode instances or DataNode instances have run out of space. (check dfs.data.dir // delete old files if any)
  6. Specified reserved spaces for DataNode instances in dfs.datanode.du.reserved is more than the free space which makes DataNode instances to understand there is no enough free space.
  7. There is no enough threads for DataNode instances (check datanode logs and dfs.datanode.handler.count value)
  8. Make sure dfs.data.transfer.protection is not equal to “authentication” and dfs.encrypt.data.transfer is equal to true.

Also please:

  • Verify the status of NameNode and DataNode services and check the related logs
  • Verify if core-site.xml has correct fs.defaultFS value and hdfs-site.xml has a valid value.
  • Verify hdfs-site.xml has dfs.namenode.http-address.. for all NameNode instances specified in case of PHD HA configuration.
  • Verify if the permissions on the directories are correct

Ref: https://wiki.apache.org/hadoop/CouldOnlyBeReplicatedTo

Ref: https://support.pivotal.io/hc/en-us/articles/201846688-HDFS-reports-Configured-Capacity-0-0-B-for-datanode

Also, please check: Writing to HDFS from Java, getting "could only be replicated to 0 nodes instead of minReplication"

Read More

PHP Azure OAuth JWT App Roles

Leave a Comment

I've created an application in an Azure AD from a manifest with several appRoles inside of it, and I can assign users to these roles. After a user completes the single sign on, returns to my application and I then request a JSON Web Token from their login. The problem is, there are no assigned roles listed in the token I get back from Azure, as it would suggest there's supposed to be here.

Is there a configuration option I'm missing or is there an alternate way to find out their assigned role through the Azure Graph API?


Update:

After specifying the resource as the App ID URI when requesting the authorisation URL I've managed to get a little further.

I'm now getting back the following error (in the return URL):

"The signed in user '<user email>' is not assigned to a role for the application '<app client id>'." 

The user has definitely been assigned a role in the Azure AD control panel for the app, and the app client id in the error message matches the app's client id exactly.


Application config:

Azure AD Application config screen

User assigned a role:

Azure AD Application user role assignments

Error message after logging in and returning to app:

Azure AD Authentication error message

1 Answers

Answers 1

@Phlip,Could you please try to set your application permission using PowerShell?

#1.down load Azure AD powershell and login in using your user in AD $msolcred=get-credential connect-msolservice -credential $msolcred  #2. get principal Id  $ClientIdWebApp = '5b597c35-**-**-ad05-***' $webApp = Get-MsolServicePrincipal –AppPrincipalId $ClientIdWebApp  # 3. use Add-MsolRoleMember to add it to “Company Administrator” role). Add-MsolRoleMember -RoleName "Company Administrator" -RoleMemberType ServicePrincipal -RoleMemberObjectId $webApp.ObjectId 

For more information, please refer to this page: https://msdn.microsoft.com/en-us/library/azure/dn919663.aspx and Use this methods to add member into role:

Add-MsolRoleMember -RoleName "Company Administrator" -RoleMemberEmailAddress "user@contoso.com" 

Any updates or results, please let me know.

Read More

Internal ruby error in vim

Leave a Comment

I've been having this problem for a while with vim. The first time I do anything that interacts with ruby, such as :ruby puts "test", I get <internal:gem_prelude>:1:in 'require': cannot load such file -- rubygems.rb (LoadError).

Some diagnostic information that may be useful : my OS is OS X 10.11.2, Vim is version 7.4, ruby is 2.1.2 installed with rvm, my shell is zsh (but this also happens with bash), and my vim is completely vanilla.

 $  ruby --version ruby 2.1.2p95 (2014-05-08 revision 45877) [x86_64-darwin13.0]  $  rvm list  rvm rubies  =* ruby-2.1.2 [ x86_64 ]  # => - current # =* - current && default #  * - default   $  which -a ruby /Users/marcusbuffett/.rvm/rubies/ruby-2.1.2/bin/ruby /usr/local/bin/ruby /usr/local/bin/ruby /usr/bin/ruby  $  vim --version VIM - Vi IMproved 7.4 (2013 Aug 10, compiled Mar 18 2016 09:07:16) MacOS X (unix) version Included patches: 1-1401 Compiled by Homebrew Huge version without GUI.  Features included (+) or not (-): +acl             +farsi           +mouse_netterm   +syntax +arabic          +file_in_path    +mouse_sgr       +tag_binary +autocmd         +find_in_path    -mouse_sysmouse  +tag_old_static -balloon_eval    +float           +mouse_urxvt     -tag_any_white -browse          +folding         +mouse_xterm     -tcl ++builtin_terms  -footer          +multi_byte      +terminfo +byte_offset     +fork()          +multi_lang      +termresponse +channel         -gettext         -mzscheme        +textobjects +cindent         -hangul_input    +netbeans_intg   +title -clientserver    +iconv           +packages        -toolbar +clipboard       +insert_expand   +path_extra      +user_commands +cmdline_compl   +job             +perl            +vertsplit +cmdline_hist    +jumplist        +persistent_undo +virtualedit +cmdline_info    +keymap          +postscript      +visual +comments        +langmap         +printer         +visualextra +conceal         +libcall         +profile         +viminfo +cryptv          +linebreak       +python          +vreplace +cscope          +lispindent      -python3         +wildignore +cursorbind      +listcmds        +quickfix        +wildmenu +cursorshape     +localmap        +reltime         +windows +dialog_con      -lua             +rightleft       +writebackup +diff            +menu            +ruby            -X11 +digraphs        +mksession       +scrollbind      -xfontset -dnd             +modify_fname    +signs           -xim -ebcdic          +mouse           +smartindent     -xsmp +emacs_tags      -mouseshape      -sniff           -xterm_clipboard +eval            +mouse_dec       +startuptime     -xterm_save +ex_extra        -mouse_gpm       +statusline      -xpm +extra_search    -mouse_jsbterm   -sun_workshop    system vimrc file: "$VIM/vimrc"      user vimrc file: "$HOME/.vimrc"  2nd user vimrc file: "~/.vim/vimrc"       user exrc file: "$HOME/.exrc"   fall-back for $VIM: "/usr/local/share/vim" Compilation: /usr/bin/clang -c -I. -Iproto -DHAVE_CONFIG_H   -F/usr/local/Frameworks -DMACOS_X_UNIX  -Os -w -pipe -march=native -mmacosx-version-min=10.11 -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=1 Linking: /usr/bin/clang   -L. -L/Users/travis/.sm/pkg/active/lib -fPIC -Bstatic -fstack-protector -L/usr/local/lib -F/usr/local/Frameworks -Wl,-headerpad_max_install_names -o vim        -lm  -lncurses -liconv -framework Cocoa   -fstack-protector  -L/System/Library/Perl/5.18/darwin-thread-multi-2level/CORE -lperl -framework Python   -lruby-static -framework CoreFoundation -lobjc -L/Users/marcusbuffett/.rvm/rubies/ruby-2.1.2/lib 

1 Answers

Answers 1

Assuming that ruby works for you normally when using from the command line, I suspect that the problem comes from the fact that you are trying to use a RVM ruby in VIM and VIM doesn't use a login shell by default. RVM, on the other hand has it's initialization done in the shell init scripts, which are run only in login shells, which you get e.g. when you open a terminal.

Now, as you have also a system ruby installed in /usr/local, VIM sees this system ruby instead of the RVM one. And I guess you don't have rubygems installed in the system ruby.

So, one quick method is to force VIM to use the login shell, so that it behaves the same way as your command line. This is answered in this SO question, and I quote from there:

# ~/.vimrc set shell=bash\ -l 

Another option would be to manually set the VIM PATH so that the first found ruby is the one from RVM, not the system one.

Read More

SSRS and powershell: Parameter not accepted

Leave a Comment

I use Powershell to run several reports on Microsoft SQL Report Services and to save the results to a Word doc. I have a script with functions that handle communications with the Report Server:

## File "qrap-functions.ps1" function GetRSConnection($server, $instance) {     $User = "xxxx"     $PWord = ConvertTo-SecureString -String "yyyy" -AsPlainText -Force     $c = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $User, $PWord      $reportServerURI = "http://" + $server + "/" + $instance + "/ReportExecution2005.asmx?WSDL"      $RS = New-WebServiceProxy -Class 'RS' -NameSpace 'RS' -Uri $reportServerURI -Credential $c     $RS.Url = $reportServerURI     return $RS } function GetReport($RS, $reportPath) {     $reportPath = "/" + $reportPath     #$reportPath     $Report = $RS.GetType().GetMethod("LoadReport").Invoke($RS, @($reportPath, $null))           $parameters = @()     $RS.SetExecutionParameters($parameters, "nl-nl") > $null     return $report } function AddParameter($params, $name, $val) {     $par = New-Object RS.ParameterValue     $par.Name = $name     $par.Value = $val     $params += $par     return ,$params } function GetReportInFormat($RS, $report, $params, $format, $saveas) {     $deviceInfo = "<DeviceInfo><NoHeader>True</NoHeader></DeviceInfo>"     $extension = ""     $mimeType = ""     $encoding = ""     $warnings = $null     $streamIDs = $null      $RS.SetExecutionParameters($params, "nl-nl") > $null      $RenderOutput = $RS.Render($format,         $deviceInfo,         [ref] $extension,         [ref] $mimeType,         [ref] $encoding,         [ref] $warnings,         [ref] $streamIDs     )     $Stream = New-Object System.IO.FileStream($saveas), Create, Write     $Stream.Write($RenderOutput, 0, $RenderOutput.Length)     $Stream.Close() } 

Then, I have a script that executes a report containing the financial quarterly data. This script runs fine:

## File "qrap-financieel.ps1" . "./qrap-functions.ps1"  $saveas = "e:\test\financieel.doc" $RS = GetRSConnection -server "MSZRDWH" -instance "reportserver_acc" $report = GetReport -RS $RS -reportPath "kwartaalrapportage/kwartaalrapportage financieel" $params = @()    $kwartaal = "[Periode Maand].[Jaar Kwartaal].&[2015-2]" $kptc = "[Kostenplaats].[Team code].&[2003]"  $params = AddParameter -params $params -name "PeriodeMaandJaarKwartaal" -val $kwartaal $params = AddParameter -params $params -name "KostenplaatsTeamcode" -val $kptc  GetReportInformat -RS $RS -report $report -params $params -format "WORD" -saveas $saveas 

The values for $kwartaal and $kptc are hard-coded here, but are parameters in the actual version of this script. Besides the financial quarterly, we have three other quarterly reports that need to be output by this script. Two of these run fine, in the fourth I can't seem to get one of the parameters right. The script for that one is:

## File "qrap-zorglog.ps1" . "./qrap-functions.ps1" $RS = GetRSConnection -server "MSZRDWH" -instance "reportserver_acc" $report = GetReport -RS $RS -reportPath "kwartaalrapportage/kwartaalrapportage zorglogistiek"  $s = "Urologie" $saveas = "e:\test\ZL Urologie.doc" $params = @()    $kwartaal = "[Periode Maand].[Jaar Kwartaal].&[2015-2]"   $params = AddParameter -params $params -name "HoofdspecialismeSpecialismeOms"                       -val "[Hoofdspecialisme].[Specialisme Oms].&[$s]" $params = AddParameter -params $params -name "PeriodeMaandJaarKwartaal"                             -val $kwartaal $params = AddParameter -params $params -name "WachttijdenSpecialismeSpecialisme"                    -val "[Wachttijden Specialisme].[Specialisme].&[$s]" $params = AddParameter -params $params -name "SpecialisatieGroeperingSpecialisatieGroeperingOms"    -val "[Specialistie Groepering].[Specialistie Groepering Oms].&[$s]"     $params = AddParameter -params $params -name "AanvragendSpecialismeSpecialismeOms"                  -val "[AanvragendSpecialisme].[Specialisme Oms].&[$s]"  GetReportInformat -RS $RS -report $report -params $params -format "WORD" -saveas $saveas 

When I execute this script, I get this error:

Exception calling "Render" with "7" argument(s): "System.Web.Services.Protocols.SoapException: This report requires a  default or user-defined value for the report parameter 'HoofdspecialismeSpecialismeOms'. To run or subscribe to this  report, you must provide a parameter value. ---> Microsoft.ReportingServices.Diagnostics.Utilities.ReportParameterValueNot SetException: This report requires a default or user-defined value for the report parameter  'HoofdspecialismeSpecialismeOms'. To run or subscribe to this report, you must provide a parameter value. 

I clearly DO supply a value for 'HoofdspecialismeSpecialismeOms'; I've previously noticed that this error also is thrown when the parameter is not in the expected format. This format, since the report filter is based on a hierarchy in an SSAS cube, looks like this: [hierarchy].[sub-level].&[member]. I've ensured that [Hoofdspecialisme].[Specialisme Oms].&[$s] is the correct format by looking it up in the query that populates the prompt in SSRS. The report does display data when run through SSRS - and taking a parameter from the prompt.

I did notice that this parameter allows multiple selection. However, I don't believe this leads to the error because that is also true for AanvragendSpecialismeSpecialismeOms.

Any idea why this one parameter fails to be fed into the report when calling GetReportInformat?

1 Answers

Answers 1

Have you tried

function AddParameter($params, $name, $val) {     $par = New-Object RS.ParameterValue     $par.Name = $name     $par.Value = $val     $params += $par     return ,$params     #      ^Removing this comma? } 

As well as declaring the data types explicitly for your parameters?

function AddParameter([Array]$params, [String]$name, [String]$val) {     $par = New-Object RS.ParameterValue     $par.Name = $name     $par.Value = $val     $params += $par     return ,$params } 

Also, with so many user-defined helper functions calling imported types that call methods and set properties to a report we can't see, it can get a little difficult to help troubleshoot in-depth for this specific report you're getting an error on. It looks like you've tried moving the line around in the order which sounds to me like you might have an issue with how that specific report parses the values you input through RS.ParameterValue so maybe take a look at if it accepts the string you set in -val for your AddParameter user defined function.

Edit:

From https://social.msdn.microsoft.com/Forums/sqlserver/en-US/e38b4a34-c780-43bb-8321-15f96d0938a9/exception-calling-render-systemwebservicesprotocolssoapexception-one-or-more-data-source?forum=sqlreportingservices

This error is generated when you are attempting to run a report in which one or more of the data sources are set to "prompt" credentials. This means we do not use your Windows credentials automatically, but rather you need to supply a different set of credentials which are used only for the data source.

Sounds like you might need to put aside the script and check if the report is different.

Read More

How to bundle httrack into a python 3 executable

Leave a Comment

There is a great website copier that I would like to bundle in my executable, created with python 3 and py2exe.
On the HTTrack official website in the FAQ section they say that there is a DLL/library version available.
But I don't know where to start, or even how to use the DLL once it would be bundled in the executable.
So how can I bundle httrack into a python 3 executable, and use its features to start copying websites?
Edit:
I found httrack-py 0.6.1 but it only supports python 2 and uses an old version of httrack, so I can't use this for my executable.

1 Answers

Answers 1

As I see it you have 2 options:

  1. You could try to convert httrack-py to python 3 following these instructions, but it's usually never a good idea to work with outdated and unmaintained 3rd party library.

  2. Since the official HTTrack provides you with DLL, you can use the library directly from python 3 code. A stackoverflow question How can I use a DLL file from Python? gives an excellent answer on how to do just that.

    The py2exe merely creates a windows installer which will take care of the details of installing python interpreter and your python code to the target system so that end user does not need to deal with anything else than just one .exe . This means you have to include 3rd party DLL's in the configuration - I would guess 3rd party DLL's to go into "data_files" (not tested this myself though).

Read More

my iOS application does not handle image file type in all application

Leave a Comment

I want my app to be in 'Open in' options for image.

I have used this code in my Info.plist

<key>CFBundleDocumentTypes</key> <array>     <dict>         <key>CFBundleTypeName</key>         <string>Image</string>         <key>LSHandlerRank</key>         <string>Alternate</string>         <key>LSItemContentTypes</key>         <array>             <string>public.image</string>         </array>     </dict>     <dict>         <key>CFBundleTypeName</key>         <string>PNG image</string>         <key>LSHandlerRank</key>         <string>Alternate</string>         <key>LSItemContentTypes</key>         <array>             <string>public.png</string>         </array>     </dict>     <dict>         <key>CFBundleTypeName</key>         <string>JPEG image</string>         <key>LSHandlerRank</key>         <string>Alternate</string>         <key>LSItemContentTypes</key>         <array>             <string>public.jpeg</string>         </array>     </dict> </array> 

In the application 'Inbox', on sharing an image, i can see my app 'Quotle' :

enter image description here

But in Apple's application 'Photo', i don't see my app :

enter image description here

What can i do to see my app in sharing menu into application 'Photo'?

1 Answers

Answers 1

In order to show your app in Photo's Share to list, you need to add a new target of Share Extension into your project, please refer the document for more info on how to add the Share Extension.

Read More

Create Azure Load Balancer for existing VMs in Azure Preview Portal

Leave a Comment

I wouldn't generally ask such questions on SO but my patience has run out as I have lost a day on this. Does anyone know how on earth someone can create a simple Load Balancer to load balance two existing VMs. The VMs are Rabbit MQs and I need to put a load balancer in front to distribute the traffic accordingly.

I wish I could give bounty to anyone that helps out.

Thanks

1 Answers

Answers 1

In your resource group, click + New to add a new resource and then search for "Load Balancer".

I have just tested, it seems to work :

azure load balancer

Once created, you can configure it to create your load balancing rules (and target your VMs).

Hope this helps,

Julien

Read More

Contact Framework equivalent to ABAddressBook.ABAddressBookRegisterExternalChangeCallback

Leave a Comment

I am migrating an application from the deprecated Address Book Framework to the new Contacts Framework. The application utilizes ABAddressBookRegisterExternalChangeCallback to be notified when another application changes a contact.

I am unable to find equivalent functionality in the Contacts Framework. Apple documentation says to use the default notification center with the CNContactStoreDidChangeNotification notification:

The notification posted when changes occur in another CNContactStore.

Taking Apple's advice, my code looks like this:

NSNotificationCenter.defaultCenter().addObserver(     self,     selector: "contactsChanged:",     name: CNContactStoreDidChangeNotification,     object: nil) 

However, I have found two problems with this approach:

  1. I am notified for all changes, including those made by my own application.
  2. Notifications are spurious - I receive many notifications for a single change.

If I log the debug description of the notification when the change was made within my app, I get something like this:

NSConcreteNotification 0x7d3370e0 {name = CNContactStoreDidChangeNotification; userInfo = {     CNNotificationOriginationExternally = 1;     CNNotificationSourcesKey =     (     ); }} 

And if the changes are made externally:

NSConcreteNotification 0x7bf7a690 {name = CNContactStoreDidChangeNotification; userInfo = {     CNNotificationOriginationExternally = 1;     CNNotificationSourcesKey =     (     ); }} 

As you can see, nothing obvious with which to distinguish them.

Can anyone tell me how to get the same behavior from the Contacts Framework as one can get from ABAddressBookRegisterExternalChangeCallback?

0 Answers

Read More

Best performance in sampling repeated value from a grouped column

Leave a Comment

This question is about the functionality of first_value(), using another function or workaround.

It is also about "little gain in performance" in big tables. To use eg. max() in the explained context below, demands spurious comparisons. Even if fast, it imposes some additional cost.


This typical query

SELECT x, y, count(*) as n  FROM t  GROUP BY x, y; 

needs to repeat all columns in GROUP BY to return more than one column. A syntactic sugar to do this, is to use positional references:

SELECT x, y, count(*) as n  FROM t  GROUP BY x, 2  -- imagine that 2, 3, etc. are repeated with x 

Sometimes needs not only sugar, but also some semantic to understand complex context:

SELECT x, COALESCE(y,z), count(*) as n  FROM t  GROUP BY x, y, z  -- y and z are not "real need" grouping clauses? 

I can imagine many other complex contexts. Let's see usual solutions:

SELECT x, max(y) as y, count(*) as n  FROM t  GROUP BY x  -- best semantic! no need for other columns here 

where max() function can be any "sample()" (eg. first or last value). The performance of something that do nothing is better than max(), e.g. the aggregate function first_value(), but it needs a WINDOW, so lost performance. There are some old suggestions to implement first/last agg functions in C.

Is there some "get any one value fast" aggregate function with better performance than max() or GROUP BY X,2,...?
Perhaps some new feature in a recent release?

2 Answers

Answers 1

If you really don't care which member of the set is picked, and if you don't need to compute additional aggregates (like count), there is a fast and simple alternative with DISTINCT ON (x) without ORDER BY:

SELECT DISTINCT ON (x) x, y, z FROM t; 

x, y and z are from the same row, but the row is an arbitrary pick from each set of rows with the same x.

If you need a count anyway, your options are limited since the whole table has to be read in either case.

Then the first_last_agg extension is the only realistic option I see to gain some performance. But don't expect much.

For other use cases without count (including the simple case at the top), there are faster solutions, depending on your exact use case: emulating a loose index scan like @Mihai commented:

Answers 2

Not an offical source, but some thoughts an a question perceived as rather generic:

In general aggregators neeed to process all matching rows. From your question text you might target aggregators that try identifying specific values (max, min, first, last, n-th, etc). Those could benefit from datastructures that maintain the proper values for a specific such aggregator. Then "selecting" that value can be sped up drastically.
E.g. some databases keep track of max and min values of columns.
You can view this support as highly specialised internal indexs that are maintained by the system itself and not under (direct) control of a user.

Now postgresql focusses more on support that helps improving queries in general, not just special cases. So, they avoid adding effort for speeding up special cases that are not obviously benefitting a broad range of use cases.

Back to speeding up sample value aggregators.

With aggregators having to process all rows in general case and not hving a general strategy that allows short circuiting that requirement for aggregators that try identying specific values (sample kind aggregators for now), it is obvious that any reformulating of a query that does not lead to a reduced set of rows that need to be processed, will take similar time to complete.

For speeding up such queries beyond processing all rows you will need a supporting datastructure. With databases this usually is provided in the form of an index.

You also could benefit from special execution operations that allow reducing the number of rows to be read.

With pg you have the capability of providing own index implementation. So you could add an implementation that best supports a special kind of aggregator you are interested in. (At least for cases where you do need to run such queries often.)

Also, execution operations like index only scans or lazy evaluation with recursive queries may allow writing a specific query in a way that speeds compared to "straight" coding.

If you are targeting your question more into general approaches you might better consult with researchers on such topics as this then is beyond anything SO is intended to provide.

If you have specific (set of) queries that need to be improved, providing explicit questions on those might allow the community to help identifying potential optimizations. Trying to optimize without good base of measurement leads nowhere, as what yields perfect result in one case might kill performance in another.

Read More

Multiple versions of software at Azure marketplace and upgrade policy

Leave a Comment

We are planning to put our product on Azure marketplace. The product is installed on Windows server machines and is distributed in nature. The architecture that suits us the most is Iaas, however, we are concerned about keeping multiple versions and the upgrade policy. We normally release 2 versions of the software every year plus there could be more patches and service packs.

Please also note that our software doesn't have in-place upgrades. That means to upgrade our software, it is needed to be uninstalled and reinstalled.

We've googled to get some help but couldn't find any satisfactory answers. I'll appreciate if someone could. The questions we are really concerned about are;

  1. How many versions can/should we keep on marketplace?
  2. What should be the process to upgrade software on machines already running on Azure?
  3. How to handle public patches and service packs?

Thanks.

0 Answers

Read More

Wednesday, March 30, 2016

How to drag a row between other rows in UITableView or UICollectionView

Leave a Comment

I am trying to implement the view shown in the animation below:

enter image description here

I found a great control called TGLStackedViewController which does almost what I need. The way it performs the moving is by taking a snapshot of the card you want to move and adding it as a subview to the collectionView, while hiding the original card. When dragging has stopped the movable view is removed and the original card is made visible again.

This works well, but doesn't produce the result I want since the movable view covers all cards. I wish for the card being moved to always be between the two cells above and below, just like in the animation. But I am not sure how to do this since all items are on the same level. I would really like to avoid making a completely custom view control and if possible do this with either UICollectionView or UITableView.

0 Answers

Read More

What is the “ownerID” in Immutable.js?

Leave a Comment

I'm going through Immutable.js's source code and there's an ownerID field that I don't understand.

Here's the source for Map.asMutable() and Map.asImmutable(): https://github.com/facebook/immutable-js/blob/master/src/Map.js#L171

It seems like the only difference between a mutable and an immutable object are their ownerIDs. What is an ownerID and what is it used for?

3 Answers

Answers 1

If you track back the property:

L#14:

import { DELETE, SHIFT, SIZE, MASK, NOT_SET, CHANGE_LENGTH, DID_ALTER, OwnerID,           MakeRef, SetRef, arrCopy } from './TrieUtils' 

in src/TrieUtils.js :

L#36:

// A function which returns a value representing an "owner" for transient writes // to tries. The return value will only ever equal itself, and will not equal // the return of any subsequent call of this function. export function OwnerID() {} 

It is some property they create like hash to represent a virtual owner.

Answers 2

It is used to ensure mutability in asMutable returned instances. When asMutable is invoked, it ensures an __ownerId and returns the current instance back -

asMutable() {     return this.__ownerID ? this : this.__ensureOwner(new OwnerID()); } 

Then any supported mutating operations return the current instance back, instead of creating a new instance with the changes (which is key for immutability).

E.g., here's how the "clear" method operates based on the presence of __ownerId -

clear() {     if (this.size === 0) {       return this;     }     if (this.__ownerID) {       this.size = 0;       this._root = null;       this.__hash = undefined;       this.__altered = true;       return this;     }     return emptyMap(); } 

Notice that when this.__ownerID is present, the method returns the current instance (thereby mutating itself). But when it is absent, it returns a new map for ensuring immutability.

Answers 3

From the source code:

// A function which returns a value representing an "owner" for transient writes // to tries. The return value will only ever equal itself, and will not equal // the return of any subsequent call of this function. function OwnerID() {} 

My understanding of the above is that the this.__ownerID field is used to compare objects. A Map being compared against itself will have the same ownerID, while a Map being compared against another Map will see two different ownerIDs.

You can see an example of this usage a little farther down in the file in question:

__ensureOwner(ownerID) {   if (ownerID === this.__ownerID) {     return this;   }   if (!ownerID) {     this.__ownerID = ownerID;     this.__altered = false;     return this;   }   return makeMap(this.size, this._root, ownerID, this.__hash); } 

In fact, searching the entire repo, you'll see that this function is common across data types, with each type having a slightly modified version to return a correct new version of that type.

Read More

Possible way to add multiple git repositories in the same Google cloud project

Leave a Comment

Is there a way to add multiple git repositories in the same Google cloud project?

5 Answers

Answers 1

There is no way of doing this as of today. Every project can only have one remote repository.

Answers 2

It's definitely possible to have multiple local repositories that correspond with the same remote Google cloud repository.

The official documentation describes the following procedure for how to use a Cloud Source Repository as a remote for a local Git repository :

Create a local Git repository

Now, create a repository in your environment using the Git command line tool and pull the source files for a sample application into the repository. If you have real-world application files, you can use these instead.

$ cd $HOME $ git init my-project $ cd my-project $ git pull https://github.com/GoogleCloudPlatform/appengine-helloworld-python 

Add the Cloud Source Repository as a remote

Authenticate with Google Cloud Platform and add the Cloud Source Repository as a Git remote.

On Linux or Mac OS X:

$ gcloud auth login $ git config credential.helper gcloud.sh $ git remote add google https://source.developers.google.com/p/<project-id>/ 

On Windows:

$ gcloud auth login $ git config credential.helper gcloud.cmd $ git remote add google https://source.developers.google.com/p/<project-id>/ 

The credential helper scripts provide the information needed by Git to connect securely to the Cloud Source Repository using your Google account credentials. You don't need to perform any additional configuration steps (for example, uploading ssh keys) to establish this secure connection.

Note that the gcloud command must be in your $PATH for the credential helper scripts to work.

It also explains how to create a local git by cloning a Cloud Source repository :

Clone a Cloud Source Repository

Alternatively, you can create a new local Git repository by cloning the contents of an existing Cloud Source Repository:

$ gcloud init $ gcloud source repos clone default <local-directory> $ cd <local-directory> 

The gcloud source repos clone command adds the Cloud Source Repository as a remote named origin and clones it into a local Git repository located in <local-directory>.

Answers 3

Git submodule should do the trick. Add git repositories as submodules.

See

Answers 4

You currently cannot do this. We know this is a useful feature, and we're working hard on it. Stay tuned!

Answers 5

No, there isn't, but you can use Git subtree merges to add multiple "subrepositories" as folders in your main repository, which will do the trick.

See details here https://help.github.com/articles/about-git-subtree-merges/

(There are also submodules as @Shishir stated, but as I understand they are only set for your current local clone and won't be included in checkouts/clones done by others, so I think submodules won't work).

Read More