質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.47%
OpenCV

OpenCV(オープンソースコンピュータービジョン)は、1999年にインテルが開発・公開したオープンソースのコンピュータビジョン向けのクロスプラットフォームライブラリです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

1回答

2382閲覧

opencvでの余白の切り出し

yosutebito092

総合スコア26

OpenCV

OpenCV(オープンソースコンピュータービジョン)は、1999年にインテルが開発・公開したオープンソースのコンピュータビジョン向けのクロスプラットフォームライブラリです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2018/11/14 07:46

イメージ説明

こんな画像の赤い線で囲った領域をこんなに直角である必要はないのですが取り出したいです。
できたら取り出した領域のいまの赤い線の部分だけを取り出してグラフ関数にはできないでしょうか。真ん中の空白はなかったことにしてもいいです。
文字の部分はなくしてもらっていいです。

なにか方法はないですか?

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

tiitoi

2018/11/14 07:51

そのような処理をする最終的な目的はなんでしょうか?
fana

2018/11/14 07:57

「グラフ関数」とは?
yosutebito092

2018/11/14 08:02

この余白を取り出してラノベの構文の傾向を解析する研究をしています。領域の赤い線をcosとかsinの関数で出力できないかなーと。できたら多分gnuplotに入れていって平均とか取れるんじゃないかと考えてます。
tiitoi

2018/11/14 08:10

構文の傾向を解析ということは、文字を認識して自然言語処理するということでしょうか?
yosutebito092

2018/11/14 08:17

余白の形見れば文章量も必然的に決まるので、それを解析しようって感じですね
fana

2018/11/14 09:10

…ということは,単に赤い領域が取れればよいわけではなくて,「各行ごとに下からどれだけ余白があるか」みたいな結果が必要なんでしょうかね.
can110

2018/11/14 10:58

①すでに赤い線は引かれた(分かっている)状態からの問題ですか?②取り出したい「赤い線の部分」において、具体的に得たいデータは何でしょうか?線分を構成する座標群、面積(スカラー)?③(得たものを)「グラフ関数にする」とは具体的にどうしたいのでしょうか(グラフ関数とは?)?
yosutebito092

2018/11/14 13:21

赤い線はわかりやすくするために勝手に引きました。ほしいデータは画像の下から赤い線までの領域で、切り取った領域の赤い線の部分をy=の関数みたいに数式にできたらいいなと思ってます
guest

回答1

0

ベストアンサー

思いつく単純な手順:

  1. 上から下まで全て黒である(=文字がない)箇所のx座標範囲を求める.→複数の領域が見つかり,その多くは「行間」であるハズ.

→隣接する領域間の距離の最頻値あたりから,行(文字のある箇所)の幅を推定
→領域のx幅の最貧値あたりから,行間の幅を推定(行間の幅は行の幅よりも小さいとか何とか条件を付けたりして)

  1. これらの情報をもとに,各行(文字のある箇所)のx座標を推定
  2. 各行位置を下から上へ見ていき,黒範囲を決定

上記のような話を実装.

  • 当方,pythonがダメなのでC++です.
  • 各処理のクオリティが色々と雑です.
  • 質問の画像とは白黒が逆になってます(背景が白で,文字が黒)
  • 画像左右の文字が無い領域が,余白なのか空行なのか判断できません.
int main(void) { //(0)画像読込 cv::Mat Src = cv::imread( "TestLetter.png", CV_LOAD_IMAGE_GRAYSCALE ); if( Src.empty() )return 0; cv::imshow( "Src", Src ); //(1)各x座標における,黒画素の下端y座標を求めておく std::vector<int> YMax( Src.cols, 0 ); for( int y=0; y<Src.rows; ++y ) { const unsigned char *pI = Src.ptr<unsigned char>(y); for( int x=0; x<Src.cols; ++x, ++pI ) { if( *pI < 250 ){ YMax[x] = y; } } } //(2)文字が無いx区間を収集 std::vector< std::pair<int,int> > NonLetterReg; int RegLeft = -1; for( int x=0; x<YMax.size(); ++x ) { if( RegLeft < 0 ) { if( YMax[x]<=0 ) { RegLeft=x; } } else { if( YMax[x]>0 ) { NonLetterReg.emplace_back( RegLeft, x-1 ); RegLeft = -1; } } } if( RegLeft >= 0 ) { NonLetterReg.emplace_back( RegLeft, YMax.size()-1 ); } //(3)行と行間の幅を推定 int LetterWidth = 0; //行の幅 {//行の幅をNonLetterRegの隣接要素間の間隔の平均として推定 int SumDx = 0; for( int i=0; i+1<NonLetterReg.size(); ++i ) { SumDx += NonLetterReg[i+1].first - NonLetterReg[i].second; } LetterWidth = SumDx / (NonLetterReg.size()-1); } int BLWidth = Src.cols; //行間の幅 {//行間の幅の推定… 面倒なのでここでは最小値にしちゃう^^ for( auto &Reg : NonLetterReg ) { BLWidth = std::min( BLWidth, Reg.second-Reg.first+1 ); } } //(4)文字の下端位置を各行に関して調べる //※面倒なので結果はデータ化せずに直接画像に描画している cv::Mat Result; //結果描画用の絵 cv::cvtColor( Src, Result, CV_GRAY2BGR ); { int LetterLeft = NonLetterReg.front().second + 1; while( LetterLeft+LetterWidth-1 < YMax.size() ) { //着目行範囲x座標(の推定):LetterLeft~LetterRight int LetterRight = LetterLeft + LetterWidth-1; int Bottom = *std::max_element( YMax.begin()+LetterLeft, YMax.begin()+LetterRight ); //x範囲全域でYMax[x]が0だったら空行. //そうでない場合…LetterLeftの位置決めがあまりにも雑なのでYMax[LetterLeft]>0になる位置に微調整する if( Bottom>0 && YMax[LetterLeft]<=0 ) { ++LetterLeft; continue; } //※座標調整の実装が雑すぎるが //結果描画 cv::rectangle( Result, cv::Point(LetterLeft,Bottom), cv::Point(LetterRight,Result.rows), cv::Scalar( 0,0,255 ), -1 ); //次の行(の推定位置)へ LetterLeft = LetterRight + 1 + BLWidth; } } cv::imshow( "Result", Result ); cv::waitKey(); return 0; }

イメージ説明

投稿2018/11/14 10:05

編集2018/11/14 12:28
fana

総合スコア11663

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.47%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問