#include <cstdio>
#include <algorithm>
#define N 1010
#define ll long long
#define fo(x, a, b) for (int x = (a); x <= (b); x++)
#define fd(x, a, b) for (int x = (a); x >= (b); x--)
using namespace std;
int n, m, zf = 0, a[N << 1];

inline int calc(int l, int r) {
	return (l + r) * (r - l + 1) / 2;
}

int main() {
	scanf("%d%d", &n, &m);
	if (n < m) swap(n, m), zf = -1; else zf = 1;
	fo(i, 1, n) a[i] = i;
	int ec = n / m, st = 1;
	fo(i, 1, m) {
		if (i == m) a[n + i] = calc(st, n), st = n + 1;
		else a[n + i] = calc(st, st + ec - 1), st = st + ec;
	}
	fo(i, 1, n) printf("%d ", a[i] * zf);
	fo(i, n + 1, n + m) printf("%d ", -a[i] * zf);
	return 0;
}
#include <bits/stdc++.h>
using namespace std;
#define all(x) (x).begin(),(x).end()
#define YES() printf("YES\n")
#define NO() printf("NO\n")
#define isYES(x) printf("%s\n",(x) ? "YES" : "NO")
#define Yes() printf("Yes\n")
#define No() printf("No\n")
#define isYes(x) printf("%s\n",(x) ? "Yes" : "No")
#define isIn(x,y,h,w) (x >= 0 && x < h && y >= 0 && y < w)

#define int long long
//using ll = long long;
using P = pair<int,int>;

ostream &operator<<(ostream &os,const P &p){ return os << "(" << p.first << "," << p.second << ")"; }
template<class T>
ostream &operator<<(ostream &os,const vector<T> &v){
	for(int i = 0;i < v.size();i++) os << (i ? "," : "[") << v[i];
	os << "]";
	return os;
}

template<class T> T &chmin(T &a,const T &b){ return a = min(a,b); }
template<class T> T &chmax(T &a,const T &b){ return a = max(a,b); }

const int INF=1e+18;
const double EPS=1e-9;
const int MOD=1000000007;

const int dx[]={1,0,-1,0},dy[]={0,-1,0,1};

int h,w,x[2010][2010],y[2010][2010];

template<long long mod = 1000000007>
struct modint{
	long long a;

	modint() : a(0){}
	modint(long long t){
		a = t % mod;
		if(a < 0) a += mod;
	}

	operator long long() const{ return a; }

	bool operator==(const modint &x) const{ return a == x.a; }
	bool operator!=(const modint &x) const{ return a != x.a; }

	modint operator-() const{ return modint(a ? (mod - a) : 0); }
	modint operator~() const{ return pow(mod - 2); }

	modint operator+(const modint &x) const{ return modint(*this) += x; }
	modint operator-(const modint &x) const{ return modint(*this) -= x; }
	modint operator*(const modint &x) const{ return modint(*this) *= x; }
	modint operator/(const modint &x) const{ return modint(*this) /= x; }

	modint &operator+=(const modint &x){
		a += x.a;
		if(a >= mod) a -= mod;
		return *this;
	}
	modint &operator-=(const modint &x){
		a -= x.a;
		if(a < 0) a += mod;
		return *this;
	}
	modint &operator*=(const modint &x){
		a = a * x.a % mod;
		return *this;
	}
	modint &operator/=(const modint &x){
		a = a * (~x).a % mod; 
		return *this;
	}

	friend ostream &operator<<(ostream &os,const modint &x){
		return os << x.a;
	}
	friend istream &operator>>(istream &is,modint &x){
		long long t;
		is >> t;
		x = modint(t);
		return is;
	}

	modint pow(long long x) const{
		modint ret = 1,tmp = a;
		for(;x;tmp *= tmp,x >>= 1){
			if(x & 1) ret *= tmp;
		}
		return ret;
	}
};

signed main(){
	int cnt = 0;
	string s[2010];
	cin >> h >> w;
	for(int i = 0;i < h;i++){
		cin >> s[i];
	}
	for(int i = 0;i < h;i++){
		for(int j = 0;j < w;j++){
			if(s[i][j] == '.') cnt++;
		}
	}
	for(int i = 0;i < h;i++){
		x[i][0] = (s[i][0] == '.');
		for(int j = 1;j < w;j++){
			if(s[i][j] == '.') x[i][j] = x[i][j - 1] + 1;
			else x[i][j] = 0;
		}
		for(int j = w - 2;j >= 0;j--){
			if(x[i][j + 1] && x[i][j]) x[i][j] = x[i][j + 1];
		}
	}

	for(int i = 0;i < w;i++){
		y[0][i] = (s[0][i] == '.');
		for(int j = 1;j < h;j++){
			if(s[j][i] == '.') y[j][i] = y[j - 1][i] + 1;
			else y[j][i] = 0;
		}
		for(int j = h - 2;j >= 0;j--){
			if(y[j + 1][i] && y[j][i]) y[j][i] = y[j + 1][i];
		}
	}
	modint<> ans;
	for(int i = 0;i < h;i++){
		for(int j = 0;j < w;j++){
			if(s[i][j] == '#') continue;
			int r = x[i][j] + y[i][j] - 1;
			ans += (modint<>(2).pow(r) - modint<>(1)) * modint<>(2).pow(cnt - r);
		}
	}
	cout << ans << endl;
}